Best way to identify manually selected element - javascript

I'm doing a chrome extension that allows user to click on some links. The extension should analyze the page (1 time per 1 hour, server-side) and if the link is changed - notify. The extension should work on any "normal" web page.
My chrome extension just allows to select element. All other job is done on server side.
What I tried:
ID - the most obvious way, but a lot of web pages don't use ID for elements.
a tag with exact href. But I also need some notifications for position changes. And there is a big chance that the extension will work not only with links.
e.path - Should I keep it like html.child(0).child(2).child(1)... or identify them with their classes and types?
So, is there any good way to identify an element on some unknown page? How should I serialize the identifier?
I'm ok if it will not work after any major changes to html template.
Thank you :)

Assuming I'm reading your question right: You want to select some element on a webpage and have a server re-read that element on a timer loop to see if the element (text, for example) has changed.
Something like an ID would be easiest but, barring that, you might consider XPath, a standard for navigating through XML (or HTML) documents.
W3Schools Reference on XPath
Just a note: from a design perspective, this is going to be challenging because you don't have control over other pages. There's nothing stopping a website from changing IDs, reorganizing elements, etc.

Related

Testcafe can see button but not click on it

In a testcafe test how can I click on an element that is clearly clickable (with t.debug() I'm able to click on the element) and visible without using ClientFunction, or t.eval -- these "workarounds" recommended in testcafe's github issues do not work.
Some additional considerations:
the code I'm testing is Angular 1.7.
the Selector is verified as correct (and I tried various types of selectors)
testcafe version 1.8.4
I've tried various t.wait times before and after selection and click
I've tried changing the element type (<button> to <div>, etc)
Try waiting for the element to be visible before clicking
await element.with({ visibilityCheck: true }).with({timeout: 10000});
Here are some typical problems with unclickable elements, I know the link is for Selenium issues, but some solutions can be used regardless of the technology used.
If you already tried with various waiting to be visible/clickable solutions, the next thing that you might want to check is if you have multiple elements with the same id, one of them being invisible, so TestCafe is unable to uniquely identify the right element. In that case, you will need to improve the locator.
Another thing to consider is that the element might be out of the viewport (when not debugging). In that case, try changing the window size (or maximizing it) or moving to element.

How can I scroll in the background using JS?

I'm building a chrome extension where I have to access the innerText of some span elements. I can safely get them using simple document.querySelector commands.
But for some spans, it returns null because they don't exist yet in the DOM> (For security reasons, I cannot disclose which website this happens with but to make it more clear, LinkedIn does a similar thing where the Experience block is only loaded if you scroll down to it.)
Now, to quote the problem using that example: I want to get the value of a span which is inside that Experience section. If I run the script inside window.onload, it returns null because the span isn't there yet.
One solution is to simply scroll the page, (or even worse, ask the users of the extension to first scroll the page before running the extension.) However, I do not want to do that.
Is there a way in JS to scroll the page in the background without visual feedback to the user so that I can get the value of the HTML elements that are initially hidden?
Assume that the span I want to get has the following class: defense-rc4

Selecting an element with no particular id, class, xpath, etc

I am currently working on writing the test automation for a web application that loads as an SWF file for our end-users, but a fully functioning Javascript version exists for the sole purpose of automation.
I have means to navigate through the application with keyboard shortcuts, but when it comes to executing click commands, I have no luck at all. Upon inspecting with Firebug/Firepath, the only value that I could find was an xpath (no id exists, no class, no anything really).
The next issue is the xpath itself.
It is:
Really brittle.
.//*[#id='flow']/div[1]/div/div[7]/div/div[3]/div[4]/div/div/div/div/div/div/div/div[3]/div[1]/img
This appears to be the xpath to the image that represents the button, not the button itself.
Executing .click() commands on the above type of xpath will do nothing until you manually hover your mouse over the button (regardless of moveToElement commands), where it will "click" the image but no functionality will run.
So I'm wondering after digging around in the actual JavaScript looking for identifiers, is there any way to select an element through any other properties? Or is there any way I can better "identify" a function? Perhaps find the xpath to the button that the image represents?
Using JUnit and Java, if that helps.
Thanks
Apparently, my comments answered the OP's question, so here goes, for reference sake:
If you need "the button itself", as you wrote in your question, use Inspect Element from the browser to find out what the actual element is you need and then simply remove from the right-hand side of your XPath expression enough axis steps until the part that remains selects the ancestor element that is the actual button element.
Now you should be able to send it a click event.
I'm afraid there won't be much we can do about the XPath statement to be "brittle", simply because you do not have an identifier to go on. That means that if the structure of the page changes, you will have to change the XPath (unless some of the ancestor elements have some notable identifiers).

what happens if one set id attribute values of several html tags, the same string?

I recently saw a html page, that i thought the id of several html tags was the same, then I realized the ids are unique but it raises the question that what could have happened if the page actually used several tags
As i have heard id attribute of every html tag(if it has one) must be unique,
now i wonder what happens if it is not the case??
what possible errors can it cause?
does different browsers show different reactions for this issue?
does javascript and jquery codes that use duplicated ids run on both tags or what?
Duplicate ids can have various different effects. Which you experience will depend on the method you use to try to access them (and possibly also from browser to browser).
You'll affect all of them
You'll affect the first one
You'll affect the last one
You'll get a collection instead of an element, try to treat it like an element and get an error
Duplicate ids are not allowed in HTML. Don't make trouble for yourself. Use classes for groups and ids for unique identifiers.
Change them as soon as possible, to save a lot of headache in the future. For elements with same property use classes
About your queries,
Now i wonder what happens if it is not the case??
Well, the HTML is not a valid one anymore. Now a days it doesn't hurt much but still not preferred.
What possible errors can it cause?
Errors are little bit hard to predict. But with jQuery you are going to get many.
Does different browsers show different reactions for this issue?
Not sure.
Does javascript and jquery codes that use duplicated ids run on both tags or what?
jQuery will give you trouble. Consider a case where you have two input fields with same ID.
and you try to select second one with out noticing. jQuery('yourID').val() and you'll be selecting the firs value instead. Like this there are a lot of possibilities.
As you said, HTML id, per specs, must be unique. If one where to put duplicated id, the js behavior relative to those ids will be unpredicatable, and could even change between 2 calls.
Any js call on one id (jquery or not) will point to one of the id but without guarentee that :
It will be the same every call
It will have the same order between 2 page refresh
It will have the same behavior beween 2 different browser
It will have the same behavior betwween 2 time the same browser
The problems that could emerge depend on how toghtly the js code is coupled to the underlying element DOM structure anw could mostly point to a undefined exception and stop the js execution.

Does JQuery works on all the buttons with same ID (different pages)

I need to use JQuery to call vb function through function
$("[id*=Button1]").click();
I have many Button1 on both sub and master.
My JQuery is on sub content page. I wonder if it actually trigger the button1 on both master and sub content page?
Thanks very much!
JQuery will act on the entire rendered HTML. It makes no difference whether the HTML originated in a "master" or a "content" page on the server. If the HTML shows up on the client as a single page (as opposed to say, an <iframe>), JQuery will act on it.
On a side note, you should do your best to keep the "id" property of each HTML element unique. That's the way it's designed to be, and you should do yourself a long-term favor by observing that basic rule.
JQuery has lots and lots of selector rules, and I'm sure you can find some way of applying those selector rules to select the correct button. See http://api.jquery.com/category/selectors/ to get started. But using selectors creatively is much better than using the same id for different elements.

Categories