首页 > 解决方案 > 为什么我的 ASP.NET CORE React Redux 应用程序中的记录没有更新?

问题描述

我是 React with Redux 的新手,我一直在开发一个新的 Web 应用程序,它有一些基本的 crud 操作。我正在使用带有存储库模式的 ASP.NET Core 构建它。

我的应用程序正确显示数据,我也可以正确添加数据,我遇到的问题是更新我的数据不起作用。在将数据传递到控制器时,您可以看到参数中的更改,一旦我尝试提交它不会更新的数据。

我的项目设置如下,我缩短了它的某些部分,只包含我正在使用的组件。

Shelly.Data
    |-BaseEntity.cs
    |-Vessel.cs

Shelly.Repo
    |-IRepository.cs
    |-Repository.cs
    |-ShellyContext.cs

Shelly.Services
    |-IVesselService.cs
    |-VesselService.cs

Shelly.UI
    |-ClientApp
        |-src
            |-components
                |-vessels
                    |-VesselsComponent.js
            |-store
                |-Vessels.js

我已经在这个问题中包含了我的存储库中的代码,因为我不相信问题出在我的 React 设置上,但也许有人可以帮助我解决这个问题。

回购/IRepository.cs

public interface IRepository<TEntity> where TEntity : BaseEntity
{
    IEnumerable<TEntity> GetAll();
    TEntity Get(long id);
    void Insert(TEntity entity);
    void Update(TEntity entity);
    void Delete(TEntity entity);
    void Remove(TEntity entity);
    void SaveChanges();
}

回购/Repository.cs

public class Repository<TEntity> : IRepository<TEntity> where TEntity : BaseEntity
{
    private readonly ShellyContext _dbContext;
    private DbSet<TEntity> entities;
    string errorMessage = string.Empty;

    public Repository(ShellyContext context)
    {
        this._dbContext = context;
        entities = context.Set<TEntity>();
    }

    ...

    public void Update(TEntity entity)
    {
        if (entity == null)
        {
            throw new ArgumentNullException("entity");
        }
        _dbContext.SaveChanges();
    }
    public void SaveChanges()
    {
        _dbContext.SaveChanges();
    }

    ...

}

服务/IVesselService

public interface IVesselService
{
    IEnumerable<Vessel> GetVessels();
    Vessel GetVessel(long id);
    void InsertVessel(Vessel vessel);
    void UpdateVessel(Vessel vessel);
    void DeleteVessel(long id);
}

服务/船舶服务

public class VesselService : IVesselService
{
    private IRepository<Vessel> vesselRepository;

    public VesselService(IRepository<Vessel> vesselRepository)
    {
        this.vesselRepository = vesselRepository;
    }
    public void UpdateVessel(Vessel vessel)
    {
        vesselRepository.Update(vessel);            
    }
}

下一部分是控制器,它从 react 调用以执行 CRUD 操作并将数据提供给 API。读取和添加似乎有效,但更新无效,您可以看到更新的数据正在传入,vessel但它似乎没有提交,只是用旧数据刷新。

控制器/VesselDataController.cs

[Route("api/[controller]")]
public class VesselDataController : Controller
{
    private readonly IVesselService vesselService;
    public VesselDataController(IVesselService vesselService)
    {
        this.vesselService = vesselService;
    }

    ...


    [HttpPost]
    public ActionResult AddVessel([FromBody]Vessel vessel)
    {
        vesselService.InsertVessel(vessel);
        return Ok(new
        {
            success = true,
            returncode = "200"
        });
    }

    [HttpPut]
    public ActionResult Update([FromBody]Vessel vessel)
    {
        vesselService.UpdateVessel(vessel);    
        return Ok(new
        {
            success = true,
            returncode = "200"
        });
    }
}

这是我的 React/Redux 配置的代码。同样,我只包含了我的相关组件的代码。

ClientApp/src/components/VesselsComponent.js

import React, { Component } from 'react';
import { bindActionCreators } from 'redux';
import { connect } from 'react-redux';
import { actionCreators } from '../../store/Vessels';

class VesselsComponent extends Component {

    state = {
        name: "",
        imo: "",
        editing: ""
    };

    componentWillMount() {
        this.props.requestVessels();
    }

    toggleEditing(itemId) {
        console.log("Editing" +  ' ' + itemId);
        this.setState({ editing: itemId });
    }

    handleVesselUpdate(vessel) {         
        this.props.updateVessel(vessel);
        setTimeout(this.props.requestVessels, 600);
    }

    handleEditItem() {
        let itemId = this.state.editing;        
        var editVessel = this.props.vessels.find((v) => v.Id === itemId);        

        editVessel.IMO = this.refs[`IMO_${itemId}`].value;
        editVessel.AddedDate = this.refs[`AddedDate_${itemId}`].value;
        editVessel.ModifiedDate = this.refs[`ModifiedDate_${itemId}`].value;        

        this.handleVesselUpdate(editVessel);        
        this.setState({ editing: "" });
    }

