Closed kvanderwyk closed 4 years ago
I think your updated approach is on the right track. There is some discussion here which may be relevant to you.
May be try using action.getName() to ensure you are mocking the correct action. Do you know if the timeout failure happens in waitFor or somewhere else? If its possible for you to share an unmanaged package or a deployable sfdx project with repro, I can have a closer look.
Hi @esalman-sfdc, thanks for your response. The timeout happens when rendering the component (via $T.createComponent
) for the third test in the suite. This happens regardless of what in particular is being tested -- I can have 15 tests and have tried randomly disabling/enabling them; if I run 2 at a time it works fine, 3 or more and I get the timeout from $T.createComponent
. The spec times out before getting to the waitFor
or anything else.
I will try debugging with action.getName()
as you suggest just to rule that out, and will see if I can repro this in an SFDX environment that doesn't expose our code.
@kvanderwyk I don't know if it helps you, but using the mocha version of the script, I make a call to update the timeout before each test:
const { expect } = chai;
const sandbox = sinon.sandbox.create();
describe('MyComponent', function test() {
this._timeout = 5000;
this._retries = 3;
afterEach(() => {
$T.clearRenderedTestComponents();
sandbox.restore();
});
});
Apologies in advance for the wordy post but I wanted to provide enough context. I've posted this as a question on StackExchange but haven't gotten any response there, so forgive me for repeating it here, but I'm having trouble finding enough examples of LTS use cases to help me figure this out. This is also somewhat related to Keith's question in #54 ...
I’m looking for help/examples for setting up tests of a component which calls a
load()
method viaafterScriptsLoaded
, then renders data based on the result of the load (which calls a server-side controller) — something like this:Component
Controller
Test suite
The specific problem I’m struggling with is where to place the
spyOn
(either inside thecreateComponent
callback as above, or before it, or elsewhere) and also where to calldone()
in thebeforeEach
. The way the example is defined above, the first spec passes. But when the second spec runs, the scripts are already loaded, so thatload()
call happens immediately, before thecreateComponent
callback happens (and so the spy is not registered and thedone()
function inside it is never called). I’ve tried moving the spy outside of thecreateComponent
callback and callingdone()
in different places, but each results in a condition where either therenderedComponent
var is not defined by the timedone()
is called (and thus the specs fail) or thedone()
method is never called due to the order that things execute the second time through and I get a timeout.Is there a better way to structure this spec so that the order of the load call in relation to when the component is done rendering can be more predictable? I prefer to keep my
it
blocks simple and re-render the component each time, and re-rendering the component with different data to test conditional display is required for this test.UPDATE
After experimenting a bit more I've tried modifying the structure of the beforeEach to this:
To summarize the difference from the above version, this moves registering the spy out of the
createComponent
callback, which ensures it always happens. Then I am using a bit of a hack withwaitFor
to make sure the pieces of the component under test have indeed been rendered before testing them. This seems to result in a consistent order of operations, but now I am seeing timeouts (using the LTS-defined 3s) with the$T.createComponent
, but only when running three or more specs. The first two specs run quickly and without a problem.I'm hoping that I'm missing something obvious with this setup, does anyone have any ideas or examples of doing something similar?