我正在尝试开发一个 API,它将采用一些电影名称作为 ViewModel 的一部分,并将在 DTO 中设置相应的电影 ID。
TBL_Movies 的表格表示(例如我只使用了 5 个数据,但实际上很少):
ID MovieName
1 Indiana Jones
2 John Wick
3 James Bond
4 Wolverine
The table representation for TBL_Transact:
Tab_ID MovieID1(int) MovieID2(int) MovieID3(int) MovieID4(int)
1 NULL NULL NULL NULL
ViewModel 结构:
{
Tab_ID: int,
MovieName1: "John Wick",
MovieName2: "Wolverine",
MovieName3: "Cast Away",
MovieName4: "A-Team" // this doesn't exist in TBL_Movies and so it will return exception to the client
}
上面的 ViewModel 将被传递到 API PUT 端点,现在我需要获取各个 ViewModel 字段的相应 MovieID 并将它们存储在 DTO 中。
DTO(MovieDetailUpdateDto)结构:
{
Tab_ID: int,
MovieName1: string,
MovieName2: string,
MovieName3: string,
MovieName4: string,
MovieID1: int,
MovieID2: int,
MovieID3: int,
MovieID4: int
}
因此,DTO 将在 MovieID1 中存储电影 ID,作为字段 MovieName1 中提到的电影的 ID,依此类推。
例如: DTO.MovieID1 将存储 2(因为“John Wick”在 MovieName1 中)。
我不想调用数据库 5 次或更多次来获取 ID。所以,我想到使用 SQL IN 运算符,并且由于我使用 EF-LINQ,所以做了这样的事情:
var movieDetailUpdateDto = _mapper.Map<MovieDetailUpdateDto>(ViewModel);
var customMovieValuesList = typeof(MovieDetailUpdateDto).GetProperties().Where(x => x.Name.ToLower().Contains("moviename")).ToList().Select(x => x.GetValue(movieDetailUpdateDto));
上面的语句给了我一个电影名称列表,但我无法理解具体名称是哪个字段。
例如: 如果列表中的值“John Wick”适用于字段 MovieName1 或 MovieName2 或任何其他 MovieName 字段。
所以,我认为使用字典我可以存储字段名及其值。但是,不确定它将如何工作或是否有效?
其次,是否可以使用 LINQ 在 SQL IN 运算符中使用“customMovieValuesList”?
第三,如何使用 LINQ 将这些 MovieID 分配回 DTO 到各自的字段中?
另外,请建议是否可以使用 SQL 连接来实现相同的目的。
我一直尝试使用 LINQ 来避免多次数据库调用。最后,它对我来说工作得很好。如果有人想分享其他出路,也很乐意遵循。
希望解决方案可以帮助某人:)
public async Task<MovieDetailDtoBase?> UpdateMovieValuesAsync(int movieId, MovieDetailUpdateViewModel movieDetailUpdateViewModel) {
var movieDetailUpdateDto = _mapper.map<MovieDetailUpdateDto>(movieDetailUpdateViewModel);
// The below linq query loops through all the properties of the
// movieDetailUpdateDto and gets back the property name and its value as
// provided in the DTO, filtering out the null values and empty strings,
// converting into an anonymous list.
var moviesKeyValuesList = (typeof(movieDetailUpdateDto).GetProperties()
.Where(p => p.Name.ToLower().Contains("moviename")).ToList()
.Where(p => p.GetValue(movieDetailUpdateDto) != null)
.Select(t => new { FieldName = t.Name, FieldValue = t.GetValue(movieDetailUpdateDto)?.ToString() })
.Where(r => r.FieldValue != string.Empty)
.ToList()
);
}
感谢大家的支持。