Просмотр исходного кода

Allow anonymous editing.

master
radivoje.milutinovic 3 лет назад
Родитель
Сommit
529c861eb1

+ 1
- 0
SecureSharing.Business/Dtos/MessageDto.cs Просмотреть файл

@@ -6,6 +6,7 @@ public sealed class MessageDto : BaseDto
{
public string Text { get; set; }
public bool IsValid { get; set; } = true;
public bool AllowEditing { get; set; } = false;
public Guid Code { get; set; } = Guid.NewGuid();
public List<FileModel> FileNames { get; set; } = new();
public DateTime? ExpiryDate { get; set; }

+ 5
- 1
SecureSharing.Business/Services/MessageService.cs Просмотреть файл

@@ -112,8 +112,12 @@ public sealed class MessageService : IMessageService

public async Task Update(MessageDto messageDto)
{
var message = await GetById(messageDto.Id);
message.Text = messageDto.Text;
message.FileNames = messageDto.FileNames;

var a = _dbContext.Messages
.Update(_mapper.Map<Message>(messageDto));
.Update(_mapper.Map<Message>(message));
await _dbContext.SaveChangesAsync();
}

+ 1
- 0
SecureSharing.Data/Data/Message.cs Просмотреть файл

@@ -6,6 +6,7 @@ public sealed class Message : BaseEntity
public string Code { get; set; }
public List<FileModel> FileNames { get; } = new();
public bool IsValid { get; set; }
public bool AllowEditing { get; set; }
public DateTime? ExpiryDate { get; set; }
public bool Anonymous { get; set; } = false;
}

+ 348
- 0
SecureSharing.Data/Migrations/20221024122405_Adding message editing.Designer.cs Просмотреть файл

@@ -0,0 +1,348 @@
// <auto-generated />
using System;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.Infrastructure;
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
using SecureSharing.Data.DbContexts;

#nullable disable

namespace SecureSharing.Data.Migrations
{
[DbContext(typeof(AppDbContext))]
[Migration("20221024122405_Adding message editing")]
partial class Addingmessageediting
{
protected override void BuildTargetModel(ModelBuilder modelBuilder)
{
#pragma warning disable 612, 618
modelBuilder
.HasAnnotation("ProductVersion", "6.0.9")
.HasAnnotation("Relational:MaxIdentifierLength", 128);

SqlServerModelBuilderExtensions.UseIdentityColumns(modelBuilder, 1L, 1);

modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityRole", b =>
{
b.Property<string>("Id")
.HasColumnType("nvarchar(450)");

b.Property<string>("ConcurrencyStamp")
.IsConcurrencyToken()
.HasColumnType("nvarchar(max)");

b.Property<string>("Name")
.HasMaxLength(256)
.HasColumnType("nvarchar(256)");

b.Property<string>("NormalizedName")
.HasMaxLength(256)
.HasColumnType("nvarchar(256)");

b.HasKey("Id");

b.HasIndex("NormalizedName")
.IsUnique()
.HasDatabaseName("RoleNameIndex")
.HasFilter("[NormalizedName] IS NOT NULL");

b.ToTable("AspNetRoles", (string)null);
});

modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityRoleClaim<string>", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("int");

SqlServerPropertyBuilderExtensions.UseIdentityColumn(b.Property<int>("Id"), 1L, 1);

b.Property<string>("ClaimType")
.HasColumnType("nvarchar(max)");

b.Property<string>("ClaimValue")
.HasColumnType("nvarchar(max)");

b.Property<string>("RoleId")
.IsRequired()
.HasColumnType("nvarchar(450)");

b.HasKey("Id");

b.HasIndex("RoleId");

b.ToTable("AspNetRoleClaims", (string)null);
});

modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUser", b =>
{
b.Property<string>("Id")
.HasColumnType("nvarchar(450)");

b.Property<int>("AccessFailedCount")
.HasColumnType("int");

b.Property<string>("ConcurrencyStamp")
.IsConcurrencyToken()
.HasColumnType("nvarchar(max)");

b.Property<string>("Email")
.HasMaxLength(256)
.HasColumnType("nvarchar(256)");

b.Property<bool>("EmailConfirmed")
.HasColumnType("bit");

b.Property<bool>("LockoutEnabled")
.HasColumnType("bit");

b.Property<DateTimeOffset?>("LockoutEnd")
.HasColumnType("datetimeoffset");

b.Property<string>("NormalizedEmail")
.HasMaxLength(256)
.HasColumnType("nvarchar(256)");

b.Property<string>("NormalizedUserName")
.HasMaxLength(256)
.HasColumnType("nvarchar(256)");

b.Property<string>("PasswordHash")
.HasColumnType("nvarchar(max)");

b.Property<string>("PhoneNumber")
.HasColumnType("nvarchar(max)");

b.Property<bool>("PhoneNumberConfirmed")
.HasColumnType("bit");

b.Property<string>("SecurityStamp")
.HasColumnType("nvarchar(max)");

b.Property<bool>("TwoFactorEnabled")
.HasColumnType("bit");

b.Property<string>("UserName")
.HasMaxLength(256)
.HasColumnType("nvarchar(256)");

b.HasKey("Id");

b.HasIndex("NormalizedEmail")
.HasDatabaseName("EmailIndex");

b.HasIndex("NormalizedUserName")
.IsUnique()
.HasDatabaseName("UserNameIndex")
.HasFilter("[NormalizedUserName] IS NOT NULL");

b.ToTable("AspNetUsers", (string)null);
});

modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserClaim<string>", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("int");

SqlServerPropertyBuilderExtensions.UseIdentityColumn(b.Property<int>("Id"), 1L, 1);

b.Property<string>("ClaimType")
.HasColumnType("nvarchar(max)");

b.Property<string>("ClaimValue")
.HasColumnType("nvarchar(max)");

b.Property<string>("UserId")
.IsRequired()
.HasColumnType("nvarchar(450)");

b.HasKey("Id");

b.HasIndex("UserId");

b.ToTable("AspNetUserClaims", (string)null);
});

modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserLogin<string>", b =>
{
b.Property<string>("LoginProvider")
.HasMaxLength(128)
.HasColumnType("nvarchar(128)");

b.Property<string>("ProviderKey")
.HasMaxLength(128)
.HasColumnType("nvarchar(128)");

b.Property<string>("ProviderDisplayName")
.HasColumnType("nvarchar(max)");

b.Property<string>("UserId")
.IsRequired()
.HasColumnType("nvarchar(450)");

b.HasKey("LoginProvider", "ProviderKey");

b.HasIndex("UserId");

b.ToTable("AspNetUserLogins", (string)null);
});

modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserRole<string>", b =>
{
b.Property<string>("UserId")
.HasColumnType("nvarchar(450)");

b.Property<string>("RoleId")
.HasColumnType("nvarchar(450)");

b.HasKey("UserId", "RoleId");

b.HasIndex("RoleId");

b.ToTable("AspNetUserRoles", (string)null);
});

modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserToken<string>", b =>
{
b.Property<string>("UserId")
.HasColumnType("nvarchar(450)");

b.Property<string>("LoginProvider")
.HasMaxLength(128)
.HasColumnType("nvarchar(128)");

b.Property<string>("Name")
.HasMaxLength(128)
.HasColumnType("nvarchar(128)");

b.Property<string>("Value")
.HasColumnType("nvarchar(max)");

b.HasKey("UserId", "LoginProvider", "Name");

b.ToTable("AspNetUserTokens", (string)null);
});

modelBuilder.Entity("SecureSharing.Data.Data.FileModel", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("int");

SqlServerPropertyBuilderExtensions.UseIdentityColumn(b.Property<int>("Id"), 1L, 1);

b.Property<int>("MessageId")
.HasColumnType("int");

b.Property<string>("Name")
.HasColumnType("nvarchar(max)");

b.HasKey("Id");

b.HasIndex("MessageId");

b.ToTable("FileModel");
});

modelBuilder.Entity("SecureSharing.Data.Data.Message", b =>
{
b.Property<int>("Id")
.ValueGeneratedOnAdd()
.HasColumnType("int");

SqlServerPropertyBuilderExtensions.UseIdentityColumn(b.Property<int>("Id"), 1L, 1);

b.Property<bool>("AllowEditing")
.HasColumnType("bit");

b.Property<bool>("Anonymous")
.HasColumnType("bit");

b.Property<string>("Code")
.HasColumnType("nvarchar(max)");

b.Property<DateTime?>("ExpiryDate")
.HasColumnType("datetime2");

b.Property<bool>("IsValid")
.HasColumnType("bit");

b.Property<string>("Text")
.HasColumnType("nvarchar(max)");

b.HasKey("Id");

b.ToTable("Messages");
});

modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityRoleClaim<string>", b =>
{
b.HasOne("Microsoft.AspNetCore.Identity.IdentityRole", null)
.WithMany()
.HasForeignKey("RoleId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
});

modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserClaim<string>", b =>
{
b.HasOne("Microsoft.AspNetCore.Identity.IdentityUser", null)
.WithMany()
.HasForeignKey("UserId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
});

modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserLogin<string>", b =>
{
b.HasOne("Microsoft.AspNetCore.Identity.IdentityUser", null)
.WithMany()
.HasForeignKey("UserId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
});

modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserRole<string>", b =>
{
b.HasOne("Microsoft.AspNetCore.Identity.IdentityRole", null)
.WithMany()
.HasForeignKey("RoleId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();

b.HasOne("Microsoft.AspNetCore.Identity.IdentityUser", null)
.WithMany()
.HasForeignKey("UserId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
});

modelBuilder.Entity("Microsoft.AspNetCore.Identity.IdentityUserToken<string>", b =>
{
b.HasOne("Microsoft.AspNetCore.Identity.IdentityUser", null)
.WithMany()
.HasForeignKey("UserId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
});

modelBuilder.Entity("SecureSharing.Data.Data.FileModel", b =>
{
b.HasOne("SecureSharing.Data.Data.Message", null)
.WithMany("FileNames")
.HasForeignKey("MessageId")
.OnDelete(DeleteBehavior.Cascade)
.IsRequired();
});

modelBuilder.Entity("SecureSharing.Data.Data.Message", b =>
{
b.Navigation("FileNames");
});
#pragma warning restore 612, 618
}
}
}

+ 26
- 0
SecureSharing.Data/Migrations/20221024122405_Adding message editing.cs Просмотреть файл

@@ -0,0 +1,26 @@
using Microsoft.EntityFrameworkCore.Migrations;

#nullable disable

namespace SecureSharing.Data.Migrations
{
public partial class Addingmessageediting : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<bool>(
name: "AllowEditing",
table: "Messages",
type: "bit",
nullable: false,
defaultValue: false);
}

protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "AllowEditing",
table: "Messages");
}
}
}

+ 3
- 0
SecureSharing.Data/Migrations/AppDbContextModelSnapshot.cs Просмотреть файл

@@ -253,6 +253,9 @@ namespace SecureSharing.Data.Migrations

SqlServerPropertyBuilderExtensions.UseIdentityColumn(b.Property<int>("Id"), 1L, 1);

b.Property<bool>("AllowEditing")
.HasColumnType("bit");

b.Property<bool>("Anonymous")
.HasColumnType("bit");


+ 51
- 9
SecureSharing/Controllers/HomeController.cs Просмотреть файл

@@ -1,4 +1,5 @@
using Microsoft.AspNetCore.Authorization;
using AutoMapper;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.StaticFiles;
using SecureSharing.Business.Dtos;
@@ -18,14 +19,16 @@ public sealed class HomeController : Controller
private readonly IMessageService _messageService;
private readonly IModelFactory _modelFactory;
private readonly IWebHostEnvironment _webHostEnvironment;
private readonly IMapper _mapper;

public HomeController(ILogger<HomeController> logger, IMessageService messageService, IModelFactory modelFactory,
IWebHostEnvironment webHostEnvironment)
IWebHostEnvironment webHostEnvironment, IMapper mapper)
{
_logger = logger;
_messageService = messageService;
_modelFactory = modelFactory;
_webHostEnvironment = webHostEnvironment;
_mapper = mapper;
}

public IActionResult Index()
@@ -33,6 +36,7 @@ public sealed class HomeController : Controller
return View();
}

