-
Notifications
You must be signed in to change notification settings - Fork 668
Testing properties validation #34
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
That would mean unit testing that Vue is working, which should be out of scope of any test. Instead you are probably interested not in the fact that validation rule works correctly, but that the validation is configured correctly. That should be easier to ensure. |
Agree with wparad. you should pass a couple of valid and invalid values to components and verify that the value either passes or doesn't, by checking if the prop's value on the component is |
Well I'd agree if that would work in that way... but how's currently working you cannot test that, since even if the value is invalid, it still passes. Let me explain. Given a Message component with a props: {
message: {
type: String,
required: true
}
} I'd expect the following test to fail, but it doesn't:
And of course, if you pass no message, it will be undefined, which doesn't test anything. I'd like to test that a property of a component indeed is required and validates properly. Right now the cleaner it got is like this: let spy = jest.spyOn(console, 'error')
afterEach(() => spy.mockReset())
it('message is of type string', () => {
cmp = createCmp({ message: 1 })
expect(spy).toBeCalledWith(expect.stringContaining('[Vue warn]: Invalid prop'))
})
it('message is required', () => {
cmp = createCmp()
expect(spy).toBeCalledWith(expect.stringContaining('[Vue warn]: Missing required prop'))
})
it('message has at least length 2', () => {
cmp = createCmp({ message: 'a' })
expect(spy).toBeCalledWith(expect.stringContaining('[Vue warn]: Invalid prop'))
})
it('message is OK when called with expected props', () => {
cmp = createCmp({ message: 'hey' })
expect(spy).not.toBeCalled()
}) |
I've found out an easier way: it('is required, is a String and validates correctly', () => {
cmp = createCmp()
const message = cmp.vm.$options.props.message
expect(message.required).toBeTruthy()
expect(message.type).toBe(String)
expect(message.validator && message.validator('a')).toBeFalsy()
expect(message.validator && message.validator('aa')).toBeTruthy()
}) At least here is not necessary to use spies, and it works, independently on how you define the props, either in the shorthand way Anyway, it would be cleaner if
The first 2 (in singular) are tracked in #27, but not What do you think @LinusBorg @wparad? |
The test you posted in your original post is fine. It tests what you want it to test. I don't think we should add a method to help test props validation. |
@eddyerburgh that's true, although I find easier an cleaner to do it as #34 (comment), since there is no need to spy on globals, or assert in side effects like the console. Do you agree on that? An example could be added to docs as per #18 maybe :) A side question I was thinking is, if it would be useful to have a |
@alexjoverm, I do like. As mentioned above, I like that you are testing the configuration of the validator, so you get a thumbs up from me 👍 |
I think there is a case for adding a |
Done ;) |
This worked for us: /*
* Ref: https://jestjs.io/docs/en/expect.html#custom-matchers-api
* this file is required on app/javascript/test/unit/jest.conf.js
*/
const customMatchers = {
toTriggerError(received) {
const spy = spyOn(console, "error")
received()
const pass = !!spy.calls.mostRecent() && spy.calls.mostRecent().args[0].includes("[Vue warn]:")
return {
message() {
return `expected ${received} to trigger error`
},
pass,
}
},
}
expect.extend(customMatchers) |
Any ideas how to do this on a functional component seeing as jest doesn't allow you to access props of a functional? Using Vue CLI 3. |
If you define your components simply as an object: export default {
name: 'Component',
props: {
message: {
type: String,
required: true,
validator: function(value) {
return value == 'Hello'
}
}
}
} Then you save yourself a lot of trouble: test('props validator', () => {
const message = Component.props.message
expect(message.validator).toBeInstanceOf(Function)
expect(message.validator('Hello')).toBeTruthy()
expect(message.validator('Hi')).toBeFalsy()
}) |
Hi thanks but why it need @ts-ignore to work with typescript ?! |
How's it possible to test when a property doesn't match a validation rule? So far, I've managed to do it as so, but it feels a bit hacky (jest in the example):
Does vue-test-utils provide a better way for this?
The text was updated successfully, but these errors were encountered: