【发布时间】:2018-06-08 15:51:33
【问题描述】:
我正在开发一个拍卖应用程序,我正在创建一种方法,以便管理员可以提交一个 Excel 电子表格,该电子表格将创建一个新的拍卖并将其存储在数据库中。所以首先我创建了一个类(模型)Uploadfile,如下所示:
[NotMapped]
public class UploadFile
{
[Required]
public HttpPostedFileBase ExcelFile { get; set; }
}
我使用NotMapped 是因为我试图了解如何创建和使用未存储在我的数据库中的模型,这就是我的问题和误解所在。
我创建了一个控制器,这是我手动完成的,因为 UploadFile 不是具有这样键的实体:
public class FileUploadsController : Controller
{
private AuctionEntities db = new AuctionEntities();
// GET: FileUploads
public ActionResult Index()
{
UploadFile UploadFile = new UploadFile();
return View(UploadFile);
}
[HttpPost]
public ActionResult Index(UploadFile UploadFile)
{
if (ModelState.IsValid)
{
if (UploadFile.ExcelFile.ContentLength > 0)
{
if (UploadFile.ExcelFile.FileName.EndsWith(".xlsx") || UploadFile.ExcelFile.FileName.EndsWith(".xls"))
{
XLWorkbook wb;
// in case if the file is corrupt
try
{
wb = new XLWorkbook(UploadFile.ExcelFile.InputStream);
}
catch (Exception ex)
{
ModelState.AddModelError(String.Empty, $"Check your file. {ex.Message}");
return View();
}
IXLWorksheet ws = null;
try // in case the sheet you are looking for is not found
{
ws = wb.Worksheet("sheet1");
}
catch
{
ModelState.AddModelError(String.Empty, "Sheet not found");
return View();
}
var firstRowUsed = ws.FirstRowUsed();
var auctionRow = firstRowUsed.RowUsed().RowBelow();
// create auction
string auctionName = auctionRow.Cell(1).Value.ToString();
DateTimeOffset startDate = DateTimeOffset.Parse(auctionRow.Cell(2).Value.ToString());
DateTimeOffset endDate = DateTimeOffset.Parse(auctionRow.Cell(3).Value.ToString());
string folderName = auctionRow.Cell(4).Value.ToString();
Models.Auction auction = new Models.Auction(auctionName, startDate, endDate, folderName);
db.Auctions.Add(auction);
// find the next table
var nextRow = auctionRow.RowBelow();
while (nextRow.IsEmpty())
{
nextRow = nextRow.RowBelow();
}
const int catNameCol = 1;
var catRow = nextRow.RowUsed().RowBelow();
// get categories from ws table and add to the auction
while (!catRow.Cell(catNameCol).IsEmpty())
{
string catName = catRow.Cell(1).Value.ToString();
int seqNo = Convert.ToInt32(catRow.Cell(2).Value.ToString());
string fileName = catRow.Cell(3).Value.ToString();
Cat cat = new Cat(auction.AuctionId, catName, seqNo, fileName);
auction.Cats.Add(cat);
catRow = catRow.RowBelow();
}
var findNextRow = catRow.RowBelow();
while (findNextRow.IsEmpty())
{
findNextRow = findNextRow.RowBelow();
}
const int itemNameCol = 1;
var itemRow = findNextRow.RowUsed().RowBelow();
while(!itemRow.Cell(itemNameCol).IsEmpty())
{
string itemName = itemRow.Cell(1).Value.ToString();
string itemDesc = itemRow.Cell(2).Value.ToString();
string catName = itemRow.Cell(3).Value.ToString();
string modelNo = itemRow.Cell(4).Value.ToString();
decimal retailValue = Convert.ToDecimal(itemRow.Cell(5).Value.ToString());
string fileName = itemRow.Cell(6).Value.ToString();
decimal initialBid = Convert.ToDecimal(itemRow.Cell(7).Value.ToString());
decimal increment = Convert.ToDecimal(itemRow.Cell(8).Value.ToString());
Cat itemCat = null;
foreach(var cat in auction.Cats)
{
if(catName == cat.CatName)
{
itemCat = cat;
}
}
Item item = new Item(itemName, itemDesc, modelNo, retailValue, fileName, startDate, endDate, initialBid, increment, null, null, null, itemCat);
itemCat.Items.Add(item);
itemRow = itemRow.RowBelow();
}
}
else
{
ModelState.AddModelError(String.Empty, "Only .xlsx and .xls files are allowed");
return View();
}
}
else
{
ModelState.AddModelError(String.Empty, "Not a valid file");
return View();
}
}
db.SaveChanges();
return View();
}
接下来我想我会尝试再次创建一个视图,以便我可以显示用户上传文件的位置并查看我的方法是否有效,这就是我在asp.net中缺乏知识的地方。
所以我尝试创建一个 ViewModel,因为我之前创建的模型是一个数据模型,所以我可以使用这个 viewmodel 在我的视图页面上显示上传。我的 ViewModel 很简单,是:
public class FileUploadViewModel
{
public HttpPostedFileBase ExcelFile { get; set; }
}
现在,我想为这个视图模型创建一个视图页面,它仍然认为这个模型有一个实体,并给我一个错误,它没有密钥等。我需要一个可以访问模型的视图页面Excel 文件在其中,我似乎无法弄清楚如何做到这一点。我已经阅读了视图模型,并且知道它们在 MVC 中的重要性,但是我似乎无法掌握如何使用它们。有人可以帮我了解如何在这里使用吗?
基本上,我想将此视图页面与我的模型或视图模型一起使用:
【问题讨论】:
-
您说问题出在您的视图模型上,但您发布的代码似乎与此无关(除了视图模型类定义)。您的 DbContext 是什么样的,您是如何创建视图模型并尝试显示它的? UploadFile 是否应该是您的实体之一?它没有钥匙。
-
UploadFile 不是实体。我根本不想将它或上传的文件存储在我的数据库中。这只是我认为将 excel 文件放入控制器的一种方式,以便我可以做我想做的事情。我想要完成的是有一个视图页面,上面写着“单击此处上传文件”,他们在那里上传电子表格,而我发布的控制器完成了其余的工作。我正在尝试使用 UploadedFile 模型或我创建的视图模型作为我传递给视图的模型来创建一个视图页面,以便我可以完成此操作。
-
我通过右键单击并添加一个类将我的模型和尝试的视图模型都添加到了我的模型文件夹中。这是我知道该怎么做的唯一方法。它认为我希望这些类作为实体,因此当我尝试使用任何一个作为模型创建视图页面时出现错误
-
好的,所以除非我遗漏了什么,否则没有什么只是“成为”一个实体,并在您的 DbContext 上显式注册为 DbSet。你能用确切的错误信息更新问题吗?
-
您的上传类不需要
[NotMapped]。那是您的视图模型。现在创建一个对该视图模型进行强类型化的视图并使用它。
标签: c# asp.net-mvc entity-framework viewmodel