简体   繁体   English

上传和查看文件ASP.NET MVC 5

[英]Upload and View Files ASP.NET MVC 5

I have this code: 我有这个代码:

    [HttpPost]
    public ActionResult Create(Knowledgebase KB, HttpPostedFileBase file)
    {
        var KBFilePath = "";
        if (ModelState.IsValid)
        {
            if (file.ContentLength > 0)
            {
                var fileName = Path.GetFileName(KB.KnowledgebaseTitle);
                var path = Path.Combine(Server.MapPath("~/Resources/KBArticles"), fileName + ".pdf");
                KBFilePath = path;
                file.SaveAs(path);
            }
            KB.KnowledgebaseLink = KBFilePath;
            db.Knowledgebases.Add(KB);
            db.SaveChanges();
            return RedirectToAction("Index", "Home");
        }

        else
        {
            return View();
        }

The link is the filepath which is stored in the DB which starts with C:/ 链接是存储在以C:/ C开头的DB中的文件路径

On another page I can view the contents of the record. 在另一个页面上,我可以查看记录的内容。 When I click on the link to which its saved on the C:/, Chrome says 'Failed to load local resource'. 当我点击其保存在C:/上的链接时,Chrome会显示“无法加载本地资源”。 I am saving into the Resources folder which is part of my ASP.NET app directory. 我保存到Resources文件夹中,该文件夹是我的ASP.NET应用程序目录的一部分。 Anyway around this? 无论如何围绕这个?

EDIT The page is served from this View: 编辑该页面由此视图提供:

public ActionResult Suggestions(String Tag)
{
      return View();
}

EDIT 2 - I put the changes in my view: 编辑2 - 我把更改放在我的视图中:

@{
string tag = "<td><a href=" + "~/Content/Files/" + ">" + item.Title.Replace(" ", "") + ".pdf" + "</a>" + "</td>";
 }
 @Html.Raw(tag)

The requested file in the browser address bar is 浏览器地址栏中请求的文件是

http://localhost:62165/Incident/~/Content/Files/

Now I get a HTTP Error 404.0 Not Found error 现在我收到HTTP错误404.0 Not Found错误

This is a full example that shows how to upload files and put them available for download through links. 这是一个完整的示例,显示如何上传文件并通过链接将其下载。

Create an empty MVC Project. 创建一个空的MVC项目。 I use MVC 4 but it should work with MVC 5. 我使用MVC 4,但它应该与MVC 5一起使用。

Controller: 控制器:

In the HomeController we are going to have a single action Index that will show the list of files available for download and the option for uploading new files. HomeController我们将有一个单一的动作Index ,它将显示可供下载的文件列表和上传新文件的选项。

Action Index GET: 行动Index GET:

  • Locate the path to 'Content/Files/'. 找到“Content / Files /”的路径。
  • Get the list of all files in that folder. 获取该文件夹中所有文件的列表。
  • Use that list as the model of the Index view. 使用该列表作为Index视图的模型。

Action Index POST: 行动Index POST:

  • Locate the path to 'Content/Files/'. 找到“Content / Files /”的路径。
  • Create a temporary array to store the content of the file. 创建一个临时数组来存储文件的内容。
  • Read the content to the buffer. 将内容读入缓冲区。
  • Write the content to a file in folder 'Content/Files/'. 将内容写入“Content / Files /”文件夹中的文件。

Code: 码:

public class HomeController : Controller
{
    public ActionResult Index()
    {
        var path = Server.MapPath("~/Content/Files/");

        var dir = new DirectoryInfo(path);

        var files = dir.EnumerateFiles().Select(f => f.Name);

        return View(files);
    }

    [HttpPost]
    public ActionResult Index(HttpPostedFileBase file)
    {
        var path = Path.Combine(Server.MapPath("~/Content/Files/"), file.FileName);

        var data = new byte[file.ContentLength];
        file.InputStream.Read(data, 0, file.ContentLength);

        using (var sw = new FileStream(path, FileMode.Create))
        {
            sw.Write(data, 0, data.Length);
        }

        return RedirectToAction("Index");
    }

}

View: 视图:

In the view we need to generate a list with links to the files. 在视图中,我们需要生成一个包含文件链接的列表。 Here we need to take care of file names that contains spaces and replace them with '%20'. 这里我们需要处理包含空格的文件名,并用'%20'替换它们。

The form to upload a file is simple. 上传文件的表单很简单。 Just an input tag to get the file and one button to send the form. 只是一个输入标签来获取文件和一个按钮来发送表单。

@model IEnumerable<string>

@{
    ViewBag.Title = "Index";
}

<h2>Files</h2>

<ul>
    @foreach (var fName in Model)
    {
        var name = fName;
        var link = @Url.Content("~/Content/Files/") + name.Replace(" ", "%20");

        <li>
            <a href="@link">@name</a>
        </li>
    }
</ul>

<div>
    @using (Html.BeginForm("Index", "Home", FormMethod.Post, new { enctype = "multipart/form-data" }))
    {
        <input type="File" name="file" id="file" value="Choose File"/>
        <button type="submit">Upload</button>
    }
</div>

The result should be: 结果应该是:

索引视图

Try to save the files in Content folder. 尝试将文件保存在“内容”文件夹中。 You can create a sub folder Content/Files. 您可以创建子文件夹Content / Files。 Put you files there. 把文件放在那里。 Then generate the links like: 然后生成如下链接:

<a href="~/Content/Files/file1.pdf">File1</a>

or use the download attribute if you want to download directly: 或者如果要直接下载,请使用下载属性:

<a href="~/Content/Files/file1.pdf" download>File1</a> . <a href="~/Content/Files/file1.pdf" download>File1</a>

Most web servers are configured to deny requests for content outside the content folder. 大多数Web服务器都配置为拒绝对内容文件夹之外的内容的请求。 This can be modified in the config file but is easier (and safer) if you use the content folder. 这可以在配置文件中修改,但如果您使用内容文件夹,则更容易(也更安全)。 This is based on my experience, if someone think that I'm wrong please let me know to fix my answer. 这是基于我的经验,如果有人认为我错了,请让我知道我的答案。 I'm always glad to learn something new. 我总是很高兴学到新的东西。

EDIT 1: How to build the a tag dynamically 编辑1:如何建立a动态标签

In the view you need a string variable link that holds the text of the link you want to show and another variable path to hold the path (maybe both are loaded from db in the controller). 在视图中,您需要一个字符串变量link保存要显示的链接和另一个变量的文本path来保存路径(也许两者都是从数据库加载到控制器)。 Then you can build the tag manually like this: 然后你可以像这样手动构建标签:

@{
    string tag = "<a href=" + path + ">" + link + "</a>";
}

@Html.Raw(tag)

EDIT 2: Dealing with spaces in Url. 编辑2:处理Url中的空格。

You need to use Html.Content to get the right relative Url. 您需要使用Html.Content来获取正确的相对Url。

@{
    string link = item.Title;
    string path = Url.Content("~/Content/Files/") + link.Replace(" ", "%20") + ".pdf";
    string tag = "<a href=" + path + ">" + link + "</a>";
}

@Html.Raw(tag)

First the Create View < 首先是创建视图<

<div class="form-group"> @Html.LabelFor(model => model.ImageData, new { @class = "control-label col-md-2" }) 
  <div class="col-md-10"> <input name="Image" type="file" /> 
    @Html.ValidationMessageFor(model => model.ImageData) 
  </div> 
</div>

Then the Controller Create Action 然后控制器创建操作

public ActionResult Create(ArtWork artwork, HttpPostedFileBase image) { 
  if (ModelState.IsValid) { 
    if (image != null) { //attach the uploaded image to the object before saving to Database 
      artwork.ImageMimeType = image.ContentLength; 
      artwork.ImageData = new byte[image.ContentLength]; 
      image.InputStream.Read(artwork.ImageData, 0, image.ContentLength); //Save image to file 
      var filename = image.FileName; 
      var filePathOriginal = Server.MapPath("/Content/Uploads/Originals"); 
      var filePathThumbnail = Server.MapPath("/Content/Uploads/Thumbnails"); 
      string savedFileName = Path.Combine(filePathOriginal, filename); 
      image.SaveAs(savedFileName); //Read image back from file and create thumbnail from it 
      var imageFile = Path.Combine(Server.MapPath("~/Content/Uploads/Originals"), filename); 

      using (var srcImage = Image.FromFile(imageFile)) 
      using (var newImage = new Bitmap(100, 100)) 
      using (var graphics = Graphics.FromImage(newImage)) 
      using (var stream = new MemoryStream()) { 
        graphics.SmoothingMode = SmoothingMode.AntiAlias; 
        graphics.InterpolationMode = InterpolationMode.HighQualityBicubic; 
        graphics.PixelOffsetMode = PixelOffsetMode.HighQuality; 
        graphics.DrawImage(srcImage, new Rectangle(0, 0, 100, 100)); 
        newImage.Save(stream, ImageFormat.Png); 
        var thumbNew = File(stream.ToArray(), "image/png"); 
        artwork.ArtworkThumbnail = thumbNew.FileContents; 
      } 
    } 

    //Save model object to database 
    db.ArtWorks.Add(artwork); 
    db.SaveChanges(); 
    return RedirectToAction("Index"); 
  } 
  return View(artwork); 
}

Then a get Image or GetThumbnail method 然后获取Image或GetThumbnail方法

public FileContentResult GetThumbnailImage(int artworkId) { 
  ArtWork art = db.ArtWorks.FirstOrDefault(p => p.ArtWorkId == artworkId); 
  if (art != null) { 
    return File(art.ArtworkThumbnail, art.ImageMimeType.ToString()); 
  } else { 
    return null; 
  } 
}

And here for the display in the view 这里是视图中的显示

<td> <img src="@Url.Action("GetThumbnailImage", "Artwork", new { Model.ArtWorkId })" alt="Artwork Image" /> </td>

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM