| { | { | ||||
| public string Text { get; set; } | public string Text { get; set; } | ||||
| public bool IsValid { get; set; } = true; | public bool IsValid { get; set; } = true; | ||||
| public bool AllowEditing { get; set; } = false; | |||||
| public Guid Code { get; set; } = Guid.NewGuid(); | public Guid Code { get; set; } = Guid.NewGuid(); | ||||
| public List<FileModel> FileNames { get; set; } = new(); | public List<FileModel> FileNames { get; set; } = new(); | ||||
| public DateTime? ExpiryDate { get; set; } | public DateTime? ExpiryDate { get; set; } |
| public async Task Update(MessageDto messageDto) | public async Task Update(MessageDto messageDto) | ||||
| { | { | ||||
| var message = await GetById(messageDto.Id); | |||||
| message.Text = messageDto.Text; | |||||
| message.FileNames = messageDto.FileNames; | |||||
| var a = _dbContext.Messages | var a = _dbContext.Messages | ||||
| .Update(_mapper.Map<Message>(messageDto)); | |||||
| .Update(_mapper.Map<Message>(message)); | |||||
| await _dbContext.SaveChangesAsync(); | await _dbContext.SaveChangesAsync(); | ||||
| } | } |
| public string Code { get; set; } | public string Code { get; set; } | ||||
| public List<FileModel> FileNames { get; } = new(); | public List<FileModel> FileNames { get; } = new(); | ||||
| public bool IsValid { get; set; } | public bool IsValid { get; set; } | ||||
| public bool AllowEditing { get; set; } | |||||
| public DateTime? ExpiryDate { get; set; } | public DateTime? ExpiryDate { get; set; } | ||||
| public bool Anonymous { get; set; } = false; | public bool Anonymous { get; set; } = false; | ||||
| } | } |
| // <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 | |||||
| } | |||||
| } | |||||
| } |
| 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"); | |||||
| } | |||||
| } | |||||
| } |
| SqlServerPropertyBuilderExtensions.UseIdentityColumn(b.Property<int>("Id"), 1L, 1); | SqlServerPropertyBuilderExtensions.UseIdentityColumn(b.Property<int>("Id"), 1L, 1); | ||||
| b.Property<bool>("AllowEditing") | |||||
| .HasColumnType("bit"); | |||||
| b.Property<bool>("Anonymous") | b.Property<bool>("Anonymous") | ||||
| .HasColumnType("bit"); | .HasColumnType("bit"); | ||||
| using Microsoft.AspNetCore.Authorization; | |||||
| using AutoMapper; | |||||
| using Microsoft.AspNetCore.Authorization; | |||||
| using Microsoft.AspNetCore.Mvc; | using Microsoft.AspNetCore.Mvc; | ||||
| using Microsoft.AspNetCore.StaticFiles; | using Microsoft.AspNetCore.StaticFiles; | ||||
| using SecureSharing.Business.Dtos; | using SecureSharing.Business.Dtos; | ||||
| private readonly IMessageService _messageService; | private readonly IMessageService _messageService; | ||||
| private readonly IModelFactory _modelFactory; | private readonly IModelFactory _modelFactory; | ||||
| private readonly IWebHostEnvironment _webHostEnvironment; | private readonly IWebHostEnvironment _webHostEnvironment; | ||||
| private readonly IMapper _mapper; | |||||
| public HomeController(ILogger<HomeController> logger, IMessageService messageService, IModelFactory modelFactory, | public HomeController(ILogger<HomeController> logger, IMessageService messageService, IModelFactory modelFactory, | ||||
| IWebHostEnvironment webHostEnvironment) | |||||
| IWebHostEnvironment webHostEnvironment, IMapper mapper) | |||||
| { | { | ||||
| _logger = logger; | _logger = logger; | ||||
| _messageService = messageService; | _messageService = messageService; | ||||
| _modelFactory = modelFactory; | _modelFactory = modelFactory; | ||||
| _webHostEnvironment = webHostEnvironment; | _webHostEnvironment = webHostEnvironment; | ||||
| _mapper = mapper; | |||||
| } | } | ||||
| public IActionResult Index() | public IActionResult Index() | ||||
| return View(); | return View(); | ||||
| } | } | ||||
| [AllowAnonymous] | |||||
| public async Task<string> UploadTemporaryFile() | public async Task<string> UploadTemporaryFile() | ||||
| { | { | ||||
| var code = Guid.NewGuid().ToString(); | var code = Guid.NewGuid().ToString(); | ||||
| [HttpPost] | [HttpPost] | ||||
| public async Task<IActionResult> CreateMessage(MessageModel model) | 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("/"); | return Redirect("/"); | ||||
| } | |||||
| model.FilesAsText = model.FilesAsText != "978682e8-3ce7-4258-b731-d027b5b213aa" | model.FilesAsText = model.FilesAsText != "978682e8-3ce7-4258-b731-d027b5b213aa" | ||||
| ? model.FilesAsText.Split("978682e8-3ce7-4258-b731-d027b5b213aa")[1] | ? 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); | await UploadFiles(model, message); | ||||
| return RedirectToAction("Link", "Home", new { code, share = true }); | 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) | private async Task UploadFiles(MessageModel model, MessageDto message) | ||||
| { | { | ||||
| var basePath = Path.Combine(_webHostEnvironment.WebRootPath.Split('/')[0], DefaultPath, | var basePath = Path.Combine(_webHostEnvironment.WebRootPath.Split('/')[0], DefaultPath, | ||||
| } | } | ||||
| [HttpGet] | [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); | return View(model); | ||||
| } | } | ||||
| [AllowAnonymous] | [AllowAnonymous] | ||||
| [HttpGet] | [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); | 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() | public IActionResult Privacy() | ||||
| { | { | ||||
| return View(); | return View(); |
| public interface IModelFactory | public interface IModelFactory | ||||
| { | { | ||||
| //public MessageModel PrepareMessageVM(MessageDto message); | //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); | |||||
| } | } |
| _messageService = messageService; | _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 | //share is true when the link is created | ||||
| { | { | ||||
| MessageModel = new MessageModel | MessageModel = new MessageModel | ||||
| { | { | ||||
| Id = message.Id, | |||||
| Code = code, | Code = code, | ||||
| Text = message.Text, | Text = message.Text, | ||||
| FileNames = message.FileNames.Select(x => x.Name).ToList(), | FileNames = message.FileNames.Select(x => x.Name).ToList(), | ||||
| Anonymous = message.Anonymous | |||||
| Anonymous = message.Anonymous, | |||||
| AllowEditing = message.AllowEditing | |||||
| }, | }, | ||||
| Share = share, | Share = share, | ||||
| IsValid = message.IsValid | IsValid = message.IsValid | ||||
| else | else | ||||
| { | { | ||||
| //ONE_TIME sharing: make the message invalid now so that it can't be accessed next time | //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 | else | ||||
| return model; | 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 }; | 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) | //public MessageModel PrepareMessageVM(MessageDto message) | ||||
| //{ | //{ | ||||
| // throw new System.NotImplementedException(); | // throw new System.NotImplementedException(); |
| public string FilesAsText { get; set; } = default!; | public string FilesAsText { get; set; } = default!; | ||||
| public bool Anonymous { get; set; } = false; | public bool Anonymous { get; set; } = false; | ||||
| public bool AllowEditing { get; set; } = false; | |||||
| // public Dictionary<int, string> AvailablePeriods { get; set; } | // public Dictionary<int, string> AvailablePeriods { get; set; } | ||||
| } | } |
| </div> | </div> | ||||
| </div> | </div> | ||||
| </div> | </div> | ||||
| <div class="mb-3"> | <div class="mb-3"> | ||||
| <div class="label-text"> | <div class="label-text"> | ||||
| Your files | Your files | ||||
| </div> | </div> | ||||
| </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"> | <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> | </div> | ||||
| </div> | |||||
| <button class=" btn btn-light share-button" type="submit">Share</button> | <button class=" btn btn-light share-button" type="submit">Share</button> | ||||
| </form> | </form> | ||||
| </div> | </div> | ||||
| <div id="div-link" class="label-text link-show"> | <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> | <a id="a-link" href="@link">@link</a> | ||||
| </div> | </div> |
| { | { | ||||
| <h1>Document is ready!</h1> | <h1>Document is ready!</h1> | ||||
| <a href="/" class="share-more-files-button">Share more files</a> | <a href="/" class="share-more-files-button">Share more files</a> | ||||
| <div> | <div> | ||||
| @if (Model.TimeLeft != null) | @if (Model.TimeLeft != null) | ||||
| { | { | ||||
| } | } | ||||
| 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> | </div> | ||||
| @{ | |||||
| 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> |