I am trying to automate testing an application written in C++.
I use UI Automation: http://msdn.microsoft.com/en-us/library/ms747327.aspx
I used UIAVerify to find automationIds of some elements but some elements are showing as disabled(grayed-out) in the tool.
Does it mean interactions for some elements are not automatable? How to automate interaction for an element which does not have a AutomationId value?
EDIT : I am trying to use automation to click on a control that has ControlType.Custom and has Name property set for it. Is there a way to do this? I tried these two ways, both fail:
method 1:
//using framework white
var button = window.Get(SearchCriteria.ByControlType(ControlType.Custom).AndByText ("<Name Property>"));
method 2:
//using Automation Framework
aeCtrl = aeParentPanel.FindFirst(TreeScope.Children,
new PropertyCondition(AutomationElement.NameProperty, "<Name Property>"));
From the "How To Use UI Verify" Word .doc file that's linked to from the UIA Verify page on codeplex:
Note A dimmed (unavailable) node in the Automation Elements Tree indicates that the element is a member of the UI Automation Raw View but does not meet the conditions necessary to be considered a member of either the Content View or Control View. However, the element can still be tested from Visual UI Automation Verify. For more information, see the UI Automation Tree Overview.
What this basically means is that these elements are 'chrome' items, they are things like menu bars or scrollbars, rather than content such as list items. They are still there and can be tested.
--
Not every element has an AutomationID. It's really up to the developer to set these as appropriate for use in testing. In some cases, they come from the underlying framework: for example, for Win32 controls, the Control ID - if present - is used to generate the AutomationID. In WPF, you have to set the deverloper has to assign it via the AutomationProperties.AutomationId Attached Property.
Typically its only set for controls in dialogs, and is used to distinguish between them. Items within a control - eg. items within a list box - are usually identified by their Name instead (or Value, for other controls). This is especially the case with items that are generated from an external source - such as a list containing filenames - since there's no reasonable way AutomationIDs could be assigned in advance there.
Related
I have spied an input text box using the Application Modeller of Blue Prism and was able to successfully highlight the text box using the below XPath:
/HTML/BODY(1)/DIV(4)/main(1)/DIV(1)/DIV(1)/DIV(1)/DIV(2)/DIV(1)/DIV(1)/DIV(2)/IFRAME(1)/HTML/BODY(1)/DIV(2)/FORM(1)/DIV(3)/TABLE(2)/TBODY(1)/TR(1)/TD(1)/DIV(1)/DIV(1)/DIV(1)/DIV(2)/DIV(1)/DIV(1)/DIV(1)/DIV(1)/DIV(1)/DIV(1)/DIV(1)/DIV(1)/DIV(1)/SPAN(1)/DIV(1)/DIV(2)/DIV(1)/DIV(1)/DIV(1)/DIV(1)/DIV(1)/TABLE(1)/TBODY(1)/TR(1)/TD(1)/INPUT(1)
I wanted to use a more robust XPath and to achieve that I was trying to use the below XPath:
//*[#id="CT"]/div/div/div/div[1]/div[1]/table/tbody[1]/tr/td/input[1]
The above XPath was identifying the element correctly in Chrome but was getting the below error message when trying the same in Blue Prism:
Error - Highlighting results - Object reference not set to an instance of an object.
Let me know if I am doing anything incorrectly.
Sorry for replying to a pretty old one! The workaround we've devised for this scenario (where making the path dynamic requires too long of a loop / search) is to use Jquery snippets. If the page is using jquery it is trivial to execute these queries very quickly using the blue prism capability of executing javascript functions.
And we put in an enhancement request, because it'd be supremely useful functionality.
Update: As a user points out below, the vanilla js querySelector method is probably safer and more future proof than using jquery if it is possible to be used.
Blue Prism does not fully support the XPath spec; alas the construct you're attempting to use here won't work.
Alternatively, you can set the Path attribute of an application modeler entry to be Dynamic, which allows you to insert dynamic parameters from the process/object level to pinpoint elements you'd like to interact with.
Unfortunately Blue Prism doesn't actually use "real" XPaths, but only an extremely limited subset: Absolute paths without wildcards. (Note: It is technically possible to match the XPath to a string with wildcards, but this seemingly causes BP to check every single element in the document, and is so slow it is almost never the right solution.)
For cases where an element can't be robustly identified via the BP application modeler (maybe because it requires complex or dynamic selectors), my workaround is to inject a JS snippet. JS can select elements much more reliably, and it can then generate the BluePrism path for that element.
Returning data from JS to BluePrism is not trivial, but one of the nicer solutions is to have JS create a <script id="_output"> element, put JSON inside it, then have BluePrism read the contents of this element.
I have a set of tabs with proper roles and attributes for accessibility support. The content that tab controls gets loaded in via ajax. But each wrapper for the content loaded in also has proper tab pane roles and attributes.
The problem is, when I run an automated audit using Chrome Accessibility Tools, the test fails stating that the corresponding ID of the tab pane is missing for all of the tabs except the one that's currently active (because that wrapper with ID has been loaded). The exact error states: "ARIA attributes which refer to other elements by ID should refer to elements which exist in the DOM."
Since the ID will exist once the tab with the corresponding aria-controls attribute is active, is this really an error? Or is this just a case of a false positive because it's an automated test and they can only do so much.
In summary, What does aria-controls do and does it really need to refer to an ID that currently exists in the DOM?
aria-controls give your assisting technology a way to move to the controlled element.
If this element is not in the DOM or can't be accessed, then yes it's an error.
The two (the element with aria-controls as well the element with the referenced id) must exist at the same time, whether at page render or via JS injection.
The DOM is parsed by the UA/AT combo before the user even gets to the control or your script fires to make it exist. If you use JS injection then you need to make sure the DOM is re-parsed.
This would apply to aria-owns as well.
I don't know whether the following would work in your architecture, but it would solve the error problem:
Design the tabs so they are all in the page at the time it loads. Format those that should not be shown to be outside the viewport using absolute positioning and something like "left: -99em." Use AJAX to reset the positioning when the time has come to display the tabs. The result is that the ARIA ID dependencies will always be valid because the tabs are always part of the DOM.
Is there a way how to display some contacts from Outlook's contact list in different manner?
So far I've seen, that there is quite some customization available for Office applications, however I haven't seen anything even remotely close to this functionality.
No, there is no way to display Outlook contacts in a different color.
Well, indeed this is what I found - it is possible only via adding of the new AutoFormatRule to the Outlook.TableView.
Sample code would be something like:
Outlook.AutoFormatRule autoFormatRule = tableView.AutoFormatRules.Add("My own rule");
autoFormatRule.Font.Bold = true;
autoFormatRule.Font.Strikethrough = true;
autoFormatRule.Filter = <filtering>;
tableView.Save();
tableView.Apply();
For filling in 'filtering' part one can use DASL Queries
But I still need to figure out what to do with the non-list views.
I can suggest only one possible way - replace the default folder view with a custom form where you can display entries in the way you need. See Creating Adjacent Windows In Outlook for more information.
Also you may consider using Add-in Express. They provide such layouts out of the box. See Advanced Outlook view and form regions.
Note, you can use any .net controls on top of custom forms.
My application under test has been developed by external suppliers so I have no control over the HTML structure. The application is extremely Javascript and Ajax heavy, with numerous dynamically generated buttons and auto-complete lists.
In other words, the characteristics of the pages are that they are filled with:
Elements with no fixed IDs (IDs are generated on the fly and have
numbers or other text dynamically added to them)
The same happens with some classes
Most of the times the buttons have no text associated with them since they are either custom coded 'down' arrows for lookup lists
(which aren't lookup lists but hidden divs) or '+' and '-' icons to
maximise or minimise portions of the content. -
It is therefore very difficult to identify these elements, especially the buttons.
I am trying to write a generic 'I click on the button near y' type of step so that it is not necessary to hardcode each and every button (assuming I can even get something to identify them with) into each and every test.
The thinking behind this is that normally there is a label of some sort close to the button at least.
What I want to to is to find the text label, then see if there is a button inside the same scope, and if there is not, move 'back' through the parent elements, and check if there is a button inside the scope of each parent level, up to 5 parents.
There might be all sorts of problems with this approach but I am just curious to see if this will work in general. I have run into some problems.
First I tried to use Xpaths, so I got the Xpath of the parent through :
$parentelement = $element->getParent();
$parentXpath->getXpath();
This would give me an Xpath of : (//html//span[text()='Cost center'])[1] and moving up through the parent elements all the time, they would become successively:
(//html//span[text()='Cost center'])[1]/..[1]
(//html//span[text()='Cost center'])[1]/..[1]/..[1]
and so forth.
The actual button is located in: (//html//span[text()='Cost center'])[1]/..[1]/..[1]//button but it has to go through all the parent elements in order to get there, so it will start with (//html//span[text()='Cost center'])[1]//button and should end with (//html//span[text()='Cost center'])[1]/..[1]/..[1]//button where it should find the button.
Trying to use Xpath I used:
$button_element = $session->getPage()->find('xpath',$parentXpath."//button")
I soon saw that the 'find' command appends an //html to the front of your xpath string so the Xpath that it tried to use ended up being (for each parent Xpath, but using this one as an example):
(//html(//html//span[text()='Cost center'])[1]/..[1])
I then stripped out the brackets as well as the //html, leaving me with:
//span[text()='Cost center'][1]/..[1]
but when I tried:
$button_element = $session->getPage()->find('xpath',$strippedParentXpath."//button")
I got the following error:
SyntaxError: Failed to execute 'evaluate' on 'Document': The string '(//html//span[text()='Cost center'][1]/..[1]//button)[1]' is not a valid XPath expression
However, Firepath can execute this expression and does not show a syntax error for it, although it does not find the actual button (since the button is actually located one level up, where Firepath DOES find it).
So my question 1 is: What is wrong with my Xpath that I can't use it in the find? It actually looks as if //span[text()='Cost center'][1]//button does not throw the same exception, since as I said, I am looping through the parent Xpaths, and it starts with //span[text()='Cost center'][1]//button. It crashes on //span[text()='Cost center'][1]/..[1]//button.
My second option was to get the parent element each time, starting with finding the text on the page, but then to search for a button inside the scope of the parent element using the findbutton functionality.
Looping through the parent elements (up to a maximum of 5):
$parentelement = $parentelement->getParent();
$butonelement = $parentelement->findbutton('xxx');
In other words, find ANY button in the scope of the parent element. The problem I have is how to specify a generic 'button'.
One has to associate SOME text with the button (depicted by the 'xxx' above).
But this is a typical example of buttons in the application:
<button class="autocomplete_button" type="button" id="button_OM_1"> </button>
Where the class is used more than once, and the ID is auto-generated and not the same number all the time. There is no text associated with the button since the class specifies an image.
Question 2: So how can I use 'findbutton' to generically find a 'button' no specific distinguishing characteristics? Please note that I actually did try findbutton("button"), taking the chance that there might be a 'button' somewhere in a button, but this did not work either. At least, it doesn't work consistently and by that I mean that the same test randomly seems to either find or not find the same button when I run the test a couple of times.
After doing some more investigation on this issue I have found the following:
My method of trying to find the closest button to a piece of text via traversing 'up' through the scope of the divs and spans around the text (using xpath) is actually working.
What is NOT working is SAHI, which I am using as the web driver. In other words, it is not a Behat/Mink problem, it is SAHI specific issue.
I tried the same code using Selenium2 and it executes perfectly.
I still require an answer to question 2 - how can I use findbutton() without a specific parameter such as the ID, name or value but I will see if I can find an answer to that question separately and on the Behat user group since I do think that is a Behat/Mink specific issue.
I normaly use css selector and with that, I use to navigate to the class and ID's that the button is inside. it is easier than xpath I think, like you can use
$this->getSession ()->getPage ()->find ( 'css', '.parrent1 .parrent2 .autocomplete_button ' );
I think this will help you as you know which button your gonna use in each scenario
In an Xpage running on Domino 9.0.1 I'm using a rich text control with some custom toolbar configuration using the control's "attr" property as it is described here: https://frostillic.us/f.nsf/posts/quick-and-dirty-ckeditor-toolbar-setup-for-xpages
I added the link toolbar template using
<xp:this.attrs>
<xp:attr name="toolbar">
<xp:this.value><![CDATA[[["Link", "Unlink", "Anchor"]]]]></xp:this.value>
</xp:attr>
</xp:this.attrs>
All three buttons are displayed fine, esp. I'm able to define an anchor link target.
But trying to reference the anchor target I find that the Link dialog is somewhat incomplete as I can't define my link to use a relative target on the same page. I tried entering a reference in the dialog's URL field as #myAnchorId, but that results in a link looking like this:
....
Here's an image of the dialog that pops up from my Xpage when I hit the "URL link" button:
And this is what the dialog looks like that I can test from the CKEditor Samples page:
I'm aware that the samples page uses CKEditor V 4, so the dialog is somewhat different, but even V 3.6 should be able to reference anchor links using the dialog.
I already looked up on the installed ckeditor's version; \DominoData\domino\html\ckeditor\version.txt says:
cke_version=3.6.6.2
cke_revision=20130606-1534
Question is: what's missing here? Do I have to somehow modify the dialog?
Oh my, finally got it to work; #IBM: this feature truly could use some proper documentation! I'll mark this answer as a community wiki.
Indeed a different dialog is used here, which btw appears to apply to all the dialogs in use with Domino's CKEditor implementation. The trick in my case is to use one of the custom toolbar items instead of the standard one; up to now I found three of those customized items:
use MenuLink instead of the standard Link item; this item
consists of two sub items ('URL Link' and 'Anchor Link'), each calling its own dialog version; the resulting toolbar definition then looks like this: ['MenuLink', 'Unlink', 'Anchor']
use MenuPaste instead of the standard Paste item; again, this
item consists of two sub items ('Paste' and 'Paste as text'), again
each calling its own dialog version
use LotusSpellChecker to add IBM's own spell checking feature, where CKE's standard spell checker isn't working
I found hints to those three custom items inside my local \DominoData\domino\html\ckeditor\config.js. Don't know if those are all custom items available to day.
EDIT:
IBM's Domino Designer Xpages User Guide mentions another means of customizing the toolbar; the section unfortunately is incorrect in describing the options for the toolbarType attribute: be aware that all named types must start with capital letters, e.g. Basic, Slim, Medium, Large, Full, while the also mentioned Lite type isn't working at all; mistyping or using a non-existing value results in the editor not being displayed at all.
The link dialog that you're using is not the default one, so you should check how to modify it or replace it with the default one.