[AllowAnonymous]
public async Task<string> UploadTemporaryFile()
{
var code = Guid.NewGuid().ToString();
@@ -56,15 +60,19 @@ public sealed class HomeController : Controller
[HttpPost]
public async Task<IActionResult> CreateMessage(MessageModel model)
{
if (string.IsNullOrWhiteSpace(model.Text) && model.Files.Count == 0 &&
model.FilesAsText == "978682e8-3ce7-4258-b731-d027b5b213aa")
if (!model.AllowEditing
&& string.IsNullOrWhiteSpace(model.Text)
&& model.Files.Count == 0
&& model.FilesAsText == "978682e8-3ce7-4258-b731-d027b5b213aa")
{
return Redirect("/");
}

model.FilesAsText = model.FilesAsText != "978682e8-3ce7-4258-b731-d027b5b213aa"
? model.FilesAsText.Split("978682e8-3ce7-4258-b731-d027b5b213aa")[1]
: "";

var message = new MessageDto { Text = model.Text, Anonymous = model.Anonymous };
var message = new MessageDto { Text = model.Text, Anonymous = model.AllowEditing || model.Anonymous, AllowEditing = model.AllowEditing};

await UploadFiles(model, message);

@@ -73,6 +81,32 @@ public sealed class HomeController : Controller
return RedirectToAction("Link", "Home", new { code, share = true });
}

[HttpPost]
[AllowAnonymous]
public async Task<IActionResult> UpdateMessage(MessageModel model)
{
if (string.IsNullOrWhiteSpace(model.Text) && model.Files.Count == 0 &&
model.FilesAsText == "978682e8-3ce7-4258-b731-d027b5b213aa")
{
return Redirect("/");
}

model.FilesAsText = model.FilesAsText != "978682e8-3ce7-4258-b731-d027b5b213aa"
? model.FilesAsText.Split("978682e8-3ce7-4258-b731-d027b5b213aa")[1]
: "";

var message = new MessageDto { Text = model.Text, Anonymous = model.Anonymous, Id = model.Id, Code = model.Code};
// var messageDto = _mapper.Map<MessageDto>(model);

await UploadFiles(model, message);

await _messageService.Update(message);

return RedirectToAction("LinkAnonymous", "Home", new { model.Code, share = true, edit = true });
}

[AllowAnonymous]
private async Task UploadFiles(MessageModel model, MessageDto message)
{
var basePath = Path.Combine(_webHostEnvironment.WebRootPath.Split('/')[0], DefaultPath,
@@ -138,20 +172,28 @@ public sealed class HomeController : Controller
}

[HttpGet]
public async Task<IActionResult> Link(Guid code, bool? share)
public async Task<IActionResult> Link(Guid code, bool? share, bool? edit)
{
var model = await _modelFactory.PrepareLinkVM(code, share);
var model = await _modelFactory.PrepareLinkVM(code, share, edit);
return View(model);
}

[AllowAnonymous]
[HttpGet]
public async Task<IActionResult> LinkAnonymous(Guid code, bool? share)
public async Task<IActionResult> LinkAnonymous(Guid code, bool? edit)
{
var model = await _modelFactory.PrepareLinkAnonymous(code, share);
var model = await _modelFactory.PrepareLinkAnonymous(code, edit);
return View(model);
}

[AllowAnonymous]
[HttpGet]
public async Task<IActionResult> LinkEdit(Guid code, bool? edit)
{
var model = await _modelFactory.PrepareLinkEdit(code, edit);
return View(model.MessageModel);
}

public IActionResult Privacy()
{
return View();

+ 3
- 2
SecureSharing/Infrastructure/IModelFactory.cs Просмотреть файл

@@ -5,6 +5,7 @@ namespace SecureSharing.Infrastructure;
public interface IModelFactory
{
//public MessageModel PrepareMessageVM(MessageDto message);
public Task<LinkModel> PrepareLinkVM(Guid code, bool? share);
public Task<LinkModel> PrepareLinkAnonymous(Guid code, bool? share);
public Task<LinkModel> PrepareLinkVM(Guid code, bool? share, bool? edit);
public Task<LinkModel> PrepareLinkAnonymous(Guid code, bool? edit);
public Task<LinkModel> PrepareLinkEdit(Guid code, bool? edit);
}

+ 14
- 5
SecureSharing/Infrastructure/ModelFactory.cs Просмотреть файл

@@ -14,7 +14,7 @@ public sealed class ModelFactory : IModelFactory
_messageService = messageService;
}

public async Task<LinkModel> PrepareLinkVM(Guid code, bool? share)
public async Task<LinkModel> PrepareLinkVM(Guid code, bool? share, bool? edit)
{
//share is true when the link is created

@@ -27,10 +27,12 @@ public sealed class ModelFactory : IModelFactory
{
MessageModel = new MessageModel
{
Id = message.Id,
Code = code,
Text = message.Text,
FileNames = message.FileNames.Select(x => x.Name).ToList(),
Anonymous = message.Anonymous
Anonymous = message.Anonymous,
AllowEditing = message.AllowEditing
},
Share = share,
IsValid = message.IsValid
@@ -50,7 +52,7 @@ public sealed class ModelFactory : IModelFactory
else
{
//ONE_TIME sharing: make the message invalid now so that it can't be accessed next time
if (share is null or false) await _messageService.InvalidateMessage(message.Id);
if (share is null or false && edit is null or false) await _messageService.InvalidateMessage(message.Id);
}
}
else
@@ -67,13 +69,20 @@ public sealed class ModelFactory : IModelFactory
return model;
}

public async Task<LinkModel> PrepareLinkAnonymous(Guid code, bool? share)
public async Task<LinkModel> PrepareLinkAnonymous(Guid code, bool? edit)
{
var model = await PrepareLinkVM(code, share);
var model = await PrepareLinkVM(code, false, edit);

return model.MessageModel.Anonymous ? model : new LinkModel { IsValid = false };
}

public async Task<LinkModel> PrepareLinkEdit(Guid code, bool? edit)
{
var model = await PrepareLinkVM(code, false, edit);

return model.MessageModel.Anonymous && model.MessageModel.AllowEditing ? model : new LinkModel { IsValid = false };
}
//public MessageModel PrepareMessageVM(MessageDto message)
//{
// throw new System.NotImplementedException();

+ 2
- 0
SecureSharing/Models/MessageModel.cs Просмотреть файл

@@ -14,5 +14,7 @@ public sealed class MessageModel
public string FilesAsText { get; set; } = default!;

public bool Anonymous { get; set; } = false;

public bool AllowEditing { get; set; } = false;
// public Dictionary<int, string> AvailablePeriods { get; set; }
}

+ 19
- 8
SecureSharing/Views/Home/Index.cshtml Просмотреть файл

@@ -41,7 +41,7 @@
</div>
</div>
</div>
<div class="mb-3">
<div class="label-text">
Your files
@@ -50,16 +50,27 @@
</div>
</div>


<div class="mb-3">
<label class="label-text">Should link be visible outside diligent network?</label>
<div class="button-box row">
<div class="single-button-input col-4">
<input id="Anonymous" class="radio-input" type="checkbox" asp-for="Anonymous" value="true">
<label for="Anonymous" class="label-available">Anonymous share</label>
</div>
</div>
</div>
@* TODO: https://www.w3schools.com/howto/howto_css_switch.asp *@
<div class="mb-3">
<label class="label-text">Should link be visible outside diligent network?</label>
<div class="button-box row">
<div class="single-button-input col-4">
<input id="Anonymous" class="radio-input" type="checkbox" asp-for="Anonymous" value="true">
<label for="Anonymous" class="label-available">Anonymous share</label>
</div>
<label class="label-text">Should content be edited after posting?</label>
<div class="button-box row">
<div class="single-button-input col-4">
<input id="AllowEditing" class="radio-input" type="checkbox" asp-for="AllowEditing" value="true">
<label for="AllowEditing" class="label-available">Allow editing</label>
</div>
</div>
</div>

<button class=" btn btn-light share-button" type="submit">Share</button>
</form>


+ 13
- 1
SecureSharing/Views/Home/Link.cshtml Просмотреть файл

@@ -20,7 +20,19 @@ else
</div>
<div id="div-link" class="label-text link-show">
@{
var link = Url.Action(Model.MessageModel.Anonymous ? "LinkAnonymous" : "Link", "Home", new { code = Model.MessageModel.Code }, "https");
string link = "";
if (Model.MessageModel.AllowEditing)
{
link = Url.Action("LinkEdit", "Home", new { code = Model.MessageModel.Code, edit = true }, "https");
}
else if (Model.MessageModel.Anonymous)
{
link = Url.Action("LinkAnonymous", "Home", new { code = Model.MessageModel.Code }, "https");
}
else
{
link = Url.Action("Link", "Home", new { code = Model.MessageModel.Code }, "https");
}
}
<a id="a-link" href="@link">@link</a>
</div>

+ 7
- 5
SecureSharing/Views/Home/LinkAnonymous.cshtml Просмотреть файл

@@ -12,8 +12,7 @@ else
{
<h1>Document is ready!</h1>
<a href="/" class="share-more-files-button">Share more files</a>


<div>
@if (Model.TimeLeft != null)
{
@@ -33,9 +32,12 @@ else
}
else
{
<div class="label-text-lower">
This message will expire when you leave this page
</div>
if (!Model.MessageModel.AllowEditing)
{
<div class="label-text-lower">
This message will expire when you leave this page
</div>
}
}
</div>


+ 100
- 0
SecureSharing/Views/Home/LinkEdit.cshtml Просмотреть файл

@@ -0,0 +1,100 @@
@{
Layout = "~/Views/Shared/_Layout.cshtml";
}
@model MessageModel

<h1>@Model.Id</h1>
<h1>@Model.Code</h1>

<h1>Share files</h1>
<form method="post" enctype="multipart/form-data" asp-controller="Home" asp-action="UpdateMessage" class="share-files-form">
<input type="hidden" asp-for="Id" value="@Model.Id">
<input type="hidden" asp-for="Code" value="@Model.Code">
<div class="mb-3">
<label class="label-text">Message (optional)</label>
<textarea asp-for="Text" class="input-message"></textarea>
</div>
<div class="mb-3">
<label class="label-text">Upload files</label>
<div id="dropContainer" class="drop-here">
<img class="image-file-upload" src="~/img/file-upload-image.png" alt=""/>
<div class="default-text text-files-upload">
<label for="fileInput" class="btn browse-button">
<span style="color:#0D1C52">Drag and drop files here or</span> browse
</label>
<input asp-for="Files" id="fileInput" type="file" multiple style="display: none"/>
<input asp-for="FilesAsText" id="fileInputAsText" type="text" style="display:none" value="978682e8-3ce7-4258-b731-d027b5b213aa"/>
</div>
</div>
</div>

<div class="mb-3">
<div class="label-text">
Your files
</div>
<div id="filesUploaded">
</div>
</div>
<button class="btn btn-light share-button" type="submit">Save</button>
</form>

<script src="~/plugins/jquery/jquery.js" type="text/javascript"></script>
<script type="text/javascript">
var filesUploaded = document.getElementById("filesUploaded");
$('#fileInput').change(function() {
var files = $('#fileInput')[0].files

for (var i = 0; i < files.length; i++){
filesUploaded.innerHTML +='<p>' + files[i].name + '</p>';
}
});

var selectedFiles;

$(document).ready(() => {
var box;
box = document.getElementById("dropContainer");
box.addEventListener("dragenter", OnDragEnter, false);
box.addEventListener("dragover", OnDragOver, false);
box.addEventListener("drop", OnDrop, false);
})

function OnDragEnter(e) {
e.stopPropagation();
e.preventDefault();
}

function OnDragOver(e) {
e.stopPropagation();
e.preventDefault();
}

function OnDrop(e) {
e.stopPropagation();
e.preventDefault();
var selectedFiles = e.dataTransfer.files;
var formData = new FormData();
var fileInput = document.getElementById("fileInputAsText");
for (var i = 0; i < selectedFiles.length; i++){
formData.append(selectedFiles[i].name, selectedFiles[i]);
}
$.ajax({
url: '/Home/UploadTemporaryFile',
type: "POST",
contentType: false,
processData: false,
data: formData,
success: function (result) {
for (var i = 0; i < selectedFiles.length; i++){
fileInput.value += result + ':' + selectedFiles[i].name + ';';
filesUploaded.innerHTML += '<p>' + selectedFiles[i].name + '</p>';
}
},
error: function (err) {
console.log(err)
}
});
}
</script>

Загрузка…
Отмена
Сохранить