问题描述
我有以下代码:
cy.get('input:checkbox').first().as('firstCheckbox').then(() => {
cy.get('@firstCheckbox').should('be.checked').click()
cy.get('.globalMessage-display > :nth-child(1) > .alert').should('be.visible')
cy.get('.globalMessage-display > :nth-child(1) > .alert').should('not.exist')
cy.get('@firstCheckbox').should('not.be.checked').click()
cy.get('.globalMessage-display > :nth-child(1) > .alert').should('be.visible')
cy.get('.globalMessage-display > :nth-child(1) > .alert').should('not.exist')
cy.get('@firstCheckbox').should('be.checked')
})
在cy.get('@firstCheckbox').should('be.checked').click()
之后,复选框移到最后一个索引位置,而不是第一个。
根据我对别名的理解,这应该无关紧要,因为我用('@')
来引用它,而且它在哪个位置并不重要。不幸的是,下一个cy.get('@firstCheckbox')
访问的是新的第一个元素,而不是我最初引用的元素。我也不能从文档中弄明白这一点。
错误在哪里?
https://docs.cypress.io/guides/core-concepts/variables-and-aliases
https://docs.cypress.io/api/commands/as
更新@agoff:
它似乎在您的代码中工作得更好,但是我注意到新代码有一个新问题。 如果取消选中该复选框,则类将使用js重新加载,导致其从dom中短暂消失。在那之后,它再也找不到它了,测试中止。 我也尝试了重新加载,但它再也找不到该元素了。如何处理此问题?
选中的复选框类的名称为custom-control-input ng-untouched ng-pristine ng-valid
。取消选中类名称后,将其更改为custom-control-input.ng-untouched.ng-valid.ng-dirty
一秒钟,然后删除该元素并将其重新加载到类名为custom-control-input ng-untouched ng-pristine ng-valid
的DOM中。这里的问题是,第二个cy.wrap($el)
试图查找元素custom-control-input.ng-untouched.ng-valid.ng-dirty
,尽管搜索并找到了类为custom-control-input ng-untouched ng-pristine ng-valid
的初始元素。那是我不明白的另一件事。
推荐答案
如果在单击事件期间,应用程序删除输入并在末尾追加一个新输入,则会发生这种情况。则您的别名无效,因为它指向不再位于DOM中的元素。
如果我移动单击处理程序中的元素,您的代码将正常工作。
如果我克隆单击处理程序中的元素,您的代码将失败。
要做什么?
单击后刷新别名()
cy.get('input:checkbox').first().as('myCheckbox').then(() => {
cy.get('@myCheckbox').should('be.checked').click()
.then(() => cy.get('input:checkbox').last().as('myCheckbox')) // it's last now!
cy.get('.globalMessage-display > :nth-child(1) > .alert').should('be.visible')
cy.get('.globalMessage-display > :nth-child(1) > .alert').should('not.exist')
cy.get('@myCheckbox').should('not.be.checked').click()
.then(() => cy.get('input:checkbox').last().as('myCheckbox'))
cy.get('.globalMessage-display > :nth-child(1) > .alert').should('be.visible')
cy.get('.globalMessage-display > :nth-child(1) > .alert').should('not.exist')
cy.get('@myCheckbox').should('be.checked')
})
alias命令还有另一个技巧。
如果克隆并替换该元素,则原始元素将从DOM分离。
cy.get('@alias')
检测分离的元素并重播原始命令以自动刷新。
它不适用于.first()
,因为元素更改了位置。
但是,如果您使用data-cy
属性而不是.first()
,您的代码将正常工作。
cy.get('input:checkbox[data-cy="first-checkbox"]')
.as('myCheckbox').then(() => {
cy.get('@myCheckbox')
.should('be.checked').click() // cloned and moved to another position
...
cy.get('@myCheckbox') // detached by previous click
.should('not.be.checked').click() // so alias replays original get
// with [data-cy="first-checkbox"]
...
cy.get('@myCheckbox').should('be.checked') // as above
})
以下是执行此操作的Cypress代码
let { subject, alias, command } = aliasObj
const resolveAlias = () => {
if ($dom.isElement(subject)) { // if this is a DOM element
const replay = () => {
cy.replayCommandsFrom(command)
return undefined
}
if ($dom.isDetached(subject)) { // is it detached?
subject = subject.filter((index, el) => $dom.isAttached(el)) // all detached?
if (!subject.length) {
return replay() // perform the replay
}
}
这篇关于柏树中的别名(`.as`)是什么?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持编程学习网!