如何在服务器端的React中访问JSX组件的DOM事件处理程序

Tok*_*ans 10 javascript jsx node.js reactjs

我正在使用React构建一个简单的静态视图引擎,其目标是呈现静态HTML标记并生成一个填充了组件DOM事件(onClick等)的js文件.

我正在做第一部分的方式是需要一个指定的JSX文件,例如,如下所示:

import React from 'React';

export default class Test extends React.Component {

    clicked() {
        alert('Clicked the header!');
    }

    render() {
        return (
            <html>
                <head>
                    <title>{this.props.title}</title>
                </head>
                <body>
                    <h1 onClick={this.clicked}>click me!!!</h1>
                </body>
            </html>
        );
    }
}
Run Code Online (Sandbox Code Playgroud)

然后我通过NodeJS-backend渲染JSX文件,如下所示:

let view = require('path-to-the-jsx-file');
view = view.default || view;

const ViewElement = React.createFactory(view);
let output = ReactDOMServer.renderToStaticMarkup(ViewElement(props));
Run Code Online (Sandbox Code Playgroud)

它非常适合提供静态HTML.但我想知道是否有办法在数组或其他东西中访问JSX文件中使用的所有组件,然后我可以使用它来检查绑定的事件和哪些处理程序.

那么在这个例子中,能够得到<h1>-tag的onClick-handler?这有可能以某种方式吗?

Tok*_*ans 2

经过一番折腾后,我想出了一个效果很好的解决方案。

如果我创建自己想要渲染的实例ReactElement(在示例中ViewElement(props)),那么我可以使用它的标准render函数渲染该元素:

let element = ViewElement(props);
let instance = new element.type();
let render = instance.render();
Run Code Online (Sandbox Code Playgroud)

从这里我可以浏览该元素的所有属性,因此,onClick-handlers 将位于render.props.

所以我要做的就是检查每个 prop 的键是否与反应事件名称匹配(例如 onClick、onDragEnd、onDragEnter 等)。如果是这样,并且该属性的值是函数类型 - 我有事件名称及其处理函数:

Object.keys(render.props).map((key) => {
    if (bigArrayOfAllTheEventNames.indexOf(key) !== -1) {
        item.events[key] = render.props[key];//check if type is function.
    }
});
Run Code Online (Sandbox Code Playgroud)

然后,我还递归render.props.children地迭代以到达其所有子组件,并将每个具有事件的组件添加到数组中。

剩下的唯一问题是我需要一种方法将渲染的 DOM 字符串绑定到我现在拥有的 javascript 处理程序。为此,我添加了使用自定义 DOM 属性的需要,然后可以使用该属性来 ID 组件,如下所示

$("[data-id=value]").on({event-name}, {it's JS-handler})

它可能还不完美,但我认为这是最好的解决方案。