    renderItemOrEditField(vessel) {
        if (this.state.editing === vessel.Id) {
            return (
                <tr key={vessel.Id}>
                    <td>{vessel.Name}</td>
                    <td>{vessel.IMO}</td>
                    <td>
                        <input onKeyDown={this.handleEditField} type="text" ref={`IMO_${vessel.Id}`} name="IMO" defaultValue={vessel.IMO} />
                        <input onKeyDown={this.handleEditField} type="text" ref={`AddedDate_${vessel.Id}`} name="AddedDate" defaultValue={vessel.AddedDate} />
                        <input onKeyDown={this.handleEditField} type="text" ref={`ModifiedDate_${vessel.Id}`} name="ModifiedDate" defaultValue={vessel.ModifiedDate} />
                    </td>
                    <td>
                        <button onClick={this.handleEditItem.bind(this)} label="Update Item">Update</button>
                    </td>
                </tr>
        )
    } else {
        return (
            <tr key={vessel.Id}>
                <td>{vessel.Name}</td>
                <td>{vessel.IMO}</td>
                <td><button onClick={this.toggleEditing.bind(this, vessel.Id)} className="btn btn-info">Edit</button></td>
            </tr>);
    }
}

renderVesselsTable(props) {
    return (
        <table className="table">
            <thead className="thead-dark">
                <tr>
                    <th>Name</th>
                    <th>IMO</th>
                    <th>Actions</th>
                </tr>
            </thead>
            <tbody>
                {props.vessels.map(vessel =>
                    this.renderItemOrEditField(vessel)
                )}
            </tbody>
        </table>
    )
}

render() {
    return (
        <div>
            <h3>Vessels</h3>                
            {this.renderVesselsTable(this.props)}

            <table className="table">
                <thead className="thead-dark">
                </thead>
                <tbody>
                    <tr>
                        <td>Name:</td>
                        <td>
                            <input className="form-control" id="vesselName" type="text" value={this.state.name} onChange={(ev) => this.setState({ name: ev.target.value })} />
                        </td>
                    </tr>
                    <tr>
                        <td>IMO:</td>
                        <td>
                            <input className="form-control" id="vesselImo" type="text" value={this.state.imo} onChange={(ev) => this.setState({ imo: ev.target.value })} />
                        </td>
                    </tr>
                    <tr>
                        <td>
                            <button className="btn btn-default btn-success" onClick={this.addVessel.bind(this)}>Add Vessel</button>
                        </td>
                    </tr>
                </tbody>
            </table>
        </div>
        );
    }
} 

export default connect(
    state => state.vessels,
    dispatch => bindActionCreators(actionCreators, dispatch)
)(VesselsComponent);

最后,这是Vessel.js来自store.

const requestVesselsType = 'REQUEST_VESSELS';
const receiveVesselsType = 'RECEIVE_VESSELS';
const requestVesselType = 'REQUEST_VESSEL';
const receiveVesselType = 'RECEIVE_VESSEL';
const addVesselType = 'ADD_VESSEL';
const updateVesselType = "UPDATE_VESSEL";
const initialState = { vessels: [], vessel: {}, isLoading: false };

let currentvessel = {};

export const actionCreators = {
    requestVessels: () => async (dispatch, getState) => {
        dispatch({ type: requestVesselsType });

        const url = 'api/VesselData/GetVessels';
        const response = await fetch(url);
        const allvessels = await response.json();

        dispatch({ type: receiveVesselsType, allvessels });
    },
    requestVessel: () => async (dispatch, getState) => {
        dispatch({ type: requestVesselType });

        const url = 'api/VesselData/GetVessel/${id}';
        const response = await fetch(url);
        const vessel = await response.json();

        dispatch({ type: receiveVesselType, vessel });
    },        
    updateVessel: (vessel) => async (dispatch, getState) => {
        const baseURL = "/api/VesselData";
        const data = JSON.stringify({
            Id: vessel.Id,
            Name: vessel.Name,
            IMO: vessel.IMO,
            ModifiedDate: vessel.ModifiedDate,
            AddedDate: vessel.AddedDate
        });
        const fetchTask = fetch(baseURL, {
            method: "PUT",
            headers: {
                Accept: "application/json",
                "Content-Type" : "application/json",
            },
            body: data
        })
            .then((data => {
                dispatch({ type: updateVesselType, vessel: data })
            }))

    }
}
export const reducer = (state, action) => {
    state = state || initialState;

    if (action.type === requestVesselsType) {
        return {
            ...state,
            isLoading: true
        };
    }
    if (action.type === receiveVesselsType) {
        return {
            ...state,
            vessels: action.allvessels,
            isLoading: false
        }
    }
    if (action.type === requestVesselType) {
        return {
            ...state,
            isLoading: true
        };
    }
    if (action.type === receiveVesselType) {
        currentvessel = action.vessel;
        return {
            ...state,
            vessel: currentvessel,
            isLoading: false
        }
    }       
    if (action.type === updateVesselType) {
        return {
            ...state,
            isLoading: false
        };
    }

    return state;
};

所以,这是我的应用程序,它是基本的,我仍在学习,但我看不出更新方法缺少提交的任何合乎逻辑的原因。上下文的保存在存储库中处理,我知道它会命中它并且没有记录更新。谁能帮我理解我哪里出错了?

标签: javascriptasp.net-corereact-redux

解决方案


如果您的问题包含完整的代码,我相信问题出在您的存储库更新方法中。它什么也没做。

public void Update(TEntity entity)
 {
     if (entity == null)
     {
        throw new ArgumentNullException("entity");
     }
     _dbContext.SaveChanges();
 }

您需要将要更新的对象附加到DbContext. 您可以使用DbContext.Update方法做到这一点

尝试Update之前打电话SaveChanges,像这样

public void Update(TEntity entity)
{
  if (entity == null)
  {
    throw new ArgumentNullException("entity");
  } 

  _dbContext.Update(entity);   //add this line
  _dbContext.SaveChanges();
}

推荐阅读