-
-
Notifications
You must be signed in to change notification settings - Fork 697
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
Chain .property() assertions on objects #193
Comments
+1 Did you ever find a solution for this? Basically, we're looking for a way to reset the chain to the original subject within expect(...) |
No, I didn’t. should.js is missing this feature too… Am 07.12.2013 um 18:18 schrieb Jeff Jo notifications@github.com:
|
Was thinking about this earlier. Two ways:
Second would be better for backwards compatibility but the first makes more logical sense. /cc @vesln @domenic for additional opinions edit: logical typo |
What do you think about: obj.should.have.property('foo').and.should.have.properyt('bar').which.equals('foobar'); Means intention depends on the used word chain?
|
I find that this would be especially nice when used in conjunction with @domenic's var profile = getProfile();
profile.should.eventually.have.property('id', 1);
profile.should.eventually.have.property('username', 'wbyoung'); But I think this would be a bit nicer chained: getProfile().should.eventually.have.property('id', 1)
.and.have.property('username', 'wbyoung'); In some ways, this could be solved via a I like the outdent idea proposed by @logicalparadox best. Perhaps getProfile().should.eventually.have.property('id', 1)
.and.also.have.property('username', 'wbyoung'); |
I made a small plugin, called |
I quite like the idea of var multiLayerObject = {
foo: {
bar: 1,
baz: 2,
},
bing: {
bong: 3
bash: 4
}
};
// Does it just go up a level?
expect(multiLayerObject).to.have.property('foo')
.and.have.property('bar', 1)
.and.also.have.property('baz', 2)
.and.also.also.have.property('bing') // ???
.and.have.property('bong', 3)
.and.also.have.property('bash', 4);
// Or does it reset to the originally object within expect()?
expect(multiLayerObject).to.have.deep.property('foo.bar', 1)
.and.also.have.deep.property('foo.baz', 2)
.and.also.have.deep.property('bing.bong', 3)
.and.also.have.deep.property('bing.bash', 4); At the risk of sounding cynical - I can see either implementation getting a few issues springing up discussing semantics and trying to alter them to the users use-case. Also worth pointing out that |
@keithamus I agree that it could be confusing. After making this little plugin, I was thinking the same thing — it certainly could read either way. I chose reset to original in my plugin, but feel that having more options could work better. Perhaps var obj = {
foo: {
bar: 'baz'
}
};
expect(obj).to.have.deep.property('foo.bar.baz')
.and.parent.has.property('baz'); // just return to `obj.foo.bar`
expect(obj).to.have.deep.property('foo.bar.baz')
.and.subject.has.property('baz'); // just return to `obj`
expect(obj).to.have.deep.property('foo.bar')
.and.also.have.deep.property('foo.bar.baz'); // return to subject before last change, `obj`
expect(obj).to.have.property('foo')
.and.have.property('bar')
.and.also.have.deep.property('bar.baz') // return to subject before last change, `obj.foo`
.and.subject.has.deep.property('foo.bar.baz'); // just return to `obj` And I don't think it sounded cynical at all, but I also had the same thoughts lingering in the back of my head. ;) |
I was pointed to this issue from my stack-overflow post here, so it seems there's no way to currently do this? |
@reggi as of right now, not really. You can simply create multiple assertions as you suggested in your question on Stack Overflow. I agree with @keithamus that my suggestion of |
I just remembered that we have chai.expect({ foo: 'bar', bar: 'foo', baz: 'bing' }).to.include({ foo: 'bar', bar: 'foo' }); This should be suitable for testing many properties. You can even combine it with var multiLayerObject = {
foo: {
bar: 1,
baz: 2,
},
bing: 3,
bong: 4,
};
chai.expect(multiLayerObject)
.to.include({ bing: 3, bong: 4 })
.and.have.property('foo').include({ bar: 1 }); |
@keithamus awesome. The docs should probably be updated to show that this is possible! |
Hey @wbyoung you're totally right. It looks the docs were missed in the original PR. Luckily it would be simple enough to add in - here is the comment which the docs are generated from - fancy making a PR? |
FYI looks like this has been a feature since 1.9.0! A hidden feature tucked away, I only just realised it existed the other day myself! |
Just curious — is it one of those things that works by happenstance or is it deliberate (i.e. test coverage)? I'll try to get a PR up when I have a few min. I'm excited about this discovery! Thanks for sharing. |
Nevermind… looked at the PR you linked to & see that there are tests. Definitely deliberate. |
@keithamus I just opened #610. |
Originally added in chaijs#230, asserting that an object contains a subset of properties and values was never documented. Questions like chaijs#193 have popped up asking for this feature even though it's been present since 1.9.0. The discussion in chaijs#193 focused mostly around getting something like this to work via the `property` assertion, but that discussion should be considered moot by the existing functionality already present in `include` that was simply overlooked. Resolves: chaijs#193
I searched this feature for a while! Why the official documentation is not up-to-date one year after? |
There's one case in the documentation where it does seem that the context goes back up to the top level, and I can't see an explanation for why this would be:
I am curious if anyone can tell whether this does indeed work as expected or just by coincidence? |
@fineline Good catch. That's my mistake. It should be split into two assertions: expect({a: 1}).to.have.property('b');
expect({a: 1}).to.not.have.own.property('b'); |
@meeber Thanks for clarifying that for me and others. |
Hello,
is there a workaround to allow something like this:
The text was updated successfully, but these errors were encountered: