Can not click on the PayPal button inside the iframe - Cypress - iframe

I am writing e2e Testcases on Cypress for webshop, we have integrated PayPal and I am unable to click on the PayPal button with in the iframe.
I always get an error in finding the element in iframe.
someone have an idea how can I do that?
code
cy.get('iframe')
.getframe3D()
.find('paypal-button-number-0')
Command
Cypress.Commands.add('getframe3D', { prevSubject: 'element' }, $iframe => {
return new Cypress.Promise(resolve => {
$iframe.ready(function() {
resolve($iframe.contents().find('body'));
});
});
});

Interacting with iframe is quite tricky in Cypress however it's possible. Your custom command looks correct and it worked for me as well. However, you can also try below way and check if it is working for you.
Here provide CSS selector for the iframe as an argument getIframeBody() function.
cy.getIframeBody('iframe').find('paypal-button-number-0').click()
Custom Commands
Cypress.Commands.add('getIframeBody', (iframe) => {
return cy.get(iframe).then($iframe => {
const $body = $iframe.contents().find('body')
cy.wrap($body)
})
})
For more info you can follow the cypress blog to interact with iFrame

Your custom command to get the iframe body is fine, you just have the wrong selector for the button.
Since it's a class, you need a . prefix
cy.get('iframe')
.getframe3D()
.find('.paypal-button-number-0')

Related

createPages in Gatsby issues ; duplications and unrendered content

I've had a few errors trying to render single blog posts.
I tried using the page template with /post/{post_name} and I was getting this error:
warn Non-deterministic routing danger: Attempting to create page: "/blog/", but
page "/blog" already exists
This could lead to non-deterministic routing behavior
I tried again with /blog/{post_name}.
I now have both routes, which I'm not sure how to clean up; but more importantly, on those pages, nothing renders, even though there should be an h1 with it's innerhtml set to the node.title and likewise a div for the content.
I've uploaded my config and components to https://github.com/zackrosegithub/gatsby so you can have a look.
Not sure how to fix
I just want to see my content rendered on the screen.
Developer tools don't seem to help when there's no content rendered as I can't find anything to inspect to try to access it another way.
Thank you for your help
Your approach is partially correct. You are using a promise-based approach but when using then() you are already settling and partially resolving it so you don't need to use the callback of resolve(), which may be causing a duplication of the promise function so try removing it.
Additionally, you may want to use a more friendly approach using async/await functions. Something like:
exports.createPages = async ({ graphql, actions, reporter }) => {
const yourQuery= await graphql(
`
{
allWordpressPost {
edges{
node{
id
title
slug
excerpt
content
}
}
}
}
`
if (yourQuery.errors) {
reporter.panicOnBuild(`Error while running GraphQL query.`);
return;
}
const postTemplate = path.resolve("./src/templates/post.js")
_.each(yourQuery.data.allWordpressPost.edges, edge => {
createPage({
path: `/post/${edge.node.slug}/`,
component: slash(postTemplate),
context: edge.node,
})
})
})
// and so on for the rest of the queries
};
In addition, place a console.log(pageContext) in your postTemplate to get what's reaching that point and name the template as:
const Post = ({pageContext}) => {
console.log("your pageContext is", pageContext);
return <div>
<h1>
{pageContext.title}
</h1>
</div>
}
export default Post;

What is the cypress cy.contains() equivalent in webdriverio?

I have mainly worked with cypress previously for e2e automated testing, I have now started working on webdriverIO. So for a cypress command such as
cy.get("[data-testid='nav-bar']").contains("Search Box").click();
What would be the equivalent for this in webdriverIO? I have tried the following approach in a PageObject Model.
class HomePage extends Page {
get navBar() {
return browser.$("[data-testid='nav-bar']");
}
openSearchBox() {
this.navBar().click('//*[text="Search Box"]');
}
}
However, this approach does not seem to work, any help on this would be appreciated.
Leaving Page Objects asside for now, you'd type this in WebdriverIO:
const bar = $('[data-testid='nav-bar']');
expect(bar.getText()).toInclude('Search Box');
bar.click();
You can use chai for the assertion instead of Jest Matchers:
const expectChai = require('chai').expect;
// ...
expectChai(bar.getText()).to.have.string('Search Box');
// ...
The exact analog to
cy.get("[data-testid='nav-bar']").contains("Search Box").click();
can be achieved with xpath selector
$("[data-testid='nav-bar']").$("./*[descendant-or-self::*[contains(text(), 'Search Box')]]").click();
It looks a bit ugly though, consider adding a custom command that would mimic Cypress's contains:
// put this to `before` hook in your wdio.conf.js
browser.addCommand('cyContains', function(text) {
this.waitForExist()
return this.$(`./*[descendant-or-self::*[contains(text(), '${text}')]]`)
}, true)
$("[data-testid='nav-bar']").cyContains("Search Box").click();
P.S.
Check out the selector in the browser console right on this page, paste in the browser console
$x("//span[descendant-or-self::*[contains(text(), 'Search Box')]]")

Deep Link doesn't open the app instead does a google search

I have been using Expo to develop a react-native app, The functionality I am currently trying to implement is to share a link with friends on platforms such as fb messenger/whatapp or even normal texts and when they click this link it will launch my app to a specific page using the parameters.
After extensive research online - I’ve come to a blocker, following expo’s documentation I defined a scheme for my app - when I press share everything works correctly a message is created and I’m able to share content but only as string.
I am using react-natives Share library to share to an app and I’m using Expo to provide me with the link.
Ideally my first goal is to get the app opening using the Expo Link before I explore further into adding more functionality to the link.
Share.share({
message: "Click Here to View More! " + Linking.makeUrl( ' ' , { postkey : "7a5d6w2x9d6s3a28d8d});
url: Linking.makeUrl( ' ' , { pkey : gkey });
title: 'This post is amazing',
})
.then((result) =>{
console.log(result)
if(result === 'dismissedAction'){
return
}
})
.catch((error) => console.log(error))
In the root of my app I have also defined the event handlers: App.js
_handleRedirect=(event)=> {
let {path,queryParams} = Linking.parse(event);
Alert.alert(`queryparams : ${event} path : ${path} `)
this.props.navigation.navigate("Post_Detail",{key:queryParams.postkey})
}
}
componentDidMount() {
let scheme = 'nxet'
Linking.getInitialURL()
.then(url => {
console.log("App.js getInitialURL Triggered")
// this.handleOpenURL({ url });
})
.catch(error => console.error(error));
Linking.addEventListener('url', ({url}) => this._handleRedirect(url));;
}
componentWillUnmount() {
Linking.removeEventListener('url', this.handleOpenURL);
}
When I share the link to Whatsapp, Facebook Messenger or even just messages or notes it appears as myapplink://, I try to enter this into the browser and instead of asking me to open my app - it does a google search.
Please note I am attempting to have this working on Android Device and facing this issue
Is there something I am doing incorrectly?
Any help is much appreciated. Thanks.
You can not open external links, means other than http, https on Android. But you can on iOS. In order to be able to open your expo links, you need proper anchor tags on android. You can create html mails and give it a try, you will see it is gonna work on Android as well.

Branch Deep Linking not working in Google Analytics hitCallback

I'm using both Google Analytics and branch.io in this website.
The website is designed for mobile.
The problem is that when clicking the banner with text "OPEN", the app cannot be opened.
Here is the code for the click:
$scope.openApp = () => {
let appOpened = false;
const open = () => {
if (!appOpened) {
appOpened = true;
branch.deepviewCta();
}
};
$timeout(open, 1000);
ga('send', 'event', 'homepage', 'download', {
hitCallback() {
open();
}
});
};
If I get rid of the GA code, it works fine:
$scope.openApp = () => {
let appOpened = false;
const open = () => {
if (!appOpened) {
appOpened = true;
branch.deepviewCta();
}
};
$timeout(open, 1000);
open();
};
The reason I put open() in hitCallback is to make sure GA sends out the hit because open() will redirect to another page.
Can you help me?
Alex from Branch.io here:
The Branch deepviewCta() function works on iOS 9+ by triggering an automatic redirect to a Universal Link URL (which opens the app) and then going to a fallback URL if that fails. But Apple is very specific about the situations in which a Universal Link is allowed to launch the app (including things like how long of a pause is allowed before redirection). Of course these restrictions are not public, so all we can do is guess. My suspicion is that putting the deepviewCta() function inside a GA callback is falling outside of Apple’s rules, so the app never opens and you are instead being sent to the fallback URL.
I can think of two options here:
You can build some way to trigger the GA and Branch functions separately so that they don’t conflict with Apple’s requirements.
We actually have a brand new, one-click integration with Google Analytics, which you can read about here and here. If you set that up, you’ll get all Branch-related events automatically instead of needing to manually collect link click data.
Hopefully that helps!

Framework7 starter page "pageInit" NOT WORKING

anyone using framework7 to create mobile website? I found it was great and tried to learn it by myself, now I meet this problem, after I create my App, I want to do something on the starter page initialization, here, my starter page is index.html, and I set data-page="index", now I write this below:
$$(document).on('pageInit', function (e) {
var page = e.detail.page;
// in my browser console, no "index page" logged
if (page.name === 'index') {
console.log("index page");
});
// but I changed to any other page other than index, it works
// my browser logged "another page"
if(page.name === 'login') {
console.log('another page');
}
});
Anyone can help? Thank you so much.
I have also encountered with the same problem before.
PageInit event doesn't work for initial page, only for pages that you navigate to, it will only work for index page if you navigate to some other page and then go back to index page.
So I see two options here:
Just not use pageInit event for index page - make its initialization just once (just make sure you put this javascript after all its html is ready, or e.g. use jquery's on document ready event)
Leave index page empty initially and load it dynamically via Framework7's mainView.loadContent method, then pageInit event would work for it (that was a good option for me as I had different index page each time, and I already loaded all other pages dynamically from underscore templates)
I am facing same issue and tried all solutions in various forums.. nothing actually worked. But after lot of RnD i stumbled upon following solution ...
var $$ = Dom7;
$$(document).on('page:init', function (e) {
if(e.detail.page.name === "index"){
//do whatever.. remember "page" is now e.detail.page..
$$(e.detail.page.container).find('#latest').html("my html here..");
}
});
var me = new Framework7({material: true});
var mainview = me.addView('.view-main', {});
.... and whatever else JS here..
this works perfectly..
surprisingly you can use "me" before initializing it..
for using for first page u better use document ready event. and for reloading page event you better use Reinit event.
if jquery has used.
$(document).on('ready', function (e) {
// ... mainView.activePage.name = "index"
});
$(document).on('pageReinit', function (e) {
//... this event occur on reloading anypage.
});

Resources