admin管理员组

文章数量:1401208

My program uses printJS which a library that helps format the content of the page for printing. I wanted to write tests with cypress to test that the print preview has been called. Currently I have a button that calls printJS when clicked and since cypress cannot interact with the print preview window, I thought it would be a good idea to stub the call to printJS then write an assertion that it was called once. I understand that this works with window.print() as you can stub that with this code.

cy.visit('http://127.0.0.1/',{
    onBeforeLoad: (win) => {
        cy.stub(win, 'print')
    }
})

Then assert with this

cy.contains('print').click()
cy.window().then((win) => {
    expect(win.print).to.be.calledOnce
})

My old button

<button type="button" class="btn btn-secnodary" onclick="window.print()">
    Print
</button>

But instead I used printJS which means my button now looks like this

<button type="button" onclick="printJS({printable: 'id_preview_modal_body', type: 'html'})" data-dismiss="modal">
    Print
</button>

The javascript gets loaded in as print.min.js which can be found here. I tried to stub the contentwindow but that doesn't seem to work so far. In the code for printJS, the printing happens here

frameElement.contentWindow.print()

from their github page, line 63

The way im stubbing it gives this issue

cy.visit('http://127.0.0.1:8000/notices/new/',{
    onBeforeLoad: (win) => {
        cy.stub(win, 'printJS')
    }
})

Uncaught TypeError: Cannot stub non-existent own property printJS

The assertion also gives this error

cy.window().then((win) => {
    expect(win.printJS).to.be.calledOnce
})

TypeError: [Function: init] is not a spy or a call to a spy!

I think the [Function: init] is a referring to const printJS = print.init from their index.js file. But i don't know how to proceed further in debugging this issue. Any help would be appreciated. Thanks!

My program uses printJS which a library that helps format the content of the page for printing. I wanted to write tests with cypress to test that the print preview has been called. Currently I have a button that calls printJS when clicked and since cypress cannot interact with the print preview window, I thought it would be a good idea to stub the call to printJS then write an assertion that it was called once. I understand that this works with window.print() as you can stub that with this code.

cy.visit('http://127.0.0.1/',{
    onBeforeLoad: (win) => {
        cy.stub(win, 'print')
    }
})

Then assert with this

cy.contains('print').click()
cy.window().then((win) => {
    expect(win.print).to.be.calledOnce
})

My old button

<button type="button" class="btn btn-secnodary" onclick="window.print()">
    Print
</button>

But instead I used printJS which means my button now looks like this

<button type="button" onclick="printJS({printable: 'id_preview_modal_body', type: 'html'})" data-dismiss="modal">
    Print
</button>

The javascript gets loaded in as print.min.js which can be found here. I tried to stub the contentwindow but that doesn't seem to work so far. In the code for printJS, the printing happens here

frameElement.contentWindow.print()

from their github page, line 63

The way im stubbing it gives this issue

cy.visit('http://127.0.0.1:8000/notices/new/',{
    onBeforeLoad: (win) => {
        cy.stub(win, 'printJS')
    }
})

Uncaught TypeError: Cannot stub non-existent own property printJS

The assertion also gives this error

cy.window().then((win) => {
    expect(win.printJS).to.be.calledOnce
})

TypeError: [Function: init] is not a spy or a call to a spy!

I think the [Function: init] is a referring to const printJS = print.init from their index.js file. But i don't know how to proceed further in debugging this issue. Any help would be appreciated. Thanks!

Share Improve this question edited Nov 27, 2018 at 18:40 Jondar the Templar asked Nov 27, 2018 at 18:11 Jondar the TemplarJondar the Templar 951 silver badge6 bronze badges 2
  • How are you importing the library (print.js)? – crabbly Commented Dec 8, 2018 at 20:10
  • I'm using django and i'm importing a folder with various *.min.js files. printjs.min.js is one of them. It's setup so that when it loads a template such as the one with the button, it loads all the *.min.js files. – Jondar the Templar Commented Dec 10, 2018 at 20:36
Add a ment  | 

2 Answers 2

Reset to default 5

The problem is the onBeforeLoad hook is called before printJS is initiated, when printJS is imported it invokes it's init() function and overwrites your stub in window.print.

This is stubbing too soon

cy.visit('http://127.0.0.1:8000/notices/new/',{
    onBeforeLoad: (win) => {
        cy.stub(win, 'printJS')
    }
})

Stubbing after ponent has loaded and printJS is initiated

const printStub

before(function(){

  cy.visit('http://127.0.0.1:8000/notices/new/')

  // maybe wait for loading to plete

  cy.window().then(win => {
    printStub = cy.stub(win, 'printJS')
  })
})

it('stubs printJS', () => {
  cy.contains('button', 'Print').click()
  cy.window().then(win => {
    expect(printStub).to.be.calledOnce
  })
})

This is the solution that worked for me. In my case I had a Print button on the page. That i need to click to open the window. I stubbed the window.

  cy.get('.white-header > .ui-g-12 > .pull-right').then((data) => {
  cy.window().then((win) => {
  cy.stub(win, 'open').returns("Print window is opened")
  data.click()
  expect(win.open).to.be.calledOnce
})
})

本文标签: javascriptHow to stub contentwindowprint with cypresstest printJS with cypressStack Overflow