Jest: ๋Š๋ฆฐ ๋ฐ˜์‘ ํ…Œ์ŠคํŠธ

์— ๋งŒ๋“  2014๋…„ 08์›” 08์ผ  ยท  80์ฝ”๋ฉ˜ํŠธ  ยท  ์ถœ์ฒ˜: facebook/jest

React์™€ Jest์— ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค. ์ฝค๋ณด๋ฅผ ์‚ฌ๋ž‘ํ•ฉ๋‹ˆ๋‹ค. ์–ด์จŒ๋“  ์ €๋Š” _livereload_ ๋ชจ๋“œ์—์„œ ํ…Œ์ŠคํŠธ๋ฅผ ์‹คํ–‰ํ•˜๋Š” ๋ฐ ์ต์ˆ™ํ•ฉ๋‹ˆ๋‹ค. ๋”ฐ๋ผ์„œ ํ…Œ์ŠคํŠธ ํŒŒ์ผ์ด ์ €์žฅ๋  ๋•Œ๋งˆ๋‹ค ํ…Œ์ŠคํŠธ๊ฐ€ ์ž๋™์œผ๋กœ ์‹คํ–‰๋ฉ๋‹ˆ๋‹ค. ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ์ž‘๋™ํ•˜์ง€๋งŒ ํ…Œ์ŠคํŠธ๋ฅผ ์‹คํ–‰ํ•˜๋Š” ๋ฐ ๊ฑฐ์˜ 3์ดˆ๊ฐ€ ๊ฑธ๋ฆฝ๋‹ˆ๋‹ค. ํ•˜๋‚˜์˜ ํ…Œ์ŠคํŠธ ํŒŒ์ผ๋งŒ ์žˆ์œผ๋ฉด ๋ฉ๋‹ˆ๋‹ค. ์ „์ฒ˜๋ฆฌ๊ธฐ๋ฅผ ํ†ตํ•ด ํŒŒ์ผ์„ ์‹คํ–‰ํ•˜๊ณ  ์žˆ์œผ๋ฏ€๋กœ ๋ฌธ์ œ๊ฐ€ ์žˆ๋Š” ๊ณณ์œผ๋กœ ์˜์‹ฌ๋ฉ๋‹ˆ๋‹ค. ํ…Œ์ŠคํŠธ๋ฅผ ๋น ๋ฅด๊ฒŒ ์‹คํ–‰ํ•˜๋Š” ๋ฐฉ๋ฒ•์— ๋Œ€ํ•œ ์ œ์•ˆ์ด๋‚˜ TDD/BDD ์›Œํฌํ”Œ๋กœ์˜ ์†๋„๋ฅผ ๋†’์ด๋Š” ๋ฐฉ๋ฒ•์— ๋Œ€ํ•œ ์กฐ์–ธ์ด ์žˆ์Šต๋‹ˆ๊นŒ?

Enhancement

๊ฐ€์žฅ ์œ ์šฉํ•œ ๋Œ“๊ธ€

๋‚ด ํ…Œ์ŠคํŠธ๋Š” ์ง€๊ธˆ๊นŒ์ง€ ๊ถŒ์žฅ๋œ ๋ชจ๋“  ์ตœ์ ํ™”๋ฅผ ์‚ฌ์šฉํ•œ ํ›„์—๋„ 14์ดˆ์ž…๋‹ˆ๋‹ค. 16GB RAM๊ณผ SSD๋ฅผ ์‚ฌ์šฉํ•˜๋”๋ผ๋„. Jest๋Š” ํ˜„์žฌ ์ƒํƒœ์—์„œ ์™„์ „ํžˆ ์‚ฌ์šฉํ•  ์ˆ˜ ์—†์Šต๋‹ˆ๋‹ค. ์ฃ„์†กํ•ฉ๋‹ˆ๋‹ค. Karma๋กœ ์ „ํ™˜ํ•ฉ๋‹ˆ๋‹ค.

๋ชจ๋“  80 ๋Œ“๊ธ€

์•ˆ๋…• ํƒ€์ด๋ก . ํ•œ ํŒŒ์ผ์— ๋Œ€ํ•ด 20์ดˆ ์ด์ƒ ๋™์•ˆ ์ด ๋ฌธ์ œ๊ฐ€ ๋ฐœ์ƒํ–ˆ์Šต๋‹ˆ๋‹ค. :)
๋ฌธ์ œ๋Š” ๋ฃจํŠธ ๋””๋ ‰ํ† ๋ฆฌ์—์„œ 'jest'๋ฅผ ์‹คํ–‰ํ•˜๋„๋ก ๊ตฌ์„ฑํ–ˆ๋‹ค๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๊ทธ๋ฆฌ๊ณ  Jest๊ฐ€ ํ…Œ์ŠคํŠธ๋ฅผ ์œ„ํ•ด ํ™•์ธํ–ˆ๋˜ ๋งŽ์€ ํ•˜์œ„ ๋””๋ ‰ํ† ๋ฆฌ๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค. ํ…Œ์ŠคํŠธ ๊ฒฝ๋กœ ์ง€์ •์ด ์ด๋ฒˆ์— 10๋ฐฐ ์ด์ƒ ์ค„์—ˆ์Šต๋‹ˆ๋‹ค. ๊ทธ๋ฆฌ๊ณ  ์ปคํ”ผ ์ „์ฒ˜๋ฆฌ๊ธฐ๋„ ์žˆ์Šต๋‹ˆ๋‹ค. package.json์—์„œ
"์Šคํฌ๋ฆฝํŠธ": {
....
"test": "jest ๊ฒฝ๋กœ/to/modules/to/test"
}

BTW, ์ปคํ”ผ๋ฅผ ์ „์ฒ˜๋ฆฌํ•˜๊ฑฐ๋‚˜ ๋ฌด์—‡์ž…๋‹ˆ๊นŒ? :)

@gothy๋ฅผ ๋‹ค์‹œ ์ฐพ์•„์ฃผ์…”์„œ ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค. JSX์™€ ํ•จ๊ป˜ ์ผ๋ฐ˜ JS๋ฅผ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ์˜ˆ์ œ(https://github.com/facebook/jest/tree/master/examples/react)์™€ ๊ฐ™์€ JSX ์ „์ฒ˜๋ฆฌ๊ธฐ๋ฅผ ํ†ตํ•ด ํ…Œ์ŠคํŠธ๋ฅผ ์‹คํ–‰ํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ์˜ˆ์ œ๋ฅผ ์‹คํ–‰ํ•˜๋Š” ๋ฐ๋„ ์•ฝ 2.5 - 3์ดˆ๊ฐ€ ๊ฑธ๋ฆฝ๋‹ˆ๋‹ค. jQuery ์˜ˆ์ œ๋Š” 1์ดˆ๋„ ์ฑ„ ๊ฑธ๋ฆฌ์ง€ ์•Š์Šต๋‹ˆ๋‹ค. JSX ์ „์ฒ˜๋ฆฌ๊ธฐ๋Š” JSX ํŒŒ์ผ์„ ์ฒ˜๋ฆฌํ•  ๋•Œ ๋„ˆ๋ฌด ๋งŽ์€ ์‹œ๊ฐ„์ด ๊ฑธ๋ฆฌ๋„๋ก ๋˜์–ด ์žˆ์Šต๋‹ˆ๊นŒ?

๋ฐ˜์‘ ํ…Œ์ŠคํŠธ

screen shot 2014-08-08 at 1 46 05 pm

jQuery ํ…Œ์ŠคํŠธ

screen shot 2014-08-08 at 1 54 55 pm

์•„, JSX์—๋Š” ์‚ฌ์šฉํ•˜์ง€ ์•Š์•˜์Šต๋‹ˆ๋‹ค. ์ด ํ”„๋กœ์„ธ์„œ์— ๋Œ€ํ•ด ์•„๋ฌด ๋ง๋„ ํ•  ์ˆ˜ ์—†์Šต๋‹ˆ๋‹ค. ์–ด์ฉŒ๋ฉด ์‹ค์ œ๋กœ ๋Š๋ฆด ์ˆ˜๋„ ์žˆ์Šต๋‹ˆ๋‹ค. ์˜ค๋ž˜๋œ ๋ฌผ๊ฑด์ด ๋งŽ์€ ์‹ค์ œ ํ”„๋กœ์ ํŠธ์˜ ๋””๋ ‰ํ† ๋ฆฌ ๋ฌธ์ œ๋ฅผ ๋ฐœ๊ฒฌํ–ˆ์Šต๋‹ˆ๋‹ค. :)

Coffeescript ์ „์ฒ˜๋ฆฌ๊ธฐ์™€ ๋น„์Šทํ•œ ๋ฌธ์ œ๋ฅผ ๊ฒฝํ—˜ํ–ˆ์Šต๋‹ˆ๋‹ค. ์—ฌ๊ธฐ์„œ ๋ฌธ์ œ๋Š” ์ „์ฒ˜๋ฆฌ๊ธฐ๊ฐ€ ์ข…์†์„ฑ๋„ ์ฒ˜๋ฆฌํ•˜๋ ค๊ณ  ํ•œ๋‹ค๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๋งŽ์€ ๊ฒƒ์„ ์š”๊ตฌํ•˜๋ฉด ์†๋„๊ฐ€ ๋Š๋ ค์ง‘๋‹ˆ๋‹ค.

