Skip to content

Commit

Permalink
mounted attr api
Browse files Browse the repository at this point in the history
  • Loading branch information
blainekasten committed Dec 12, 2015
1 parent 04db2ba commit 2132d4e
Show file tree
Hide file tree
Showing 2 changed files with 63 additions and 0 deletions.
28 changes: 28 additions & 0 deletions src/MountedTraversal.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
import {
attributePropMap,
nodeEqual,
isAttributeSelector,
isSimpleSelector,
splitSelector,
selectorError,
Expand Down Expand Up @@ -65,6 +67,27 @@ export function instHasType(inst, type) {
}
}

export function instHasAttribute(inst, compatAttrKey, attrValue) {
if (!isDOMComponent(inst)) return false;

// compatibility for html attributes or react props
const attrKey = attributePropMap[compatAttrKey] || compatAttrKey;

/*
* we could gain from the `getAttribute` `HTMLElement` api, but
* for compatibility between `shallow` and `mount` I think we should
* stick to property look up with a compatiblity check for the
* attr/react prop naming.
*/
const instProps = inst._reactInternalComponent._currentElement.props;

if (attrValue) {
return instProps[attrKey] === attrValue;
}

return instProps.hasOwnProperty(attrKey);
}

// called with private inst
export function renderedChildrenOfInst(inst) {
return REACT013
Expand Down Expand Up @@ -172,6 +195,11 @@ export function buildInstPredicate(selector) {
} else if (selector[0] === '#') {
// selector is an id name
return inst => instHasId(inst, selector.substr(1));
} else if (isAttributeSelector.test(selector)) {
const attrKey = selector.split(/\[([a-zA-Z\-]*?)(=|\])/)[1];
const attrValue = selector.split(/"(.*?)"/)[1]; // can be undefined for queries like `[key]`

return node => instHasAttribute(node, attrKey, attrValue);
}
// selector is a string. match to DOM tag or constructor displayName
return inst => instHasType(inst, selector);
Expand Down
35 changes: 35 additions & 0 deletions src/__tests__/ReactWrapper-spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,41 @@ describeWithDOM('mount', () => {
expect(wrapper.find(Foo).type()).to.equal(Foo);
});

it('should find component based on an attribute', () => {
const wrapper = mount(
<div>
<span title="foo" />
</div>
);

expect(wrapper.find('[title="foo"]')).to.have.length(1);
expect(wrapper.find('span[title="foo"]')).to.have.length(1);
expect(wrapper.find('[title]')).to.have.length(1);
expect(wrapper.find('span[title]')).to.have.length(1);
});

it('should find components with html attributes or props', () => {
const wrapper = mount(
<div>
<span htmlFor="foo" />
</div>
);

expect(wrapper.find('[htmlFor="foo"]')).to.have.length(1);
expect(wrapper.find('[for="foo"]')).to.have.length(1);
});

it('should find components with multiple matching attributes', () => {
const wrapper = mount(
<div>
<span htmlFor="foo" label="bar" />
</div>
);

expect(wrapper.find('span[for="foo"][label="bar"]')).to.have.length(1);
expect(wrapper.find('span[label="bar"][baz]')).to.have.length(0);
});

it('should find multiple elements based on a class name', () => {
const wrapper = mount(
<div>
Expand Down

0 comments on commit 2132d4e

Please sign in to comment.