Let's say I have an object that has a function that creates another object as part of its operation.
sinon = require('sinon')
chai = require 'chai'
sinonChai = require("sinon-chai")
chai.use(sinonChai)
chai.should()
Paper = {}
Paper.Origami = require('../assets/src/coffee/origami.coffee').Paper.Origami
describe '#throwOrigami', ->
it 'should create origami and throw it', ->
m = new Monkey()
throwSpy = sinon.spy(m, 'throwOrigami')
createSpy = sinon.spy(Paper, 'Origami')
# next function creates origami, then 'throws' it at someone
m.throwOrigami();
createSpy.should.have.been.calledWithNew
throwSpy.should.have.been.calledOnce
The Monkey class has a require at the top for Paper.Origami.
I can get this test to pass if I create an Origami inside the test, but it won't pass if I leave it to the create inside of the Monkey object. I suspect this is because the require paths differ between the two objects -- maybe node doesn't see them as the same object.
Question: can I get the sinon spy to spy on the creation of the Origami object that happens inside the Monkey object?
require resolves paths before looking in its cache, so it should not matter that the paths are different. However, you create a new Paper object with an Origami property in your test. Hence, when you spy on Paper, 'Origami', it is the property Origami of the Paper object you created locally in your test file which is replaced with a spy. I suppose you could do the following instead:
Paper = require('../assets/src/coffee/origami.coffee').Paper
If you now alter the Paper object, it would be the same as used in your Monkey module. However, I would suggest using something like proxyquire to spy or mock on dependencies.