2

I believe what I am trying to achieve has been done many times, but I can't manage it.

I would just like to be able to test if an element has a certain class on a certain element.

Splash

import React from 'react';
import { NavLink } from 'react-router-dom'
import Logo from '../shared/logo/index';
import * as styles from './style.css';

class Splash extends React.Component {
  render(){
    return (
      <div className={styles.indexAppContent}>
        <NavLink to="/home"  className={styles.index}>
          <Logo />
        </NavLink>
      </div>
    );
  }
}

export default Splash;

style.css

.index {
  div {
    color: #FFF;
    //font-size: 8rem;
  }
  position: absolute;
  left: 50%;
  top: 50%;
  display: block;
  transform: translate3d(-50%, -50%, 0);
  -webkit-transform: translate3d(-50%, -50%,0);
  -moz-transform: translate3d(-50%, -50%,0);
  -ms-transform: translate3d(-50%, -50%,0);
}

.indexAppContent {
  height: 100vh;
  width: 100vw;
  position: relative;
}

However this is the output:

{ className: undefined,
  children: 
   { '$$typeof': Symbol(react.element),
     type: { [Function: NavLink] propTypes: [Object], defaultProps: [Object] },
     key: null,
     ref: null,
     props: 
      { to: '/home',
        className: undefined,
        children: [Object],
        activeClassName: 'active',
        ariaCurrent: 'true' },
     _owner: null,
     _store: {} } }

Splash

/* eslint-disable object-property-newline */
import React from 'react';
import ReactTestUtils from 'react-dom/test-utils'
import { expect } from 'chai';
import { NavLink } from 'react-router-dom'
import { shallow } from 'enzyme';

//Splash
import Splash from '../../../src/components/Splash';
import * as styles from '../../../src/components/Splash/style.css';

//logo
import Logo from '../../../src/components/shared/logo';


describe('<Splash />', () => {

  const wrapperSplash = shallow(<Splash/>);
  const wrapperNavLink = shallow(<NavLink />);
  const wrapperLogo = shallow(<Logo />);

  it('must be defined', () => {
    expect(wrapperSplash).to.be.defined;
  });

  it('should have one logo', () => {
    expect(wrapperSplash.find(Logo)).to.have.length(1);
  })

  it('should have className', () => {
    expect(wrapperSplash.first().prop('className'))
      .to.contain('indexAppContent');
  })

  it('Logo links to Home', () => {
    expect(wrapperSplash.find(NavLink).first().props().to)
      .equals('/Home');
  })

});

Test

/* eslint-disable object-property-newline */
import React from 'react';
import ReactTestUtils from 'react-dom/test-utils'
import { expect } from 'chai';
import { NavLink } from 'react-router-dom'
import { shallow } from 'enzyme';

  it('should have className', () => {
    console.info(wrapperSplash.first().props());
    expect(wrapperSplash.first().prop('className'))
      .to.contain('indexAppContent');
  })

Test Helper

import path from 'path';
import csshook from 'css-modules-require-hook/preset' // import hook before routes
import routes from '/shared/views/routes'
import requireHacker from 'require-hacker';
import sass from 'node-sass';
import {jsdom} from 'jsdom';
import injectTapEventPlugin from 'react-tap-event-plugin';

injectTapEventPlugin();

hook({
  extensions: ['.css'],
  generateScopedName: '[local]',
  preprocessCss: (data, filename) =>
    sass.renderSync({
      data,
      file: filename,
      importer: (url) => {
        if (url.indexOf('~') === 0) {
          const node_modules_path = path.resolve(__dirname, '../..', 'node_modules');

          return {
            file: path.join(node_modules_path, url.replace('~', ''))
          };
        }

        return {file: url};
      }
    }).css
});

const fakeComponentString = `
  module.exports = require('react').createClass({
    render() {
      return null;
    }
  });
`;

requireHacker.hook('svg', () => fakeComponentString);

// jsdom
const exposedProperties = ['window', 'navigator', 'document'];


global.document = jsdom('');
global.window = document.defaultView;
Object.keys(document.defaultView).forEach((property) => {
  if (typeof global[property] === 'undefined') {
    global[property] = document.defaultView[property];
  }
});

global.navigator = {
  userAgent: 'node.js'
};
6
  • 1
    And wrapperSplash would be....? Commented Sep 4, 2017 at 17:39
  • Sorry guys, was just trying to make it smaller. I've updated it now Commented Sep 4, 2017 at 19:49
  • and where are you providing the className prop here? const wrapperSplash = shallow(<Splash/>); shouldnt it be const wrapperSplash = shallow(<Splash className="something"/>);? Commented Sep 4, 2017 at 20:42
  • lol updated again, I actually thought I had put that in Commented Sep 4, 2017 at 20:47
  • @Sag1v the prop should be coming from the component added to the test with import Splash from '../../../src/components/Splash'; which is the component itselfs Commented Sep 4, 2017 at 20:49

1 Answer 1

1

You are checking a prop of that component and not the existence of a class in the root node that was rendered by this component.
Obviously you are not passing this prop.
You set the class on the root element of this component, thus you should check for nested element that hold this class value in the dom and not the attribute (prop) className You can do it with this syntax for example:

 it('should have class of indexAppContent', () => {
    expect(wrapperSplash.find('.indexAppContent')).to.have.length(1);
  })
Sign up to request clarification or add additional context in comments.

3 Comments

I see what you mean, the problem is that with css modules, the class is never output as what the style is. So the rendered class will never actually be .indexAppContent. I think this is really what is going on
would it be index-appContent? (cammelCase attribute in css modules)
It renders to src-components-Splash-___style__indexAppContent___2gYy0 So pretty random, I believe it takes the days dateTime as well

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.