๋‚˜๋Š” ๋˜ํ•œ jest๋กœ ๋Š๋ฆฐ ํ…Œ์ŠคํŠธ๋ฅผ ๊ฒฝํ—˜ํ•ฉ๋‹ˆ๋‹ค :(

๊ฐ™์€ ์ผ์„ ๊ฒช๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ๋‚˜๋Š” ๊ทธ๊ฒƒ์ด ์ „์ฒ˜๋ฆฌ์™€ ๊ด€๋ จ์ด ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค(์ด ์ž‘์€ ํŒŒ์ผ์— ๋Œ€ํ•œ JSX ์ฒ˜๋ฆฌ๋Š” ๋น ๋ฆ„). ๋‹ค์Œ require ๋ฌธ ์ค‘ ํ•˜๋‚˜๋ฅผ ์ œ์™ธํ•˜๊ณ  ์˜ˆ์ œ ํ…Œ์ŠคํŠธ์˜ ๋ชจ๋“  ์ฝ”๋“œ๋ฅผ ์ฃผ์„ ์ฒ˜๋ฆฌํ–ˆ๋Š”๋ฐ ํ…Œ์ŠคํŠธ๋Š” ์—ฌ์ „ํžˆ 4์ดˆ๊ฐ€ ๊ฑธ๋ฆฝ๋‹ˆ๋‹ค. ๋‚ด๊ฐ€ ์ฃผ์„์„ ์ œ๊ฑฐํ•˜์ž๋งˆ์ž ํ…Œ์ŠคํŠธ๋Š” 0.1์ดˆ๊ฐ€ ๊ฑธ๋ฆฝ๋‹ˆ๋‹ค. ์กฐ๊ธˆ ํŒŒํ—ค์ณ๋ณด๋‹ˆ HasteModuleLoader๊ฐ€ 490๊ฐœ์˜ ํ•„์ˆ˜ ํŒจํ‚ค์ง€(_shouldMock())๋ฅผ ์ฒ˜๋ฆฌํ•ด์•ผ ํ•˜๊ณ  ๋ฐ˜์‘/์• ๋“œ์˜จ์ด ํ•„์š”ํ•  ๋•Œ ๋ชจ์˜ํ•˜์ง€ ์•Š์•„์•ผ ํ•˜๋Š” ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค.

var React = require('react/addons');

๋˜๋Š”

var CheckboxWithLabel = require('../CheckboxWithLabel.js');

๋‹ค์Œ var React = require('react/addons'); ์„ ์ œ๊ฑฐํ–ˆ์ง€๋งŒ ์—ฌ์ „ํžˆ ์ „์ฒ˜๋ฆฌ๊ธฐ๋ฅผ ํ†ตํ•ด ํŒŒ์ผ์„ ์‹คํ–‰ํ–ˆ์Šต๋‹ˆ๋‹ค. ๋‚˜๋Š” ์•„๋งˆ 0.2์ดˆ ๊ฐœ์„ ์„ ์–ป์—ˆ๋‹ค. ์ „์ฒ˜๋ฆฌ๊ธฐ๋ฅผ ์ œ๊ฑฐํ•˜๋ฉด ๋‹ค์Œ๊ณผ ๊ฐ™์€ ๊ฒฐ๊ณผ๊ฐ€ ๋‚˜ํƒ€๋‚ฉ๋‹ˆ๋‹ค.

JSX ์ „์ฒ˜๋ฆฌ๊ธฐ ์‚ฌ์šฉ
screen shot 2014-08-10 at 5 35 22 pm

JSX ์ „์ฒ˜๋ฆฌ๊ธฐ ์—†์ด
screen shot 2014-08-10 at 5 34 12 pm

์ €๋Š” Jasmine๋ณด๋‹ค Mocha๋ฅผ ์„ ํ˜ธํ•˜๊ณ  ๋ฐ˜์‘ ๊ตฌ์„ฑ ์š”์†Œ๋ฅผ ๋นŒ๋“œํ•œ ๋‹ค์Œ mocha ํ…Œ์ŠคํŠธ ์ œํ’ˆ๊ตฐ(์•„๋ž˜ ์Šค๋‹ˆํŽซ)์„ ํ†ตํ•ด ์‹คํ–‰ํ•  gulpfile์„ ์„ค์ •ํ•˜๊ธฐ๋กœ ๊ฒฐ์ •ํ–ˆ์Šต๋‹ˆ๋‹ค.

function buildScript(file, watch) {
  var bundler = browserify(file);
  var stream;
  bundler.transform(reactify);
  stream = bundler.bundle();
  return stream.on('error', handleErrors)
  .pipe(source(file))
  .pipe(gulp.dest(buildDir + '/'))
  .pipe(mocha({ reporter: 'list' }));
}

์—ฌ์ „ํžˆ reactify๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ JSX ํŒŒ์ผ์„ ์‚ฌ์ „ ์ฒ˜๋ฆฌํ•ด์•ผ ํ•˜์ง€๋งŒ ๋Š๋ฆฐ ํ…Œ์ŠคํŠธ์— ๋Œ€ํ•œ ๊ฒฝ๊ณ  ๋ฉ”์‹œ์ง€๋ฅผ ์ œ๊ฑฐํ•ฉ๋‹ˆ๋‹ค. ๋”ฐ๋ผ์„œ ๋Ÿฐํƒ€์ž„์€ ์—ฌ์ „ํžˆ โ€‹โ€‹2์ดˆ ๋ฏธ๋งŒ์ด ๊ฑธ๋ฆฌ์ง€๋งŒ ์‹ค์ œ ํ…Œ์ŠคํŠธ๋Š” ์•ฝ 32ms์ž…๋‹ˆ๋‹ค. ์—ฌ์ „ํžˆ JSX๋ฅผ ์‚ฌ์šฉํ•  ๊ฐ€์น˜๊ฐ€ ์žˆ๋Š”์ง€ ๊ฒฐ์ •ํ•ฉ๋‹ˆ๋‹ค.

์˜ค, ๋‹น์‹  ๋ง์ด ๋งž์•„. JSX๋ฅผ ์‚ฌ์šฉํ•˜์ง€ ์•Š๋Š” jest ๋ฐ˜์‘ ์˜ˆ์ œ๋ฅผ ํ…Œ์ŠคํŠธํ–ˆ๋Š”๋ฐ 4์ดˆ์— ๊ฐ€๊นŒ์› ๋Š”๋ฐ 0.75์ดˆ๋กœ ์ค„์—ˆ์Šต๋‹ˆ๋‹ค. JSX๋ฅผ ์‚ฌ์šฉํ•  ๊ฐ€์น˜๊ฐ€ ์žˆ๋Š”์ง€ ์ •๋ง ์ƒ๊ฐํ•˜๊ฒŒ ๋งŒ๋“ญ๋‹ˆ๋‹ค. ํฐ ํ”„๋กœ์ ํŠธ์—์„œ๋Š” ๋‹ค๋ฅธ ํŒจํ‚ค์ง€๊ฐ€ ๋งŽ์ง€ ์•Š์€ ํ•œ ๊ฝค ๋นจ๋ฆฌ ๋Š๋ ค์งˆ ๊ฒƒ์ž…๋‹ˆ๋‹ค. ์ „์ฒ˜๋ฆฌ๊ธฐ๊ฐ€ ํ•ด๋‹น ๋‹จ์ผ ํŒŒ์ผ์ด ์•„๋‹ˆ๋ผ ๋ชจ๋“  490๊ฐœ ์š”๊ตฌ์‚ฌํ•ญ์—์„œ ์‹คํ–‰๋˜๋Š”์ง€ ๊ถ๊ธˆํ•ฉ๋‹ˆ๋‹ค. ๊ทธ ๊ฐ„๋‹จํ•œ ๊ตฌ์„ฑ ์š”์†Œ์— ๋Œ€ํ•ด 3์ดˆ๊ฐ€ ๊ฑธ๋ฆฌ๋ฉด ์•ˆ ๋ฉ๋‹ˆ๋‹ค.

์–ด๋Š ์ชฝ์ด๋“ , ๋‚ด ์›Œํฌํ”Œ๋กœ๋ฅผ ์œ„ํ•ด ํ…Œ์ŠคํŠธ๋ฅผ ๋น ๋ฅด๊ฒŒ ์ˆ˜ํ–‰ํ•ด์•ผ ํ•ฉ๋‹ˆ๋‹ค. ์ ์–ด๋„ ํ•˜๋‚˜์˜ ์ œํ’ˆ๊ตฐ์„ ์‹คํ–‰ํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ์•Œ์•„๋‚ด์•ผ ํ•ฉ๋‹ˆ๋‹ค. ์žฌ์Šค๋ฏผ์—์„œ๋Š” "describe" ๋ฐ "it" ๋Œ€์‹  "ddescribe" ๋˜๋Š” "iit"๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋‹จ์ผ ํ…Œ์ŠคํŠธ ๋˜๋Š” ์ œํ’ˆ๊ตฐ์„ ์‹คํ–‰ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. Jest๋Š” ์ •๋ง ํ›Œ๋ฅญํ•ฉ๋‹ˆ๋‹ค. ์ด์ œ ๋น ๋ฅธ ์›Œํฌํ”Œ๋กœ๊ฐ€ ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.

var React = require('react');

var CheckboxWithLabel = React.createClass({displayName: 'CheckboxWithLabel',
    getInitialState: function() {
        return { isChecked: false };
    },
    onChange: function() {
        this.setState({isChecked: !this.state.isChecked});
    },
    render: function() {
        return (
            React.DOM.label(null,
                React.DOM.input(
                    {type:"checkbox",
                        checked:this.state.isChecked,
                        onChange:this.onChange}
                ),
                this.state.isChecked ? this.props.labelOn : this.props.labelOff
            )
            );
    }
});

module.exports = CheckboxWithLabel; 

@jeffchan ์ด ์˜ณ์•˜์Šต๋‹ˆ๋‹ค. ํ•„์š”ํ•œ ๋ชจ๋“  ์ฝ”๋“œ๋Š” JSX ํŒŒ์ผ๋ฟ๋งŒ ์•„๋‹ˆ๋ผ ์ „์ฒ˜๋ฆฌ๊ธฐ๋ฅผ ํ†ตํ•ด ์‹คํ–‰๋ฉ๋‹ˆ๋‹ค.

๊ฐ€์žฅ ๋น ๋ฅธ ์†”๋ฃจ์…˜์€ ์ž‘์—…ํ•˜๋Š” ๋™์•ˆ ๋ณ€๊ฒฝ๋œ JSX ํŒŒ์ผ๋งŒ ์ฒ˜๋ฆฌํ•˜๊ธฐ ์œ„ํ•ด ๊ฟ€๊บฝ ๊ฟ€๊บฝ ๋งˆ์‹œ๊ณ  ๊ฐ์‹œํ•˜๊ณ  ๋ฐ˜์‘ํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๊ทธ๋Ÿฌ๋ฉด ์‹คํ–‰ํ•˜๋ ค๋Š” ํ…Œ์ŠคํŠธ๋งŒ ์ง€์ •ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์ด๋ ‡๊ฒŒ ํ•˜๋ฉด JSX ํŒŒ์ผ์ด ํ•œ ๋ฒˆ๋งŒ ์ฒ˜๋ฆฌ๋˜๊ณ  ๋‚ด๊ฐ€ ์–ด๋–ค ํ…Œ์ŠคํŠธ๋ฅผ ์‹คํ–‰ํ• ์ง€ ์ œ์–ดํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์ด์™€ ๊ฐ™์€ ๊ฒƒ์€ ํ…Œ์ŠคํŠธ ์›Œํฌํ”Œ๋กœ์— ์ •๋ง ์ข‹์„ ๊ฒƒ์ž…๋‹ˆ๋‹ค.

gulp jest --tests "Checkbox*,*Form*"

๊ทธ๋Ÿฐ ๋‹ค์Œ Watchify๋Š” ์ด๋Ÿฌํ•œ ํ…Œ์ŠคํŠธ๊ฐ€ ์˜์กดํ•˜๋Š” ๋ณ€๊ฒฝ ์‚ฌํ•ญ์„ ๊ฐ์‹œํ•œ ๋‹ค์Œ ๋ณ€๊ฒฝ ์‚ฌํ•ญ๋งŒ ์ฒ˜๋ฆฌํ•œ ๋‹ค์Œ ์ž‘์—… ์ค‘์ธ ํ…Œ์ŠคํŠธ๋งŒ ์‹คํ–‰ํ•ฉ๋‹ˆ๋‹ค.

@iamrandys 100% ๋™์˜ํ•ฉ๋‹ˆ๋‹ค. Jest์™€ React๋Š” ํ›Œ๋ฅญํ•˜์ง€๋งŒ JSX๋ฅผ JS๋กœ ์ปดํŒŒ์ผํ•˜๋Š” ๊ฒƒ์€ ํฐ ์žฅ์• ๋ฌผ์ž…๋‹ˆ๋‹ค. Gulp๊ฐ€ JSX ์ „์ฒ˜๋ฆฌ๊ธฐ๋ฅผ ํ†ตํ•ด ์‹คํ–‰๋˜๋Š” ํ•„์ˆ˜ ํŒŒ์ผ(๋น„ JSX) ๋ฌธ์ œ๋ฅผ ์–ด๋–ป๊ฒŒ ํ•ด๊ฒฐํ• ์ง€ ๊ถ๊ธˆํ•˜์‹ญ๋‹ˆ๊นŒ? ๋‹ค์Œ๊ณผ ๊ฐ™์€ ๊ฒƒ์„ ์ œ์•ˆํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๊นŒ? - http://blog.avisi.nl/2014/04/25/how-to-keep-a-fast-build-with-browserify-and-reactjs/ ?

์˜ˆ, gulp ํ”Œ๋Ÿฌ๊ทธ์ธ์ด ์žˆ๋Š” ์ผ์ข…์˜ ์บ์‹ฑ ๋ ˆ์ด์–ด์— ๋Œ€ํ•ด ์ƒ๊ฐํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค.
์ž‘์—…

2014๋…„ 8์›” 11์ผ 08:35 Tyrone Avnit [email protected] ์€ ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ผ์Šต๋‹ˆ๋‹ค.

@iamrandys https://github.com/iamrandys 100% ๋™์˜ํ•ฉ๋‹ˆ๋‹ค. ๋†๋‹ด๊ณผ
React๋Š” ํ›Œ๋ฅญํ•˜์ง€๋งŒ JSX๋ฅผ JS๋กœ ์ปดํŒŒ์ผํ•˜๋Š” ๊ฒƒ์€ ํฐ ์žฅ์• ๋ฌผ์ž…๋‹ˆ๋‹ค. ๋‹จ์ง€
Gulp๊ฐ€ ํ•„์š”ํ•œ ํŒŒ์ผ(๋น„
JSX)๊ฐ€ JSX ์ „์ฒ˜๋ฆฌ๊ธฐ๋ฅผ ํ†ตํ•ด ์‹คํ–‰๋˜๊ณ  ์žˆ์Šต๋‹ˆ๊นŒ? ๋‹น์‹ ์€ ๋ญ”๊ฐ€๋ฅผ ์ œ์•ˆํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๊นŒ
๋‹ค์Œ๊ณผ ๊ฐ™์ด? -
http://blog.avisi.nl/2014/04/25/how-to-keep-a-fast-build-with-browserify-and-reactjs/
?

โ€”
์ด ์ด๋ฉ”์ผ์— ์ง์ ‘ ๋‹ต์žฅํ•˜๊ฑฐ๋‚˜ GitHub์—์„œ ํ™•์ธํ•˜์„ธ์š”.
https://github.com/facebook/jest/issues/116#issuecomment -51749798.

์ •ํ™•ํžˆ๋Š” gulp์™€ watchify๋ฅผ ์‚ฌ์šฉํ•˜๋ฉด ๋ฐ˜์‘ ์†๋„๊ฐ€ ๋†€๋ผ์šธ ์ •๋„๋กœ ๋น ๋ฆ…๋‹ˆ๋‹ค. ๋˜์ ธ
gulp-livereload๋Š” ๊ฐ ๋ณ€๊ฒฝ ํ›„ ๋ธŒ๋ผ์šฐ์ €๋ฅผ ์ƒˆ๋กœ ๊ณ ์น˜๊ณ 
๋†€๋ผ์šด ๊ฐœ๋ฐœ ํ™˜๊ฒฝ. ๋ณ€๊ฒฝํ•˜๊ณ  ์ €์žฅํ•˜๋ฉด ๊ฑฐ์˜
์—ด๋ ค ์žˆ๋Š” ๋ชจ๋“  ๋ธŒ๋ผ์šฐ์ €์™€ ๋ชจ๋“  ์žฅ์น˜์—์„œ ๋ณ€๊ฒฝ ์‚ฌํ•ญ์„ ์ฆ‰์‹œ ํ™•์ธํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์ง€๊ธˆ
๋‚ด TDD์— ๋Œ€ํ•ด ๋™์ผํ•œ ๊ฒƒ์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.

๋Œ€๋žต ์ด๋ ‡์ง€๋งŒ hbsfy ๋Œ€์‹  reactify๋ฅผ ์‚ฌ์šฉํ•˜์‹ญ์‹œ์˜ค.
https://gist.github.com/benhowdle89/9533185

2014๋…„ 8์›” 11์ผ ์›”์š”์ผ ์˜ค์ „ 2:35 Tyrone Avnit [email protected]
์ผ๋‹ค:

@iamrandys https://github.com/iamrandys 100% ๋™์˜ํ•ฉ๋‹ˆ๋‹ค. ๋†๋‹ด๊ณผ
React๋Š” ํ›Œ๋ฅญํ•˜์ง€๋งŒ JSX๋ฅผ JS๋กœ ์ปดํŒŒ์ผํ•˜๋Š” ๊ฒƒ์€ ํฐ ์žฅ์• ๋ฌผ์ž…๋‹ˆ๋‹ค. ๋‹จ์ง€
Gulp๊ฐ€ ํ•„์š”ํ•œ ํŒŒ์ผ(๋น„
JSX)๊ฐ€ JSX ์ „์ฒ˜๋ฆฌ๊ธฐ๋ฅผ ํ†ตํ•ด ์‹คํ–‰๋˜๊ณ  ์žˆ์Šต๋‹ˆ๊นŒ? ๋‹น์‹ ์€ ๋ญ”๊ฐ€๋ฅผ ์ œ์•ˆํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๊นŒ
๋‹ค์Œ๊ณผ ๊ฐ™์ด? -
http://blog.avisi.nl/2014/04/25/how-to-keep-a-fast-build-with-browserify-and-reactjs/
?

โ€”
์ด ์ด๋ฉ”์ผ์— ์ง์ ‘ ๋‹ต์žฅํ•˜๊ฑฐ๋‚˜ GitHub์—์„œ ํ™•์ธํ•˜์„ธ์š”.
https://github.com/facebook/jest/issues/116#issuecomment -51749798.

@iamrandys๋‹˜ ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค. Mocha์™€ Chai๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๋น ๋ฅธ ๋ฐ˜์‘ ์„ฑ๋ถ„ ๋ณด์ผ๋Ÿฌ ํ”Œ๋ ˆ์ดํŠธ ๊ฐœ๋ฐœ(์ž์Šค๋ฏผ์œผ๋กœ ์‰ฝ๊ฒŒ ๋Œ€์ฒด ๊ฐ€๋Šฅ). ํ…Œ์ŠคํŠธ๋Š” ๋งค์šฐ ๋น ๋ฅด๋ฉฐ Livereload์˜ ์ถ”๊ฐ€ ์ด์ ์„ ์–ป์„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์›ํ•˜๋Š” ๋Œ€๋กœ ์‚ฌ์šฉํ•˜์‹ญ์‹œ์˜ค.

์–ด๋Š ์ชฝ์ด๋“ , ๋‚ด ์›Œํฌํ”Œ๋กœ๋ฅผ ์œ„ํ•ด ํ…Œ์ŠคํŠธ๋ฅผ ๋น ๋ฅด๊ฒŒ ์ˆ˜ํ–‰ํ•ด์•ผ ํ•ฉ๋‹ˆ๋‹ค. ์ ์–ด๋„ ํ•˜๋‚˜์˜ ์ œํ’ˆ๊ตฐ์„ ์‹คํ–‰ํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ์•Œ์•„๋‚ด์•ผ ํ•ฉ๋‹ˆ๋‹ค. ์žฌ์Šค๋ฏผ์—์„œ๋Š” "describe" ๋ฐ "it" ๋Œ€์‹  "ddescribe" ๋˜๋Š” "iit"๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋‹จ์ผ ํ…Œ์ŠคํŠธ ๋˜๋Š” ์ œํ’ˆ๊ตฐ์„ ์‹คํ–‰ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. Jest๋Š” ์ •๋ง ํ›Œ๋ฅญํ•ฉ๋‹ˆ๋‹ค. ์ด์ œ ๋น ๋ฅธ ์›Œํฌํ”Œ๋กœ๊ฐ€ ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.

ํ™•์‹คํžˆ it.only ๋ฅผ ์“ธ ์ˆ˜ ์žˆ๊ณ  describe.only ๋„ ํ•  ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค.

Karma๋Š” ๋‹น์‹ ์ด ์›ํ•˜๋Š” ๊ฒƒ์„ ์ •ํ™•ํžˆ ํ•˜๊ณ  ๋‹น์‹ ์ด ํ•ด์•ผ ํ•  ์ผ์€ ์ถ”๊ฐ€ํ•˜๊ธฐ๋งŒ ํ•˜๋ฉด ๋ฉ๋‹ˆ๋‹ค.
karma.conf ํŒŒ์ผ์„ ํ”„๋กœ์ ํŠธ์— ์ถ”๊ฐ€ํ•ฉ๋‹ˆ๋‹ค. ๋‚˜๋Š” ์นด๋ฅด๋งˆ๊ฐ€ ๋ฐ˜์‘์„ ์ง€์›ํ•œ๋‹ค๋Š” ๊ฒƒ์„ ๊นจ๋‹ซ์ง€ ๋ชปํ–ˆ์Šต๋‹ˆ๋‹ค.
๊ทธ๋ฆฌ๊ณ  ๋ธŒ๋ผ์šฐ์ €ํ™”ํ•ฉ๋‹ˆ๋‹ค. ์ด์ œ ๋ชจ๋“  ๋ธŒ๋ผ์šฐ์ €์—์„œ ๋™์‹œ์— ํ…Œ์ŠคํŠธํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.
๋‚˜๋Š” ๋‹น์‹ ์˜ ์ƒ์šฉ๊ตฌ ํ”„๋กœ์ ํŠธ์— ๋Œ€ํ•œ PR์„ ๋งŒ๋“ค์—ˆ์Šต๋‹ˆ๋‹ค.

https://github.com/iamrandys/react-component-boilerplate/tree/karma

'npm test'๋ฅผ ์‹คํ–‰ํ•˜๊ธฐ๋งŒ ํ•˜๋ฉด karma๊ฐ€ ๋ธŒ๋ผ์šฐ์ €๋ฅผ ์‹คํ–‰ํ•˜๊ณ  ๋‹ค์Œ์„ ๊ฐ์‹œํ•ฉ๋‹ˆ๋‹ค.
๋ณ€๊ฒฝ.

2014๋…„ 8์›” 12์ผ ํ™”์š”์ผ ์˜ค์ „ 10:35 Tyrone Avnit [email protected]
์ผ๋‹ค:

@iamrandys https://github.com/iamrandys ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค
๋ฐ˜์‘ ๊ตฌ์„ฑ ์š”์†Œ ๋ณด์ผ๋Ÿฌ ํ”Œ๋ ˆ์ดํŠธ
https://github.com/TYRONEMICHAEL/react-component-boilerplate ์‚ฌ์šฉ
๋ชจ์นด์™€ ์ฐจ์ด(์ž์Šค๋ฏผ์€ ์‰ฝ๊ฒŒ ๋Œ€์ฒด ๊ฐ€๋Šฅ). ํ…Œ์ŠคํŠธ๋Š” ๊ทน๋„๋กœ
Livereload์˜ ์ถ”๊ฐ€ ์ด์ ์„ ์–ป์„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ์›ํ•˜๋Š” ๋Œ€๋กœ ์‚ฌ์šฉํ•˜์‹ญ์‹œ์˜ค.

โ€”
์ด ์ด๋ฉ”์ผ์— ์ง์ ‘ ๋‹ต์žฅํ•˜๊ฑฐ๋‚˜ GitHub์—์„œ ํ™•์ธํ•˜์„ธ์š”.
https://github.com/facebook/jest/issues/116#issuecomment -51931532.

JSX ๋ณ€ํ™˜์ด ์•„๋‹Œ JSX ํŒŒ์ผ์„ ๋ฐฉ์ง€ํ•˜๋ ค๋ฉด ๋‹ค์Œ preprocessor.js๋ฅผ ์‚ฌ์šฉํ•˜์‹ญ์‹œ์˜ค. ๊ทธ๋Œ€๋กœ /** @jsx ์ ‘๋‘์‚ฌ๊ฐ€ ํฌํ•จ๋œ .jsx ํŒŒ์ผ๋งŒ ์ฒ˜๋ฆฌํ•ฉ๋‹ˆ๋‹ค. .js ํŒŒ์ผ์„ JSX ๋ณ€ํ™˜ํ•˜๋ ค๋ฉด || ์•ž์— ์žˆ๋Š” if ์กฐ๊ฑด์˜ ์ฒซ ๋ฒˆ์งธ ๋ถ€๋ถ„์„ ์ œ๊ฑฐํ•˜๋ฉด ๋ฉ๋‹ˆ๋‹ค( src.slice ... ์กฐ๊ฑด๋งŒ ๋‚จ๋„๋ก).

// from http://facebook.github.io/jest/docs/tutorial-react.html
var ReactTools = require('react-tools');
var MAGIC = "/** @jsx";
module.exports = {
  process: function(src, file) {
    if (!/\.jsx$/.test(file) || src.slice(0, MAGIC.length) != MAGIC) return src;
    return ReactTools.transform(src);
  }
};

๊ทธ๋ž˜๋„ ์ข€ ๋Š๋ฆฝ๋‹ˆ๋‹ค.

ํฅ๋ฏธ๋กœ์šด ์Šค๋‹ˆํŽซ @sqs. ์ˆ˜์ •ํ•ด์ค˜ ๋‚ด๊ฐ€ ํ‹€๋ ธ๋‹ค๋ฉด ์—ฌ์ „ํžˆ ๊ฐ ํŒŒ์ผ์„ ์‚ดํŽด๋ณด๊ณ  ๋ณ€ํ™˜ํ•ด์•ผ ํ•˜๋Š”์ง€ ํ™•์ธํ•  ํ•„์š”๊ฐ€ ์—†์Šต๋‹ˆ๊นŒ? ๋‚˜๋Š” react-component-boilerplate๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ๋งŽ์€ ์„ฑ๊ณต์„ ๊ฑฐ๋‘์—ˆ๋‹ค. ํ…Œ์ŠคํŠธ๋Š” ์‹ค์ œ๋กœ ๋งค์šฐ ๋น ๋ฅด๊ฒŒ ์‹คํ–‰๋ฉ๋‹ˆ๋‹ค.

์•„์ฃผ ์ข‹์•„. ์ด๋ฅผ ํ†ตํ•ด ์‹œ๊ฐ„์ด 9.3์ดˆ์—์„œ 4.7์ดˆ๋กœ ๋‹จ์ถ•๋˜์—ˆ์Šต๋‹ˆ๋‹ค. ์ด๊ฒƒ์€ ๋‹จ์ผ ํ…Œ์ŠคํŠธ์šฉ์ž…๋‹ˆ๋‹ค. ๋‚˜๋Š” ์—ฌ์ „ํžˆ ํ›จ์”ฌ ๋” ๋น ๋ฅธ Karma๋ฅผ ์œ ์ง€ํ•ด์•ผ ํ•  ๊ฒƒ์ž…๋‹ˆ๋‹ค(100๋ฒˆ์˜ ํ…Œ์ŠคํŠธ๋Š” 1์ดˆ ๋ฏธ๋งŒ ์†Œ์š”). ๋˜ํ•œ Karma๋Š” ์ž‘์—… ์‹œ ๋ณ€๊ฒฝ ์‚ฌํ•ญ์„ ๊ด€์ฐฐํ•˜๊ณ  ์—ฌ๋Ÿฌ ๋ธŒ๋ผ์šฐ์ €์—์„œ ์ฝ”๋“œ๋ฅผ ํ…Œ์ŠคํŠธํ•˜์ง€๋งŒ Jest์˜ ์ž๋™ ์กฐ๋กฑ์„ ์ข‹์•„ํ•ฉ๋‹ˆ๋‹ค. rewireify๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์ˆ˜๋™์œผ๋กœ ์ŠคํŒŒ์ด๋ฅผ ๋งŒ๋“œ๋Š” ๊ฒƒ์€ ์ถ”๊ฐ€ ์ž‘์—…์ด์ง€๋งŒ ์™„์ „ํžˆ ์ œ์–ดํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์˜ˆ, ์ œ๊ฐ€ ๋‹น์‹ ์„ ์˜คํ•ดํ•˜๊ณ  ์žˆ์„์ง€๋„ ๋ชจ๋ฅด์ง€๋งŒ, jsx๊ฐ€ ํฌํ•จ๋œ .js ํŒŒ์ผ์ด ์žˆ๊ณ  pragma ํ—ค๋”๋ฅผ ๊ธฐ๋ฐ˜์œผ๋กœ ๊ฐ์ง€ํ•˜๋ ค๋Š” ๊ฒฝ์šฐ .jsx์— ๋Œ€ํ•œ ๊ฒ€์‚ฌ๋ฅผ ์ œ๊ฑฐํ•œ๋‹ค๋Š” ์˜๋ฏธ์ž…๋‹ˆ๋‹ค.

๋‚ด iPhone์—์„œ ๋ณด๋‚ธ

2014๋…„ 8์›” 28์ผ 23์‹œ 45๋ถ„์— Tyrone Avnit [email protected]์ด ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ผ์Šต๋‹ˆ๋‹ค.

ํฅ๋ฏธ๋กœ์šด ์Šค๋‹ˆํŽซ @sqs. ์ˆ˜์ •ํ•ด์ค˜ ๋‚ด๊ฐ€ ํ‹€๋ ธ๋‹ค๋ฉด ์—ฌ์ „ํžˆ ๊ฐ ํŒŒ์ผ์„ ์‚ดํŽด๋ณด๊ณ  ๋ณ€ํ™˜ํ•ด์•ผ ํ•˜๋Š”์ง€ ํ™•์ธํ•  ํ•„์š”๊ฐ€ ์—†์Šต๋‹ˆ๊นŒ? ๋‚˜๋Š” react-component-boilerplate์™€ ํ•จ๊ป˜ ๋งŽ์€ ์„ฑ๊ณต์„ ๊ฑฐ๋‘์—ˆ์Šต๋‹ˆ๋‹ค. ํ…Œ์ŠคํŠธ๋Š” ์‹ค์ œ๋กœ ๋งค์šฐ ๋น ๋ฅด๊ฒŒ ์‹คํ–‰๋ฉ๋‹ˆ๋‹ค.

โ€”
์ด ์ด๋ฉ”์ผ์— ์ง์ ‘ ํšŒ์‹ ํ•˜๊ฑฐ๋‚˜ GitHub์—์„œ ํ™•์ธํ•˜์„ธ์š”.

์•ˆ๋…•ํ•˜์„ธ์š”! ๋‚˜๋Š” ๋†๋‹ด์„ ์œ„ํ•ด --watch ์„ ํ•˜๊ณ  ์žˆ์œผ๋ฉฐ ์ผ๋ฐ˜์ ์œผ๋กœ ์ด ์ž‘์—…์„ ๋” ๋น ๋ฅด๊ฒŒ ์ง„ํ–‰ํ•˜๋ ค๊ณ  ๋…ธ๋ ฅํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ๊ณง ๋‹ค์‹œ ๋ณด๊ณ ํ•  ๊ฒƒ์ž…๋‹ˆ๋‹ค.

๋‚˜๋ฅผ ์œ„ํ•œ ์ฒซ ๋ฒˆ์งธ ์‹คํ–‰์€ ์•ฝ 5์ดˆ๊ฐ€ ๊ฑธ๋ฆฝ๋‹ˆ๋‹ค. ๊ทธ ํ›„ ๊ฐ ์ถ”๊ฐ€ ์‹คํ–‰์—๋Š” ์•ฝ 1.2-1.5์ดˆ๊ฐ€ ๊ฑธ๋ฆฝ๋‹ˆ๋‹ค.

๊ทธ ์‹œ๊ฐ„ ์ค‘ ์ƒ๋‹นํ•œ ์‹œ๊ฐ„์ด ์„œ๋‘˜๋Ÿฌ ์บ์‹œ๋ฅผ ๋กœ๋“œํ•˜๋Š” ๋ฐ ์†Œ๋น„๋œ ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค(๋‚ด ํ”„๋กœ์ ํŠธ์˜ ๊ฒฝ์šฐ ์ด๋ฏธ 4๋ฉ”๊ฐ€ ํŒŒ์ผ์ž…๋‹ˆ๋‹ค.

--watch ์ž‘์—…์„ ๊ธฐ๋Œ€ํ•˜๊ณ  ์žˆ์ง€๋งŒ ํ…Œ์ŠคํŠธ๋ฅผ ์‹คํ–‰ํ•˜๋Š” ๋ฐ 1.2์ดˆ์˜ ๋กœ๋“œ ์‹œ๊ฐ„์ด ํ•„์š”ํ•œ ๋ฌด์Šจ ์ผ์ด ์ผ์–ด๋‚˜๊ณ  ์žˆ๋Š”์ง€ ๊ถ๊ธˆํ•ฉ๋‹ˆ๋‹ค. ๋‚˜๋Š” ์„œ๋‘๋ฅด๋Š” ๊ฒƒ์ด ๋ฌด์—‡์„ ํ•˜๊ณ  ์žˆ๊ณ  ์™œ ๋†๋‹ด์ด ๊ทธ๊ฒƒ์„ ์‚ฌ์šฉํ•˜๋Š”์ง€์— ๋Œ€ํ•ด ์•„๋ฌด๊ฒƒ๋„ ์•Œ์ง€ ๋ชปํ•˜๊ธฐ ๋•Œ๋ฌธ์— ๋‚˜๋Š” ๊ฝค ๋‹จ์„œ๊ฐ€ ์—†์Šต๋‹ˆ๋‹ค.

Haste๋Š” CommonJS ๋ชจ๋“ˆ ํ˜•์‹์˜ ํŠน์ง•์„ ์ง€์›ํ•ฉ๋‹ˆ๋‹ค. ๋ชจ๋“ˆ ์ด๋ฆ„์ด ์ƒ๋Œ€์ ์ธ ๊ฒƒ์ด ์•„๋‹ˆ๋ผ ์ตœ์ƒ์œ„ ์ˆ˜์ค€์ธ ๊ฒฝ์šฐ์ž…๋‹ˆ๋‹ค. ์ฆ‰, ํ”„๋กœ๊ทธ๋žจ์„ ์‹คํ–‰ํ•˜๊ธฐ ์ „์— ๋ฏธ๋ฆฌ ๋ชจ๋“ˆ(๋ฐ ์ข…์†์„ฑ)์„ ์•Œ์•„์•ผ ํ•ฉ๋‹ˆ๋‹ค. ๊ทธ๋ ‡์ง€ ์•Š์œผ๋ฉด ๊ฐ require ์—์„œ ๋ชจ๋“ˆ์„ ์ฐพ๊ธฐ ์œ„ํ•ด ํŒŒ์ผ ์‹œ์Šคํ…œ์„ ํƒ์ƒ‰ํ•˜๋Š” ๊ฒƒ์ด ์—„์ฒญ๋‚˜๊ฒŒ ๋น„ํšจ์œจ์ ์ž…๋‹ˆ๋‹ค. ๊ทธ๋Ÿฌ๋‚˜ ์šฐ๋ฆฌ๋Š” ๋Œ€๋ถ€๋ถ„์˜ ์‚ฌ๋žŒ๋“ค์ด ์ƒ๋Œ€ ๋ชจ๋“ˆ ํ˜•์‹(์˜ˆ: node.js)์„ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์œผ๋ฉฐ Haste์— ๋Œ€ํ•œ ์•”์‹œ์  ์ข…์†์„ฑ์„ ์ œ๊ฑฐํ•˜๊ธฐ๋ฅผ ์›ํ•˜๋ฉฐ(์˜ต์…˜์ด ์ œ๊ณต๋˜์ง€ ์•Š๋Š” ํ•œ) ์ด๋ ‡๊ฒŒ ํ•˜๋ฉด ๋” ๋นจ๋ผ์งˆ ๊ฒƒ์ž…๋‹ˆ๋‹ค.

@amasad ๋Œ€๋‹จํ•˜๋„ค์š” . ๋‚˜๋Š” intern.js๋ฅผ ์‹œ๋„ํ–ˆ๊ณ  cmd ๋ผ์ธ์—์„œ ์ผ๋ฐ˜ ๋‹จ์œ„ ํ…Œ์ŠคํŠธ๋ฅผ ์‹คํ–‰ํ•˜์—ฌ ๋ช‡ ms ์•ˆ์— ์™„๋ฃŒ๋ฉ๋‹ˆ๋‹ค. ๋†๋‹ด์ด ๊ทธ๋ ‡๊ฒŒ ๋นจ๋ฆฌ ๊ฐˆ ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๊นŒ? ๊ทธ๋ฆฌ๊ณ  jasmine์ด๋‚˜ mocha์™€ ๊ฐ™์€ ๋‹ค๋ฅธ ํ”„๋ ˆ์ž„์›Œํฌ์—์„œ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋„๋ก automocking ๋ถ€๋ถ„์„ ์ถ”์ถœํ•˜๋Š” ๊ฒƒ์„ ๊ณ ๋ คํ•ด ๋ณด์…จ์Šต๋‹ˆ๊นŒ?

beforeEach ๋˜๋Š” it ์ฝœ๋ฐฑ์—์„œ ๋ฐ˜๋ณต์ ์œผ๋กœ ์‚ฌ์šฉํ•˜๋Š” ๋Œ€์‹  describe ์ฝœ๋ฐฑ์—์„œ ํŒŒ์ผ(ํŠนํžˆ 'react/addons' ๋ฐ ํ…Œ์ŠคํŠธ ์ค‘์ธ ๋ชจ๋“ˆ)์ด ํ•„์š”ํ•œ ๊ฒƒ์„ ๋ฐœ๊ฒฌํ–ˆ์Šต๋‹ˆ๋‹ค.

๋ถ„๋ช…ํžˆ ๋‚˜๋Š” โ€‹โ€‹jsx๊ฐ€ ์•„๋‹Œ ์ปคํ”ผ ์Šคํฌ๋ฆฝํŠธ๋ฅผ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์ง€๋งŒ ์ด๊ฒƒ์€ require ํ˜ธ์ถœ์„ ์ž๋™์œผ๋กœ ๋ชจ์˜ํ•˜๊ธฐ ์œ„ํ•ด ์ž‘์—…ํ•˜๋Š” ์ „์ฒ˜๋ฆฌ๊ธฐ ์ž‘์—…๊ณผ ๋†๋‹ด์„ ๋ชจ๋‘ ์ €์žฅํ•ฉ๋‹ˆ๋‹ค.

__tests__/login_fields.coffee (3.013s) (์•„์•ผ!)

describe 'Login Fields', -> 
 beforeEach ->
    {TestUtils} = require('react/addons').addons
    LoginFields = require '../login_fields'
    ...
  it 'should have left animation states defined', ->
    {TestUtils} = require('react/addons').addons
    ...
  it 'should have a translateX value equal to enterStateStart.left', ->
    {TestUtils} = require('react/addons').addons
    ...
  it 'should call handleLogin on button click or enter press with the entered username and password', ->
    {TestUtils} = require('react/addons').addons
    ...
  it 'should call updateFields on all change events', ->
    {TestUtils} = require('react/addons').addons
    ...

๊ทธ๋Ÿฌ๋‚˜, ๊ทธ๊ฒƒ์€ ํ›จ์”ฌ ๋นจ๋ผ์ง‘๋‹ˆ๋‹ค ...
__tests__/login_fields.coffee (0.604s) (๋‚˜์˜์ง€ ์•Š์Œ)

describe 'Login Fields', ->
  {TestUtils} = require('react/addons').addons
  LoginFields = require '../login_fields'
  # require other repeatedly needed modules here as well

  beforeEach ->
    # now you can use TestUtils to renderIntoDocument LoginFields here

  it 'should have left animation states defined', ->
    # and use TestUtils here
  ...

๋‚ด ํ…Œ์ŠคํŠธ๋Š” ์ง€๊ธˆ๊นŒ์ง€ ๊ถŒ์žฅ๋œ ๋ชจ๋“  ์ตœ์ ํ™”๋ฅผ ์‚ฌ์šฉํ•œ ํ›„์—๋„ 14์ดˆ์ž…๋‹ˆ๋‹ค. 16GB RAM๊ณผ SSD๋ฅผ ์‚ฌ์šฉํ•˜๋”๋ผ๋„. Jest๋Š” ํ˜„์žฌ ์ƒํƒœ์—์„œ ์™„์ „ํžˆ ์‚ฌ์šฉํ•  ์ˆ˜ ์—†์Šต๋‹ˆ๋‹ค. ์ฃ„์†กํ•ฉ๋‹ˆ๋‹ค. Karma๋กœ ์ „ํ™˜ํ•ฉ๋‹ˆ๋‹ค.

๋‚˜๋Š” karma, mocha, chai, sinon, rewireify ๋ฐ aliasify๋กœ ํฐ ์„ฑ๊ณต์„ ๊ฑฐ๋‘์—ˆ์Šต๋‹ˆ๋‹ค. 300๊ฐœ ์ด์ƒ์˜ ํ…Œ์ŠคํŠธ๊ฐ€ 1/2์ดˆ์— ์‹คํ–‰๋ฉ๋‹ˆ๋‹ค. ๋ฌด์—‡๋ณด๋‹ค๋„ React๋Š” ํ›Œ๋ฅญํ•ฉ๋‹ˆ๋‹ค!!!!! ํŒ€์€ ๊ทธ๊ฒƒ์„ ์‚ฌ๋ž‘ํ•˜๊ณ  ๊ทธ๊ฒƒ์œผ๋กœ ์ •๋ง ์ข‹์€ ๊ฒƒ๋“ค์„ ๊ฐœ๋ฐœํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ๋„ˆ๋ฌด ๊นจ๋—ํ•˜๊ณ  ์œ ์ง€ ๋ณด์ˆ˜๊ฐ€ ๊ฐ€๋Šฅํ•ฉ๋‹ˆ๋‹ค. ์šฐ๋ฆฌ๊ฐ€ ์ง€๊ธˆ๊นŒ์ง€ ์‚ฌ์šฉํ–ˆ๋˜ ๊ฒƒ๊ณผ๋Š” ์—„์ฒญ๋‚œ ์ฐจ์ด๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค.

๋ฐฉ๊ธˆ ์ด๊ฒƒ์— ๋ถ€๋”ช์ณค์Šต๋‹ˆ๋‹ค. ํ…Œ์ŠคํŠธ๊ฐ€ _REALLY_ ๋Š๋ฆฌ๊ฒŒ ์‹คํ–‰๋ฉ๋‹ˆ๋‹ค. ๋Š๋ฆฐ ํ…Œ์ŠคํŠธ์˜ ๋ฌธ์ œ๋Š” ๊ฐœ๋ฐœ์ž๊ฐ€ ํ…Œ์ŠคํŠธ๋ฅผ ๋น„ํ™œ์„ฑํ™”ํ•˜๊ฑฐ๋‚˜ ์ผ๋ถ€๋งŒ ์‹คํ–‰ํ•œ๋‹ค๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ์ด ๋ฌธ์ œ์˜ ์›์ธ์ด ๋ฌด์—‡์ธ์ง€ ์•„์‹ญ๋‹ˆ๊นŒ? ๋‚ด๊ฐ€ ์–ด๋–ป๊ฒŒ ๋„์›€์ด ๋  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค?

๋‚˜๋Š”์ด ์ •ํ™•ํ•œ ๋ฌธ์ œ๊ฐ€์žˆ์—ˆ์Šต๋‹ˆ๋‹ค. ํ…Œ์ŠคํŠธ๋Š” ์ฒ˜์Œ์— ์•ฝ 17 ์ดˆ๊ฐ€ ๊ฑธ๋ ธ๊ณ  ์บ์‹ฑ ํ›„์—๋Š” 4 ์ดˆ๊ฐ€ ๊ฑธ๋ ธ์Šต๋‹ˆ๋‹ค. ๋‚ด ๋นŒ๋“œ ๋””๋ ‰ํ† ๋ฆฌ์™€ ์™ธ๋ถ€ ๋ชจ๋“ˆ์ด ์ œ๋Œ€๋กœ ์ œ์™ธ๋˜์ง€ ์•Š์€ ๊ฒƒ์œผ๋กœ ๋‚˜ํƒ€๋‚ฌ์Šต๋‹ˆ๋‹ค. ์†Œ์Šค ๋””๋ ‰ํ† ๋ฆฌ๋ฅผ ๊ฐ€๋ฆฌํ‚ค๋„๋ก testPathDirs ๊ตฌ์„ฑ ์˜ต์…˜์„ ์„ค์ •ํ•˜๋ฉด ๋Ÿฐํƒ€์ž„์ด 0.5์ดˆ๋กœ ๋‹จ์ถ•๋˜์—ˆ์Šต๋‹ˆ๋‹ค.

์ด๊ฒƒ์€ React v0.12+๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์ €์—๊ฒŒ ํšจ๊ณผ์ ์ด์—ˆ์Šต๋‹ˆ๋‹ค.

var ReactTools = require('react-tools');


module.exports = {
  process: function(src, file) {
    if(!file.match(/\.react\.js$/)) return src;

    return ReactTools.transform(src);
  }
};

Jest๋„ ์‚ฌ์šฉํ•˜๊ธฐ ์‹œ์ž‘ํ–ˆ์Šต๋‹ˆ๋‹ค. ์ผ๋ฐ˜ JavaScript ๋ชจ๋“ˆ(JSX/React ์—†์Œ)์„ ํ…Œ์ŠคํŠธํ•˜๊ธฐ๋งŒ ํ•˜๋ฉด Jest๊ฐ€ ๋งค์šฐ ๋Š๋ฆฝ๋‹ˆ๋‹ค. ์ธ๋ผ์ธ ํ…Œ์ŠคํŠธ์™€ ๋‚ด์žฅํ˜• ์กฐ๋กฑ์ด๋ผ๋Š” ์•„์ด๋””์–ด๊ฐ€ ๋งˆ์Œ์— ๋“ค์ง€๋งŒ ๋„ˆ๋ฌด ๋Š๋ฆฌ๊ธฐ ๋•Œ๋ฌธ์— Mocha๊ฐ€ ๊ทธ๋ฆฌ์›Œ์ง‘๋‹ˆ๋‹ค. ๋ฒ”์ธ์ด ๋ฌด์—‡์ธ์ง€ ์ž˜ ๋ชจ๋ฅด๊ฒ ์Šต๋‹ˆ๋‹ค ... ๋Š๋ฆฐ ์†๋„๋ฅผ ์ผ์œผํ‚ค๋Š” ๋””๋ ‰ํ† ๋ฆฌ ํŠธ๋ฆฌ๋ฅผ ๊ฒ€์ƒ‰ํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ํŒŒ์ผ์„ ์ง์ ‘ ์ง€์ •ํ•˜๋ฉด ์—ฌ์ „ํžˆ ๋งค์šฐ ๋Š๋ฆฝ๋‹ˆ๋‹ค.

์ ์–ด๋„ ์†๋„ ์ €ํ•˜์˜ ์›์ธ์— ๋Œ€ํ•œ ์•„์ด๋””์–ด๊ฐ€ ์žˆ์Šต๋‹ˆ๊นŒ? (์ €๋Š” JSX/CoffeeScript๋ฅผ ์‚ฌ์šฉํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ์ž๋™ ๋ชจ์˜ ๊ธฐ๋Šฅ์ด ๊บผ์ ธ ์žˆ์Šต๋‹ˆ๋‹ค.)

์ฒซ ๋ฒˆ์งธ ์ธ์ˆ˜๊ฐ€ ํ•ญ์ƒ true๋ฅผ ๋ฐ˜ํ™˜ํ–ˆ๊ธฐ ๋•Œ๋ฌธ์— ์›๋ž˜ ์˜ˆ์ œ๋Š” ์ €์—๊ฒŒ ํšจ๊ณผ๊ฐ€ ์—†์—ˆ์Šต๋‹ˆ๋‹ค.

var ReactTools = require('react-tools');
var MAGIC = "/** <strong i="6">@jsx</strong> ";
module.exports = {
  process: function(src, file) {
    if (src.slice(0, MAGIC.length) != MAGIC) return src;
    return ReactTools.transform(src);
  }
};

@culshaw @haihappen ์ข‹์€ ํ•ด๊ฒฐ ๋ฐฉ๋ฒ•์— ๊ฐ์‚ฌ๋“œ๋ฆฝ๋‹ˆ๋‹ค. 10s+ ํ…Œ์ŠคํŠธ๋ฅผ 2+๋กœ ์ค„์ด์‹ญ์‹œ์˜ค. ์ด ํ•ด๊ฒฐ ๋ฐฉ๋ฒ•์€ ๋ฐ˜์‘ ํŒŒ์ผ์— ํ™•์žฅ์ž _.jsx/_.react.js๋ฅผ ์‚ฌ์šฉํ•ด์•ผ ํ•œ๋‹ค๊ณ  ์ƒ๊ฐํ•˜๊ฒŒ ๋งŒ๋“ค์—ˆ์Šต๋‹ˆ๋‹ค. ๋ฐ˜์‘ ํŒŒ์ผ์„ ์‚ฌ์šฉํ•  ๋•Œ๋„ ๋„์›€์ด ๋  ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค.

์†”์งํžˆ ๋งํ•ด์„œ Grunt๋ฅผ ํ†ตํ•ด ๋‚˜๋Š” ์—ฌ์ „ํžˆ +20s์˜ ์‹œ๊ฐ„์„ ์–ป์—ˆ์Šต๋‹ˆ๋‹ค.
Karma๋กœ ์ž‘์—…ํ•˜๋Š” ๋ฐ˜์‘ ๋ฐ ์ด ์‹œ๊ฐ„์€ ์•ฝ +4/5์ดˆ์ž…๋‹ˆ๋‹ค.

๋ชจ๋‘ VM ๋‚ด๋ถ€์— ์žˆ์ง€๋งŒ

์ด๊ฒƒ์— ๋Œ€ํ•ด ๋‹ค์‹œ ๋ณด๊ณ ํ•˜๊ธฐ ์œ„ํ•ด์„œ์ž…๋‹ˆ๋‹ค. ์šฐ๋ฆฌ๋Š” Karma/Mocha๋กœ ๋ฐ˜์‘์„ ํ…Œ์ŠคํŠธํ•˜๊ณ  ์žˆ์œผ๋ฉฐ 700๊ฐœ์— ๊ฐ€๊นŒ์šด ํ…Œ์ŠคํŠธ์ด๋ฉฐ ๋ชจ๋“  ํ…Œ์ŠคํŠธ๋ฅผ ์‹คํ–‰ํ•˜๋Š” ๋ฐ ์•ฝ 4์ดˆ๊ฐ€ ๊ฑธ๋ฆฝ๋‹ˆ๋‹ค. ์šฐ๋ฆฌ๋Š” ๋ชจ์˜๋ฅผ ์ฒ˜๋ฆฌํ•ด์•ผ ํ•˜์ง€๋งŒ ๊ทธ๋งŒํ•œ ๊ฐ€์น˜๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค. ๋ฐ˜์‘์€ ํ›Œ๋ฅญํ–ˆ์Šต๋‹ˆ๋‹ค. ํ ์žก์„ ๋ฐ ์—†์ด ์ƒ์พŒํ•˜๊ฒŒ ์•ˆ์ •์ ์ž…๋‹ˆ๋‹ค. ๊ฒŒ์ž„ ์ฒด์ธ์ €! ์šฐ๋ฆฌ ํŒ€์€ ๋‹ค๋ฅธ ๊ฒƒ์„ ์‚ฌ์šฉํ•˜์—ฌ ์ด๋ฏธ์ง•ํ•  ์ˆ˜ ์—†์—ˆ์Šต๋‹ˆ๋‹ค.

๋‚˜๋Š” Jest๊ฐ€ ๋น ๋ฅด๋„๋ก ํ•œ ์ ์ด ์—†๋‹ค. ์ €๋Š” ๋ชจ์นด๋ฅผ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. Jest๊ฐ€ ๋นจ๋ž๋‹ค๋ฉด ๋‚˜๋Š”
๋Œ€์‹  ์‚ฌ์šฉํ–ˆ์„ ๊ฒƒ์ž…๋‹ˆ๋‹ค.

2015๋…„ 2์›” 5์ผ ๋ชฉ์š”์ผ ์˜คํ›„ 12์‹œ 17๋ถ„, Gil Birman [email protected]
์ผ๋‹ค:

@iamrandys https://github.com/iamrandys
์–ด๋–ป๊ฒŒ ๊ทธ๋ ‡๊ฒŒ ๋นจ๋ฆฌ ๋†๋‹ด์„ ํ•  ์ˆ˜ ์žˆ์—ˆ๋Š”์ง€ ์ž์„ธํžˆ ์•Œ๋ ค์ฃผ์„ธ์š”.

โ€”
์ด ์ด๋ฉ”์ผ์— ์ง์ ‘ ๋‹ต์žฅํ•˜๊ฑฐ๋‚˜ GitHub์—์„œ ํ™•์ธํ•˜์„ธ์š”.
https://github.com/facebook/jest/issues/116#issuecomment -73097182.

@iamrandys ์—๊ฒŒ ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค. ๋‚ด "์–ด๋–ป๊ฒŒ ๋นจ๋ฆฌ ๋†๋‹ด์„ ํ•˜๊ฒŒ ๋˜์—ˆ๋‚˜์š”?"๋ฅผ ์‚ญ์ œํ–ˆ์Šต๋‹ˆ๋‹ค. ๋‚ด๊ฐ€ ๋‹น์‹ ์˜ ๊ฒŒ์‹œ๋ฌผ์„ ์ž˜๋ชป ์ฝ์—ˆ๋‹ค๋Š” ๊ฒƒ์„ ๊นจ๋‹ฌ์€ ํ›„์˜ ์งˆ๋ฌธ(ํ•˜์ง€๋งŒ ๋‹น์‹ ์€ ๋™์‹œ์— ์‘๋‹ตํ–ˆ์Šต๋‹ˆ๋‹ค)... ์–ด์จŒ๋“ , ๊ทธ๊ฒƒ์€ ๋ถ€๋„๋Ÿฌ์šด ์ผ์ž…๋‹ˆ๋‹ค. ์ œ ์ƒ๊ฐ์—๋Š” ๋†๋‹ด์ด ์—ฌ์ „ํžˆ ํ”„๋กœ๋•์…˜์— ์‚ฌ์šฉํ•  ์ค€๋น„๊ฐ€ ๋˜์ง€ ์•Š์€ ๊ฒƒ์œผ๋กœ ๊ฐ„์ฃผ๋˜์–ด์•ผ ํ•ฉ๋‹ˆ๋‹ค.

@haihappen ๋ฐ @darcyadams ์˜ ํ•ด๊ฒฐ ๋ฐฉ๋ฒ•/๋ณ€๊ฒฝ ์‚ฌํ•ญ์€ ๋‹จ์ผ ํ…Œ์ŠคํŠธ์— ๋Œ€ํ•ด ํ…Œ์ŠคํŠธ ์‹œ๊ฐ„์„ 3.5์ดˆ์—์„œ ์•ฝ 1์ดˆ๋กœ

๋‚˜๋Š” ๊ฐ™์€ ๋ฌธ์ œ๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค. ์ž‘์€ ํ”„๋กœ์ ํŠธ์—์„œ ๋‹จ 3๊ฐœ์˜ ํ…Œ์ŠคํŠธ๋ฅผ ๋ฐ›์•˜๊ณ  3์ดˆ๊ฐ€ ๊ฑธ๋ฆฝ๋‹ˆ๋‹ค.

ํ”„๋กœ์ ํŠธ ๋กœ๋“œ๋งต์˜ ์–ด๋Š ๋ถ€๋ถ„์—์„œ๋‚˜ ์„ฑ๋Šฅ์„ ๊ฐœ์„ ํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๊นŒ?

BTW: ๋ณ€๊ฒฝ๋œ ํŒŒ์ผ์— ๋Œ€ํ•ด์„œ๋งŒ ๋‹จ์œ„ ํ…Œ์ŠคํŠธ๋ฅผ ๋‹ค์‹œ ์‹คํ–‰ํ•˜๋Š” (๋งค์šฐ ํ•ดํ‚น ๊ฐ™์€) ๋ฐฉ๋ฒ•์„ ์ฐพ์•˜์Šต๋‹ˆ๋‹ค. ์ผ๋ฐ˜์ ์œผ๋กœ ์‹คํ–‰ํ•  ํ…Œ์ŠคํŠธ๊ฐ€ ํ•˜๋‚˜๋ฟ์ด๋ฏ€๋กœ ๋‹ค์‹œ ๋งค์šฐ ๋นจ๋ผ์ง‘๋‹ˆ๋‹ค. ์—ฌ๊ธฐ์— ๋„ฃ์–ด: https://gist.github.com/mik01aj/fefb7718331e5454b9d1

Strange Jest๋Š” React.js 2015 conf์—์„œ ์–ธ๊ธ‰๋˜์ง€ ์•Š์•˜์Šต๋‹ˆ๋‹ค.

testPathDirs๊ฐ€ ๋ฒ”์ธ์œผ๋กœ ๋ณด์ž…๋‹ˆ๋‹ค. package.json์—์„œ ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ง€์ •ํ•ฉ๋‹ˆ๋‹ค.

  "jest": {
    "unmockedModulePathPatterns": [
      "./node_modules"
    ],
    "scriptPreprocessor": "./preprocessor.js",
    "testDirectoryName": "tests",
    "testPathDirs": ["tests"]
  }

@adjavaherian ์ž๋™ ์กฐ๋กฑ์„ ์‚ฌ์šฉํ•˜๋Š” ๊ฒฝ์šฐ ์กฐ์‹ฌ ํ•˜์‹ญ์‹œ์˜ค :

์‹ค์ œ๋กœ testPathDirs๊ฐ€ ์ข…์†์„ฑ์„ ํฌํ•จํ•˜์ง€ ์•Š์œผ๋ฉด ์ž๋™ ์กฐ๋กฑ์ด ๋ฏธ๋ฌ˜ํ•˜๊ณ  ์‹ค๋ง์Šค๋Ÿฌ์šด ๋ฐฉ์‹์œผ๋กœ ์ค‘๋‹จ๋  ๊ฒƒ์œผ๋กœ ์˜ˆ์ƒํ•ฉ๋‹ˆ๋‹ค.

์ด๋Ÿฌํ•œ ์šฐ๋ ค๋กœ ์ธํ•ด ํ…Œ์ŠคํŠธ ์„ค์ •์— ๋ฌธ์ œ๊ฐ€ ์žˆ์„ ์ˆ˜ ์žˆ๋‹ค๊ณ  ์ƒ๊ฐํ•ฉ๋‹ˆ๋‹ค. ๋‚ด๊ฐ€ ์—ฌ๊ธฐ์—์„œ ํ‹€๋ฆด ์ˆ˜๋„ ์žˆ์ง€๋งŒ ๋‚ด๊ฐ€ ์•„๋Š” ํ•œ ์šฐ๋ฆฌ๋Š” ๋ชจ๋‘ beforeEach ํ…Œ์ŠคํŠธ ๋‚ด์—์„œ ๋‹ค๋ฅธ ํ•„์ˆ˜ ๋ชจ๋“ˆ๊ณผ ํ•จ๊ป˜ var component = React.createFactory(require("component/path")) ์™€ ๊ฐ™์€ ๊ฒƒ์„ ์‚ฌ์šฉํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ํ™•์‹คํžˆ ์ด๊ฒƒ์ด ๋ชจ๋“  ํ…Œ์ŠคํŠธ์— ํ•„์š”ํ•œ ๊ฒƒ์€ ์•„๋‹™๋‹ˆ๋‹ค. ๊ณต์žฅ์€ ๋งค๋ฒˆ ์ƒˆ๋กœ์šด ๋ถ€ํ’ˆ์„ ์ƒ์‚ฐํ•ด์•ผ ํ•ฉ๋‹ˆ๋‹ค. ๋‚ด๊ฐ€ beforeEach ๋ธ”๋ก ํ…Œ์ŠคํŠธ ์†๋„๋ฅผ 10๋ฐฐ ์ฆ๊ฐ€์‹œํ‚ต๋‹ˆ๋‹ค. ๋ถˆํ–‰ํžˆ๋„ ์ด ๊ฒฝ์šฐ ์ผ๋ถ€ ํ…Œ์ŠคํŠธ๊ฐ€ ์ด์ƒํ•˜๊ฒŒ ์‹คํŒจํ•˜๋Š”๋ฐ ๊ทธ ์ด์œ ๋ฅผ ๋ชจ๋ฅด๊ฒ ์Šต๋‹ˆ๋‹ค.

์ด๊ฒƒ์ด ๋„์›€์ด ๋˜๋Š”์ง€ ํ™•์‹คํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ์ƒ๊ฐ?

๋ณด๊ณ ๋œ ํ…Œ์ŠคํŠธ ์‹คํ–‰ ์‹œ๊ฐ„์—์„œ ์ „์ฒ˜๋ฆฌ ์‹œ๊ฐ„์„ ์ œ์™ธํ•˜๋ฉด ์ข‹์„ ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๊ทธ ์ž‘์—…์˜ ๋Œ€๋ถ€๋ถ„์ด ๋ณ€ํ™˜ ๋‹จ๊ณ„์—์„œ ๋‚˜์˜ค๋Š” ๊ฒฝ์šฐ ๋นจ๊ฐ„์ƒ‰์„ ๋ณด๋Š” ๊ฒƒ์€ ๋ถˆ๊ณตํ‰ํ•ฉ๋‹ˆ๋‹ค.

์•ˆ๋…•ํ•˜์„ธ์š” ์—ฌ๋Ÿฌ๋ถ„,

๊ฐ™์€ ๋ฌธ์ œ๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค. ์‹คํ–‰ํ•˜๋Š” ๋ฐ ์•ฝ 1๋ถ„์ด ๊ฑธ๋ฆฌ๋Š” ํ…Œ์ŠคํŠธ ์ผ€์ด์Šค๋„ ์žˆ์Šต๋‹ˆ๋‹ค.

์„ฑ๋Šฅ ๋ฌธ์ œ๋ฅผ ์–ด๋””์„œ๋ถ€ํ„ฐ ์‹œ์ž‘ํ•ด์•ผ ํ• ์ง€ ๋ชจ๋ฅด๊ฒ ์Šต๋‹ˆ๋‹ค. ํžŒํŠธ๊ฐ€ ์žˆ์Šต๋‹ˆ๊นŒ?


์—…๋ฐ์ดํŠธ

๋‚ด VM ํ™˜๊ฒฝ์—์„œ๋งŒ ๋‚˜ํƒ€๋‚˜๋Š” ์ด ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ–ˆ์Šต๋‹ˆ๋‹ค(cf : http://stackoverflow.com/a/13703132). ์ด์ œ ํ…Œ์ŠคํŠธ๋Š” ์—ฌ์ „ํžˆ ๋‚ด๊ฐ€ ์˜ˆ์ƒํ•œ ๊ฒƒ๋ณด๋‹ค ๋Š๋ฆฌ์ง€๋งŒ ๋ฐฉ๋ž‘์ž ์ˆ˜์ • ์ด์ „๋ณด๋‹ค ํ›จ์”ฌ ๋น ๋ฆ…๋‹ˆ๋‹ค(๋‚ด ํ…Œ์ŠคํŠธ ์ŠˆํŠธ์˜ ๊ฒฝ์šฐ 60์ดˆ -> 6์ดˆ)

์†๋„๊ฐ€ ์—ฌ์ „ํžˆ ๋ฌธ์ œ๋ผ๋ฉด Mocha๋กœ ์ด๋™ํ•˜๋Š” ๊ฒƒ์ด ์ข‹์Šต๋‹ˆ๋‹ค. ์šฐ๋ฆฌ๋Š” ์ด ํฌํฌ๋กœ ๋งŽ์€ ์„ฑ๊ณต์„ ๊ฑฐ๋‘์—ˆ์Šต๋‹ˆ๋‹ค. ์—ฌ๊ธฐ์—์„œ๋Š” ๋‹จ์ˆœ์—์„œ ๋ณต์žกํ•œ React ๋ฐฐํฌ์— ๋Œ€ํ•œ ํ…Œ์ŠคํŠธ๋ฅผ ์„ค์ •ํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ์„ค๋ช…ํ•ฉ๋‹ˆ๋‹ค. https://github.com/adjavaherian/mocha-react ์šฐ๋ฆฌ๋Š” ์•ฝ 3์ดˆ ๋™์•ˆ 100๊ฐœ ์ด์ƒ์˜ ํ…Œ์ŠคํŠธ๋ฅผ ์ •๊ธฐ์ ์œผ๋กœ ์‹คํ–‰ํ•ฉ๋‹ˆ๋‹ค.

๋‚˜๋Š” Mocha๊ฐ€ ๊ฐˆ ๊ธธ์ด๋ผ๋Š” ๋ฐ ๋™์˜ํ•ฉ๋‹ˆ๋‹ค. ์ตœ๋Œ€ ๊ฑฐ์˜ 900๋ฒˆ์˜ ํ…Œ์ŠคํŠธ๋ฅผ ์ˆ˜ํ–‰ํ•˜๋ฉฐ ์•ฝ 4์ดˆ๊ฐ€ ์†Œ์š”๋ฉ๋‹ˆ๋‹ค.

2015๋…„ 4์›” 23์ผ ์˜คํ›„ 4์‹œ 53๋ถ„์— Amir Djavaherian [email protected]์ด ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ผ์Šต๋‹ˆ๋‹ค.

์†๋„๊ฐ€ ์—ฌ์ „ํžˆ ๋ฌธ์ œ๋ผ๋ฉด Mocha๋กœ ์ด๋™ํ•˜๋Š” ๊ฒƒ์ด ์ข‹์Šต๋‹ˆ๋‹ค. ์šฐ๋ฆฌ๋Š” ์ด ํฌํฌ๋กœ ๋งŽ์€ ์„ฑ๊ณต์„ ๊ฑฐ๋‘์—ˆ์Šต๋‹ˆ๋‹ค. ์—ฌ๊ธฐ์—์„œ๋Š” ๋‹จ์ˆœ์—์„œ ๋ณต์žกํ•œ React ๋ฐฐํฌ์— ๋Œ€ํ•œ ํ…Œ์ŠคํŠธ๋ฅผ ์„ค์ •ํ•˜๋Š” ๋ฐฉ๋ฒ•์„ ์„ค๋ช…ํ•ฉ๋‹ˆ๋‹ค. https://github.com/adjavaherian/mocha-react ์šฐ๋ฆฌ๋Š” ์•ฝ 3์ดˆ ๋™์•ˆ 100๊ฐœ ์ด์ƒ์˜ ํ…Œ์ŠคํŠธ๋ฅผ ์ •๊ธฐ์ ์œผ๋กœ ์‹คํ–‰ํ•ฉ๋‹ˆ๋‹ค.

โ€”
์ด ์ด๋ฉ”์ผ์— ์ง์ ‘ ํšŒ์‹ ํ•˜๊ฑฐ๋‚˜ GitHub์—์„œ ํ™•์ธํ•˜์„ธ์š”.

๊ฐ™์€ ๊ฒฝํ—˜์œผ๋กœ Jest๋ฅผ ๋‹จ ํ•˜๋‚˜์˜ ํ…Œ์ŠคํŠธ(JSX ์‚ฌ์šฉ)๋กœ ์„ค์ •ํ•˜๊ณ  ์•ฝ 3์ดˆ๊ฐ€ ์†Œ์š”๋ฉ๋‹ˆ๋‹ค.

@iamrandys ์„ค์ • ์˜ˆ์‹œ๋ฅผ ๋ณด์—ฌ์ฃผ์‹œ๊ฒ ์Šต๋‹ˆ๊นŒ? ์™„๋ฒฝํ•œ ์ฝค๋น„์ธ ๊ฒƒ ๊ฐ™์Šต๋‹ˆ๋‹ค.

@amasad babel-loader๊ฐ€ cacheDirectory ์˜ต์…˜์—์„œ ํ—ˆ์šฉํ•˜๋Š” ๊ฒƒ๊ณผ ์œ ์‚ฌํ•œ ์ปดํŒŒ์ผ๋œ ํŒŒ์ผ์— ๋Œ€ํ•œ ์บ์‹œ๋ฅผ ๊ตฌ์ถ•ํ•˜๋Š” Jest ์˜ต์…˜์ด ์žˆ์Šต๋‹ˆ๊นŒ? - https://github.com/babel/babel-loader#options

์ €์—๊ฒŒ ๋†๋‹ด์„ ๋Š๋ฆฌ๊ฒŒ ๋งŒ๋“œ๋Š” ๊ฒƒ์€ ์ปดํŒŒ์ผ์ด ์•„๋‹ˆ๋ผ ์ž‘์—…์ž ํ’€ ํ”„๋กœ์„ธ์Šค์˜ ์‹œ์ž‘์ž…๋‹ˆ๋‹ค. ๋‚ด ๋ชจ๋“  ํ…Œ์ŠคํŠธ๋Š” ์•ฝ 4์ดˆ๊ฐ€ ๊ฑธ๋ฆฌ๋Š” ์ฒซ ๋ฒˆ์งธ ํ…Œ์ŠคํŠธ๋ฅผ ์ œ์™ธํ•˜๊ณ  0.05์ดˆ ์ด๋‚ด์— ํ†ต๊ณผํ•ฉ๋‹ˆ๋‹ค.
https://github.com/jeffmo/node-worker-pool
https://github.com/facebook/jest/blob/master/src/TestRunner.js#L376

@songawee ์•ˆ ํ•˜๋Š”๋ฐ PR์„ ๋ณด๋‚ด์„œ ์˜ต์…˜์œผ๋กœ ๊ฐ–๊ณ  ์‹ถ๋‚˜์š”? ์บ์‹œ๋ฅผ ๊นจ์•ผ ํ•  ๋•Œ๋ฅผ ์•„๋Š” ๊ฒƒ์ด ๋•Œ๋•Œ๋กœ ๋ถˆ๊ฐ€๋Šฅํ•˜๊ธฐ ๋•Œ๋ฌธ์— ๊ธฐ๋ณธ์ ์œผ๋กœ ์ผœ์ ธ ์žˆ์–ด์•ผ ํ•œ๋‹ค๊ณ  ์ƒ๊ฐํ•˜์ง€ ์•Š์Šต๋‹ˆ๋‹ค. ์˜ˆ๋ฅผ ๋“ค์–ด ์ปดํŒŒ์ผ๋Ÿฌ ์˜ต์…˜์„ ๋ณ€๊ฒฝํ•˜๋ฉด ์บ์‹œ๊ฐ€ ์žฌ์„ค์ •๋˜์–ด์•ผ ํ•ฉ๋‹ˆ๋‹ค. ๋˜ ๋‹ค๋ฅธ ์˜ต์…˜์€ ์บ์‹ฑ ์™ธ์— ์บ์‹œ ์žฌ์„ค์ • ์˜ต์…˜์„ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.

@doodzik node-haste ๋ชจ๋“ˆ์„ ๋งํ•˜๊ณ  ์ฝ๋Š” ๊ฒƒ์ด ์•„๋‹ˆ๋ผ ์ž‘์—…์ž ํ’€์ด๋ผ๊ณ  ํ™•์‹ ํ•ฉ๋‹ˆ๊นŒ?

@amasad ๋‚ด๊ฐ€ ํ•œ ๊ฒƒ์€ jest ์‹คํ–‰์˜ ๊ฐ ๋‹จ๊ณ„๊ฐ€ ์™„๋ฃŒ๋˜๋Š” ๋ฐ ๊ฑธ๋ฆฌ๋Š” ์‹œ๊ฐ„์„ ์ธก์ •ํ•œ ๊ฒƒ์ž…๋‹ˆ๋‹ค.
๊ทธ๋ฆฌ๊ณ  node-worker-pool ๋Š” ํ…Œ์ŠคํŠธ๊ฐ€ ๋Š๋ฆฐ ๋งˆ์ง€๋ง‰ ์ธ์Šคํ„ด์Šค์˜€์Šต๋‹ˆ๋‹ค.
๋‚ด ๋ฐœ๊ฒฌ์ด ๋‹จ์ง€ ์ฆ์ƒ์ผ ๋ฟ ๋ฌธ์ œ์˜ ๊ทผ์›์ด ์•„๋‹ ์ˆ˜๋„ ์žˆ์Šต๋‹ˆ๋‹ค.
ํ•˜์ง€๋งŒ ์ œ๋Œ€๋กœ ๋ถ„์„ํ•  ์‹œ๊ฐ„์ด ์—†์—ˆ๋‹ค.

๋‚ด ํ…Œ์ŠคํŠธ๋Š” ํ˜„์žฌ ๋‹ค์Œ๊ณผ ๊ฐ™์Šต๋‹ˆ๋‹ค.
screen shot 2015-06-03 at 00 10 16

๋‚ด ๋ฐ˜์‘ ํ…Œ์ŠคํŠธ๋Š” ๋Š๋ฆฝ๋‹ˆ๋‹ค(์˜ˆ์ œ ํด๋”์— ์žˆ๋Š” ํ…Œ์ŠคํŠธ). ๋‚ด๊ฐ€ ๋งํ•˜๋Š” ๊ฒƒ์€ ๋ฌด๋ฐ˜์‘ ํ…Œ์ŠคํŠธ์ž…๋‹ˆ๋‹ค.

+1

์—ฌ๊ธฐ๋„ ๋งˆ์ฐฌ๊ฐ€์ง€์ž…๋‹ˆ๋‹ค. ํ…Œ์ŠคํŠธ๊ฐ€ ๋งค์šฐ ๋Š๋ฆฝ๋‹ˆ๋‹ค. ์‹ค๋ง:

๋ฌธ์ œ์— ์ง๋ฉดํ•œ ์‚ฌ๋žŒ์€ ๋‚˜๋ฟ์ด๋ผ๊ณ  ์ƒ๊ฐํ–ˆ์Šต๋‹ˆ๋‹ค. Jest๋ฅผ ์ฒ˜์Œ ์‚ฌ์šฉํ•˜๊ณ  ํ…Œ์ŠคํŠธ ๊ฒฐ๊ณผ๊ฐ€ ๋น ๋ฅด์ง€ ์•Š์Šต๋‹ˆ๋‹ค. Facebook์ด Jest๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ํ…Œ์ŠคํŠธํ•˜๋Š” ๋ฐฉ๋ฒ•์ด ๊ถ๊ธˆํ•˜์‹ญ๋‹ˆ๊นŒ?

React Europe ์ปจํผ๋Ÿฐ์Šค Q&A ์„ธ์…˜์—์„œ React ์‚ฌ์šฉ์ž์— ๋Œ€ํ•œ Jest ๊ฐœ์„  ์‚ฌํ•ญ์— ๋Œ€ํ•œ ๋‚ด ์งˆ๋ฌธ - https://youtu.be/CRJZBZ_-6hQ?t=363

๋ชจ์นด+์‹œ๋…ผ์œผ๋กœ ๋ฐ”๊ฟจ์Šต๋‹ˆ๋‹ค. ๊ฒฐ์ฝ” ๋” ํ–‰๋ณตํ•˜์ง€ ์•Š์•˜์Šต๋‹ˆ๋‹ค.

2015๋…„ 8์›” 31์ผ 17:45 Alan Rubin [email protected] ์€ ๋‹ค์Œ๊ณผ ๊ฐ™์ด ์ผ์Šต๋‹ˆ๋‹ค.

React Europe ์ปจํผ๋Ÿฐ์Šค Q&A์—์„œ Jest to React์— ๋Œ€ํ•œ ๋‚ด ์งˆ๋ฌธ
์„ธ์…˜ - https://youtu.be/CRJZBZ_-6hQ?t=363

โ€”
์ด ์ด๋ฉ”์ผ์— ์ง์ ‘ ๋‹ต์žฅํ•˜๊ฑฐ๋‚˜ GitHub์—์„œ ํ™•์ธํ•˜์„ธ์š”.
https://github.com/facebook/jest/issues/116#issuecomment -136394910.

๋‚˜๋„ ๊ฐ™์€ ๋ฌธ์ œ๋ฅผ ์•ˆ๊ณ ์žˆ์–ด. Jest ํ…Œ์ŠคํŠธ๋Š” ์‹œ๊ฐ„์ด ๋งŽ์ด ๊ฑธ๋ฆฌ๊ณ  ์‹คํ–‰ ์‹œ๊ฐ„์€ ์‹ค์ œ๋กœ ๋‹ค์–‘ํ•ฉ๋‹ˆ๋‹ค. ๋ณ‘๋ ฌ๋กœ ์‹คํ–‰ํ• ์ง€ ์•„๋‹ˆ๋ฉด ํ•˜๋‚˜์˜ ํ”„๋กœ์„ธ์Šค(--runInBand)์—์„œ ์‹คํ–‰ํ• ์ง€ ์—ฌ๋ถ€๋Š” ์ค‘์š”ํ•˜์ง€ ์•Š์•˜์Šต๋‹ˆ๋‹ค. ์ž‘์—…์ž ํ”„๋กœ์„ธ์Šค ๊ฐ„์˜ ๋ฆฌ์†Œ์Šค ๊ฒฝํ•ฉ์ด ์•„๋‹Œ ๊ฒƒ์œผ๋กœ ๋ณด์ž…๋‹ˆ๋‹ค.

v8 ํ”„๋กœํŒŒ์ผ๋Ÿฌ(https://github.com/node-inspector/v8-profiler)๋กœ CPU ๋คํ”„๋ฅผ ์ƒ์„ฑํ–ˆ๊ณ  ๋Œ€๋ถ€๋ถ„์˜ ์‹œ๊ฐ„์ด ๋ชจ๋“ˆ์„ ์กฐ๋กฑํ•˜๋Š” ๋ฐ ์†Œ๋น„๋˜๋Š” ๊ฒƒ์œผ๋กœ ๋‚˜ํƒ€๋‚ฌ์Šต๋‹ˆ๋‹ค. ์ฆ‰, ๋‚ด ๋‹จ์œ„ ํ…Œ์ŠคํŠธ ์‹คํ–‰ ์‹œ๊ฐ„์˜ 25%๊ฐ€ jest-cli/src/lib/utils.js#runContentWithLocalBindings์—์„œ ์†Œ๋น„๋ฉ๋‹ˆ๋‹ค.

์„ฑ๋Šฅ ์—…๋ฐ์ดํŠธ๊ฐ€ ์žˆ์Šต๋‹ˆ๊นŒ? ๋ฐฉ๊ธˆ es6 ๋ฐ babel-jest๋กœ ๋†๋‹ด์„ ์ฃผ์› ์ง€๋งŒ > 10์ดˆ ์•ˆ์— 2๊ฐœ์˜ ๊ฐ„๋‹จํ•œ ํ…Œ์ŠคํŠธ๋ฅผ ์‹คํ–‰ํ–ˆ์Šต๋‹ˆ๋‹ค :-(
์†๋„๋ฅผ ๋†’์ด๊ธฐ ์œ„ํ•ด ์ด ์Šค๋ ˆ๋“œ์—์„œ ๋งŽ์€ ์•„์ด๋””์–ด๋ฅผ ์‹œ๋„ํ–ˆ์ง€๋งŒ ์•„๋ฌด ๊ฒƒ๋„ ํšจ๊ณผ๊ฐ€ ์—†์—ˆ์Šต๋‹ˆ๋‹ค...

์šฐ๋ฆฌ๋Š” ๊ณง ์ด๊ฒƒ์— ์ง‘์ค‘ํ•  ๊ฒƒ์ž…๋‹ˆ๋‹ค. ์šฐ๋ฆฌ๋Š” ์ง€๊ธˆ ๋†๋‹ด์— ๋Œ€ํ•œ ์ž‘์—…์œผ๋กœ ์•ฝ๊ฐ„ ์ –์–ด ์žˆ์ง€๋งŒ ๋” ๋ฉ‹์ง€๊ฒŒ ๋งŒ๋“ค๊ธฐ ์œ„ํ•ด ์ตœ์„ ์„ ๋‹คํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค.

์ปค๋ฎค๋‹ˆํ‹ฐ์—์„œ ๋„์›€์„ ์ค„ ์ˆ˜ ์žˆ๋Š” ์ž‘์—…์ด ์žˆ์Šต๋‹ˆ๊นŒ?

+1

ํ˜„์žฌ ๊ฐ€์žฅ ํฐ ๋„์›€์€ ์‹ค์ œ๋กœ ๋ฌธ์„œ, ์›น ์‚ฌ์ดํŠธ๋ฅผ ๊ฐœ์„ ํ•˜๊ณ  ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•˜๊ณ  ์˜คํ”ˆ ์†Œ์Šค์—์„œ ์‚ฌ๋žŒ๋“ค์„ ๋•๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค.

๋นŒ๋“œ ํŒŒ์ดํ”„๋ผ์ธ์—์„œ JEST ํ…Œ์ŠคํŠธ ์†๋„๋ฅผ ๋†’์ด๊ธฐ ์œ„ํ•ด ์ˆ˜ํ–‰ํ•œ ํ•œ ๊ฐ€์ง€๋Š” ๋‹จ์ผ ์ฝ”์–ด ์‹œ์Šคํ…œ์„ ๋‹ค์ค‘ ์ฝ”์–ด ์‹œ์Šคํ…œ์œผ๋กœ ๊ต์ฒดํ•˜๋Š” ๊ฒƒ์ž…๋‹ˆ๋‹ค. ๊ธฐ๋ณธ์ ์œผ๋กœ jest๋Š” ์‚ฌ์šฉ ๊ฐ€๋Šฅํ•œ ํ•˜๋“œ์›จ์–ด ์Šค๋ ˆ๋“œ ์ˆ˜๋งŒํผ ์ž‘์—…์ž๋ฅผ ์ƒ์„ฑํ•ฉ๋‹ˆ๋‹ค. ์ด๊ฒƒ์ด ๊ฐ€๋Šฅํ•˜์ง€ ์•Š์€ ๊ฒฝ์šฐ '-w'(maxWorkers)๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์ˆ˜๋™์œผ๋กœ ์žฌ์ƒํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ๋‹จ์ผ ์ฝ”์–ด์—์„œ๋„ ์†๋„ ํ–ฅ์ƒ์„ ์–ป์„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

๊ถ๊ทน์ ์œผ๋กœ ์šฐ๋ฆฌ๋Š” ๋ชจ์˜ ๋ชจ๋“ˆ์ด ๋งค์šฐ ๋น„์šฉ์ด ๋งŽ์ด ๋“ค๊ณ (์œ„์˜ ๋‚ด ์„ค๋ช… ์ฐธ์กฐ) ๋Œ€๋ถ€๋ถ„์˜ ์‹คํ–‰ ์‹œ๊ฐ„์„ ์œ ๋ฐœํ•œ๋‹ค๋Š” ๊ฒƒ์„ ๋ฐœ๊ฒฌํ–ˆ์Šต๋‹ˆ๋‹ค.

๋‚˜๋ฅผ ์œ„ํ•ด es6์„ ์‚ฌ์šฉํ•˜๋Š” Jest๋Š” ์™„์ „ํžˆ ์‚ฌ์šฉํ•  ์ˆ˜ ์—†์Šต๋‹ˆ๋‹ค. ์‹œ์ž‘ํ•˜๋Š” ๋ฐ๋งŒ 10์ดˆ ์ด์ƒ์ด ๊ฑธ๋ฆฌ๊ณ  ํ˜„์žฌ ๊ฐ€์ง€๊ณ  ์žˆ๋Š” ๋‹จ์ผ ํ…Œ์ŠคํŠธ๋ฅผ ์‹คํ–‰ํ•˜๋Š” ๋ฐ 2์ดˆ๊ฐ€ ๊ฑธ๋ฆฝ๋‹ˆ๋‹ค. ๋‚˜๋Š” ์นด๋ฅด๋งˆ๋กœ ๋‹ค์‹œ ์ „ํ™˜ํ•˜์—ฌ ํ›จ์”ฌ ๋” ๋งŽ์€ ๊ฒƒ์„ ๊ธฐ๋Œ€ํ–ˆ์Šต๋‹ˆ๋‹ค :(

์šฐ๋ฆฌ๋Š” ํ˜„์žฌ node-haste๋ฅผ ์ด ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•ด์•ผ ํ•˜๋Š” ์ƒˆ๋กœ์šด ๋ชจ๋“ˆ ํ•ด์„๊ธฐ๋กœ ๊ต์ฒดํ•˜๊ธฐ ์œ„ํ•ด ๋…ธ๋ ฅํ•˜๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค.

์•ˆ๋…• ๋ชจ๋‘. ์ด ๋ฌธ์ œ์— ๋Œ€ํ•œ ์†Œ์‹์ด ์žˆ์Šต๋‹ˆ๊นŒ?

์•ˆ๋…•ํ•˜์„ธ์š”, Jest๋Š” ๋น„ React ํ…Œ์ŠคํŠธ์— ์ ํ•ฉํ•ฉ๋‹ˆ๊นŒ? ์šฐ๋ฆฌ ํŒ€์—์„œ ๋ฐ˜์‘ ์•ฑ๊ณผ ๋ฐ˜์‘ํ•˜์ง€ ์•Š๋Š” ์•ฑ ๋ชจ๋‘์— ๋Œ€ํ•œ ๊ณตํ†ต ํ‘œ์ค€์„ ๊ฐ–๊ณ  ์‹ถ์Šต๋‹ˆ๋‹ค.

Jest๋Š” ๋ณดํŽธ์ ์ธ ํ…Œ์ŠคํŠธ ์‹คํ–‰๊ธฐ์ด๋ฉฐ React๋ฅผ ์‚ฌ์šฉํ•  ํ•„์š”๊ฐ€ ์ „ํ˜€ ์—†์Šต๋‹ˆ๋‹ค. :) ์˜ˆ์ œ ์ค‘ ํ•˜๋‚˜๋ฅผ ์‚ดํŽด๋ณด์‹ญ์‹œ์˜ค!

์•ˆ๋…•ํ•˜์„ธ์š” ์—ฌ๋Ÿฌ๋ถ„, ์—ฌ๊ธฐ์— ๋ช‡ ๊ฐ€์ง€ ํฅ๋ฏธ๋กœ์šด ์ •๋ณด๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค. ๋˜ํ•œ ํ…Œ์ŠคํŠธ๊ฐ€ ๋Š๋ฆฌ๊ฒŒ ์‹คํ–‰๋˜๋Š” ๋ฌธ์ œ๋„ ๊ฒช๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ํ˜„์žฌ ์‹คํ–‰ํ•˜๋Š” ๋ฐ ~15์ดˆ๊ฐ€ ๊ฑธ๋ฆฌ๋Š” 13๊ฐœ์˜ ํ…Œ์ŠคํŠธ๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค.

์ €๋Š” packages.json ํŒŒ์ผ์— "testPathDirs": ["<rootDir>/path/to/tests/"] ๋ฅผ ์ถ”๊ฐ€ํ•˜๋Š” ๊ฒƒ์ด ์‹œ์ž‘ ์‹œ๊ฐ„์„ ์ƒ๋‹นํžˆ ๊ฐœ์„ ํ•˜๋Š” ๋ฐ ๋„์›€์ด ๋œ๋‹ค๋Š” ๊ฒƒ์„ ๋ฐœ๊ฒฌํ–ˆ์Šต๋‹ˆ๋‹ค.

@cpojer ์ƒˆ๋กญ๊ณ  ํ–ฅ์ƒ๋œ ๋ชจ๋“ˆ ๋ฆฌ์กธ๋ฒ„์— ๋Œ€ํ•œ ์—…๋ฐ์ดํŠธ๊ฐ€ ์žˆ์Šต๋‹ˆ๊นŒ? ์ด๊ฒƒ์ด ํ…Œ์ŠคํŠธ๋ฅผ ํ›จ์”ฌ ๋” ๋น ๋ฅด๊ฒŒ ์‹คํ–‰ํ•˜๋Š” ์—ด์‡ ๊ฐ€ ๋˜๊ธฐ๋ฅผ ์ง„์‹ฌ์œผ๋กœ ๋ฐ”๋ž๋‹ˆ๋‹ค.

์ด ์ž‘์—…์€ #599์—์„œ ์ง„ํ–‰๋ฉ๋‹ˆ๋‹ค.

@cpojer ๊ฐ์‚ฌ
์™„์„ฑ๋œ Haste2๋ฅผ ๊ธฐ๋Œ€ํ•ฉ๋‹ˆ๋‹ค

๋ชจ์นด๋ฅผ ์‚ฌ์šฉํ•œ ๋™์ผํ•œ ํ…Œ์ŠคํŠธ๊ฐ€ 44ms๋กœ ์‹คํ–‰๋˜์—ˆ์œผ๋ฉฐ ๋†๋‹ด์ด 6์ดˆ๊ฐ€ ๊ฑธ๋ ธ์Šต๋‹ˆ๋‹ค.

jest ๋ฅผ ์‚ฌ์šฉํ•˜์—ฌ ์ดˆ๊ธฐ 6๊ฐœ์˜ ํ…Œ์ŠคํŠธ ํŒŒ์ผ์„ Mocha , jsdom ๋ฐ sinon ์‚ฌ์šฉ์œผ๋กœ ์ „ํ™˜ํ•˜๋Š” ๋ฐ ์•ฝ 15๋ถ„์ด ๊ฑธ๋ ธ์Šต๋‹ˆ๋‹ค.

์ข‹์€ ์†Œ์‹์ž…๋‹ˆ๋‹ค. ์˜ค๋Š˜ #599๋ฅผ ๋ณ‘ํ•ฉํ•˜๊ณ  ๋งˆ์นจ๋‚ด ๋Š๋ฆฐ ์‹œ์ž‘์„ ์—†์• ์•ผ ํ•ฉ๋‹ˆ๋‹ค.

์ข‹์•„, ์ด๊ฒƒ์€ Jest 0.9์—์„œ ๋งˆ์นจ๋‚ด ์ˆ˜์ •๋˜์–ด์•ผ ํ•œ๋‹ค. ์‹œ๊ฐ„์ด ์˜ค๋ž˜ ๊ฑธ๋ ค์„œ ์ฃ„์†กํ•˜์ง€๋งŒ Jest์—๋Š” ์•ฝ๊ฐ„์˜ ๊ด‘๋Œ€๊ฐ€์žˆ์—ˆ์Šต๋‹ˆ๋‹ค :)

React ํ…Œ์ŠคํŠธ ์ž์ฒด์˜ ์†๋„๋ฅผ ๋†’์ด๋Š” ๋ฐฉ๋ฒ•์€ https://github.com/facebook/react/pull/6052 ๋ฅผ ์ฐธ์กฐ jest-cli@next ๋กœ ํƒœ๊ทธ๊ฐ€ ์ง€์ •๋˜์–ด ์žˆ์Šต๋‹ˆ๋‹ค. ํ•ด๊ฒฐ๋˜๋Š” ๋Œ€๋กœ ์ด ๋ฌธ์ œ๋ฅผ ์ข…๋ฃŒํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.

npm install jest-cli@next ์ด ์ƒˆ ๋ฒ„์ „์„ ์‹คํ–‰ํ•˜๋ ค๋Š” ๊ฒฝ์šฐ( jest@next @cpojer ๋Œ€์‹ )

์˜ค ์˜ˆ, ํ•ญ์ƒ์ด ์‹ค์ˆ˜๋ฅผํ•ฉ๋‹ˆ๋‹ค :) ์›๋ž˜ ์˜๊ฒฌ์„ ์ˆ˜์ •ํ–ˆ์Šต๋‹ˆ๋‹ค.

npm install jest-cli@next ์‚ฌ์šฉํ•˜์—ฌ ์—…๊ทธ๋ ˆ์ด๋“œํ•œ ํ›„ @cpojer dontMock ์ง€์ •ํ•˜๋Š” ๋ฐ ๋ฌธ์ œ๊ฐ€ ์žˆ์Šต๋‹ˆ๋‹ค. ์ฆ‰, ์—…๋ฐ์ดํŠธ ์ „์—([email protected] ์‚ฌ์šฉ) ์ด ์ค„์ด ์ œ๋Œ€๋กœ ์ž‘๋™ํ•ฉ๋‹ˆ๋‹ค.

jest.dontMock('../../../../fixtures');

๊ทธ๋Ÿฐ ๋‹ค์Œ 0.9.0์œผ๋กœ ์—…๋ฐ์ดํŠธํ•œ ํ›„ ๋™์ผํ•œ ํ˜ธ์ถœ๋กœ ์ธํ•ด ๋ชจ๋“ˆ์ด ์กฐ๋กฑ๋ฉ๋‹ˆ๋‹ค.

@steinbachr ์•„๋งˆ๋„ ๋ณ„๋„์˜ ๋ฌธ์ œ๋กœ ๊ฐ€์•ผํ•ฉ๋‹ˆ๋‹ค. ์žฌํ˜„์„ ์ œ๊ณตํ•  ์ˆ˜ ์žˆ๋‹ค๋ฉด ์ข‹์„ ๊ฒƒ์ž…๋‹ˆ๋‹ค. ์ด ๋ฌธ์ œ๊ฐ€ FB์— ์˜ฌ๋ผ์˜ค๋Š” ๊ฒƒ์„ ๋ณธ ์ ์ด ์—†์Šต๋‹ˆ๋‹ค!

๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค @cpojer , ์—ฌ๊ธฐ์—์„œ ์ƒ์„ฑ๋œ ๋ฌธ์ œ

์ด ํŽ˜์ด์ง€๊ฐ€ ๋„์›€์ด ๋˜์—ˆ๋‚˜์š”?
0 / 5 - 0 ๋“ฑ๊ธ‰