【问题标题】:React+Reflux: Passing Variables to Data StoresReact+Reflux:将变量传递给数据存储
【发布时间】:2015-02-20 19:26:33
【问题描述】:

我正在构建一个 React+Reflux 应用程序,除其他外,它允许创建/删除/编辑类别。到目前为止,我能够显示所有类别并通过关联的存储和操作在 React 组件中处理类别的创建/删除。这一切都很好,更新数据库并按预期重新渲染组件。我的症结在于试图深入到特定的现有类别以对其进行编辑。

认为我需要以某种方式将类别 ID 传递给商店,然后商店将通过 ajax 调用将其传递给 php/sql 查询,以便获取/设置特定于该特定的数据类别。如果我完全绕过商店并将ajax调用放在组件本身中,我可以通过带有React-router的url参数让它工作(当然没有自动重新渲染)但我无法弄清楚如何通过商店做到这一点。

换句话说,这或多或少有效:

  • “ManageCategories”React 组件使用 CategoryStore 列出所有类别,每个类别都包含在一个锚标记中,该锚标记将类别 ID 传递给“ManageCategory”路由/组件
  • “ManageCategory”组件在其 getInitialState 方法的 ajax 调用中直接使用类别 ID 参数来显示特定于类别的数据

但是,我认为下面是更正确的 Reflux 方法,但我不确定如何让它发挥作用:

  • “ManageCategories”组件同上
  • “ManageCategory”组件以某种方式将其类别 ID 参数传递给 CategoryStore(或者可能是不同的“IndividualCategoryStore”?),该组件仅返回特定于该类别的数据并处理对该类别的更新/编辑

我能够通过向 CategoryStore 添加一个新方法(“getCategoryData”)来获得这种工作的一种笨重版本,该方法在“ManageCategory”组件的 getInitialState 方法中调用并传递 categoryId 参数。这会导致所有类别(来自 CategoryStore 的 getDefaultData)的闪烁,然后是正确的单个类别列表(来自组件的 getInitialState)。

我对 React+Reflux 背后的概念感到相当满意,但在这一点上,我认为我可能误解了一些基本的东西。在这个特定问题上工作了一个多星期,但我发现的示例/教程/文档都没有解决将变量传递到数据存储的具体问题。

动作:

var Actions = Reflux.createActions([
"createCategory",
"deleteCategory",
"editCategory"
]);

分类商店:

var CategoryStore = Reflux.createStore({
listenables: [Actions],
onCreateCategory: function(catName) {
    // ajax call to create new category that calls updateCategories on success
},
onDeleteCategory: function(catId) {
    // ajax call to delete category that calls updateCategories on success
},
updateCategories: function(){
    $.ajax({
        url: url + '?action=getAllCategories',
        async: false,
        dataType: 'json',
        success: function(categoryData) {
            this.categories = categoryData;
        }.bind(this),
        error: function(xhr, status, err) {
            console.error(url, status, err.toString());
        }.bind(this)
    });
    this.trigger(this.categories);
},
getDefaultData: function() {
    $.ajax({
        url: url + '?action=getAllCategories',
        async: false,
        dataType: 'json',
        success: function(categoryData) {
            this.categories = categoryData;
        }.bind(this),
        error: function(xhr, status, err) {
            console.error(url, status, err.toString());
        }.bind(this)
    });
    return this.categories;
}
});

类别组件:

var Category = React.createClass({
handleDeleteCategory: function() {
    Actions.deleteCategory(this.props.id);
},
render: function() {
    return (
        <li className="category">
            <IconButton icon="action-highlight-remove" onClick={this.handleDeleteCategory} />
            <h5><a href={"/#/manage-category/" + this.props.id}>{this.props.name} ({this.props.id})</a></h5>
        </li>
    );
}
});

ManageCategories 组件:

var ManageCategories = React.createClass({
mixins: [
    Reflux.connect(CategoryStore, "categories")
],
getInitialState: function() {
    return {
        categories: []
    };
},
handleCreateCategory: function() {
    // category creation code
},
render: function() {
    var categoryNodes = this.state.categories.map(function(category) {
        return (
            <Category name={category.name} id={category.id} />
        )
    });
    return (
        <div className="dev-tools-container">
            <h1>Developer Tools</h1>
            <div className="categories">
                <h3>Categories</h3>
                <ul>
                    {categoryNodes}
                </ul>
                <h4>Create New Category:</h4>
                <form>
                    <label htmlFor="new-category-name">Category Name</label> <input type="text" id="new-category-name" /><br />
                    <PaperButton label="Create" primary={true} onClick={this.handleCreateCategory} />
                </form>
            </div>
        </div>
    );
}
});

提前感谢您提供任何见解或帮助。

【问题讨论】:

    标签: reactjs refluxjs


    【解决方案1】:

    最终在这里发布我的问题后,我想我可能已经弄清楚我一直误入歧途了。我正在考虑将类别 ID 传递给商店以过滤其中的数据,而我真正需要做的就是从商店中获取完整的数据集合并在组件中选择性地使用它。

    因此,一旦将 catId 作为 url 参数传递到 ManageCategory 组件,我需要做的就是根据 catId 过滤数据。

    例如,在 ManageCategory 组件中,我可以使用 lodash 过滤和提取当前类别的名称值,如下所示。根本不需要编辑 CategoryStore 中存储的数据集合。

    var ManageCategory = React.createClass({
    mixins: [
        Reflux.connect(CategoryStore, "categoryData")
    ],
    getInitialState: function() {
        return {
            categoryData: []
        };
    },
    render: function() {
        var categoryName = _.chain(this.state.categoryData)
                            .filter({"id": this.props.params.catid})
                            .pluck("name");
    
        return (
            <div className="category-container">
                <h1>{categoryName}</h1>
            </div>
        );
    }
    });
    

    如果有更好的方法,请随时告诉我,但现在这正是我所需要的。希望所有这些内容对其他人也有帮助。

    【讨论】:

    • 这种数据操作在组件内部似乎不合适。您可以将该责任转移到商店并让您的组件使用给定的catId 触发操作。商店可以使用catId 来检索您的组件将根据...呈现的数据,然后您的组件代码不会与数据格式紧密耦合。
    • 或者甚至可能只是您商店中的一个帮助方法来为您获取这些数据。似乎您想在路由器和控制器视图之间放置一个缓冲区,以便您可以处理此数据操作,因为您必须为应用程序中的每个页面/控制器视图执行类似的操作。
    • 但是如果不同的组件以不同的方式从存储中获取数据怎么办?我认为这是一个非常糟糕的设计
    • 您的“列表”中可能只有每条记录的数据摘要,当您选择一个时,它需要关闭才能获取其余记录。这应该在您过滤之前首先发生吗?
    猜你喜欢
    • 2011-09-15
    • 1970-01-01
    • 1970-01-01
    • 2020-12-27
    • 2015-04-13
    • 1970-01-01
    • 2015-12-20
    • 2023-01-09
    • 2012-05-16
    相关资源
    最近更新 更多