security: use more antiforgery tokens

This commit is contained in:
Gary Sharp
2025-07-25 12:32:44 +10:00
parent fd43d85778
commit 7deead494b
222 changed files with 12919 additions and 11728 deletions
@@ -17,6 +17,7 @@ namespace Disco.Web.Areas.Config.Controllers
[DiscoAuthorize(Claims.DiscoAdminAccount)]
public partial class AuthorizationRoleController : AuthorizedDatabaseController
{
[HttpGet]
public virtual ActionResult Index(int? id)
{
if (id.HasValue)
@@ -72,13 +73,11 @@ namespace Disco.Web.Areas.Config.Controllers
}
}
[HttpGet]
public virtual ActionResult Create()
{
// Default Role
var m = new Models.AuthorizationRole.CreateModel()
{
AuthorizationRole = new Disco.Models.Repository.AuthorizationRole()
};
var m = new Models.AuthorizationRole.CreateModel();
// UI Extensions
UIExtensions.ExecuteExtensions<ConfigAuthorizationRoleCreateModel>(ControllerContext, m);
@@ -86,16 +85,16 @@ namespace Disco.Web.Areas.Config.Controllers
return View(m);
}
[HttpPost]
[HttpPost, ValidateAntiForgeryToken]
public virtual ActionResult Create(Models.AuthorizationRole.CreateModel model)
{
if (ModelState.IsValid)
{
// Check for Existing
var existing = Database.AuthorizationRoles.Where(m => m.Name == model.AuthorizationRole.Name).FirstOrDefault();
var existing = Database.AuthorizationRoles.Where(m => m.Name == model.Name).FirstOrDefault();
if (existing == null)
{
var roleId = UserService.CreateAuthorizationRole(Database, model.AuthorizationRole);
var roleId = UserService.CreateAuthorizationRole(Database, model.Name);
return RedirectToAction(MVC.Config.AuthorizationRole.Index(roleId));
}
@@ -6,6 +6,7 @@ using Disco.Services.Devices;
using Disco.Services.Devices.ManagedGroups;
using Disco.Services.Plugins.Features.UIExtension;
using Disco.Services.Web;
using Disco.Web.Areas.Config.Models.DeviceBatch;
using System;
using System.Linq;
using System.Web.Mvc;
@@ -24,7 +25,7 @@ namespace Disco.Web.Areas.Config.Controllers
var m = Database.DeviceBatches
.Include(nameof(DeviceBatch.DeviceBatchAttachments))
.Where(db => db.Id == id.Value)
.Select(db => new Models.DeviceBatch.ShowModel()
.Select(db => new ShowModel()
{
DeviceBatch = db,
DeviceCount = db.Devices.Count(),
@@ -34,7 +35,7 @@ namespace Disco.Web.Areas.Config.Controllers
if (m == null || m.DeviceBatch == null)
throw new ArgumentException("Invalid Device Batch Id", "id");
m.DeviceModelMembers = m.DeviceBatch.Devices.GroupBy(d => d.DeviceModel).Select(dG => new Models.DeviceBatch._ShowModelMembership()
m.DeviceModelMembers = m.DeviceBatch.Devices.GroupBy(d => d.DeviceModel).Select(dG => new _ShowModelMembership()
{
DeviceModel = dG.Key,
DeviceCount = dG.Count(),
@@ -82,9 +83,9 @@ namespace Disco.Web.Areas.Config.Controllers
public virtual ActionResult Create()
{
// Default Batch
var m = new Models.DeviceBatch.CreateModel()
var m = new CreateModel()
{
DeviceBatch = DeviceBatches.DefaultNewDeviceBatch(Database)
PurchaseDate = DateTime.Today,
};
// UI Extensions
@@ -93,22 +94,28 @@ namespace Disco.Web.Areas.Config.Controllers
return View(m);
}
[DiscoAuthorizeAll(Claims.Config.DeviceBatch.Create, Claims.Config.DeviceBatch.Configure), HttpPost]
public virtual ActionResult Create(Models.DeviceBatch.CreateModel model)
[DiscoAuthorizeAll(Claims.Config.DeviceBatch.Create, Claims.Config.DeviceBatch.Configure)]
[HttpPost, ValidateAntiForgeryToken]
public virtual ActionResult Create(CreateModel model)
{
if (ModelState.IsValid)
{
// Check for Existing
var existing = Database.DeviceBatches.Where(m => m.Name == model.DeviceBatch.Name).FirstOrDefault();
if (existing == null)
var alreadyExists = Database.DeviceBatches.Any(m => m.Name == model.Name);
if (!alreadyExists)
{
Database.DeviceBatches.Add(model.DeviceBatch);
var batch = new DeviceBatch()
{
Name = model.Name,
PurchaseDate = model.PurchaseDate,
};
Database.DeviceBatches.Add(batch);
Database.SaveChanges();
return RedirectToAction(MVC.Config.DeviceBatch.Index(model.DeviceBatch.Id));
return RedirectToAction(MVC.Config.DeviceBatch.Index(batch.Id));
}
else
{
ModelState.AddModelError("Name", "A Device Batch with this name already exists.");
ModelState.AddModelError(nameof(CreateModel.Name), "A Device Batch with this name already exists.");
}
}
@@ -121,7 +128,7 @@ namespace Disco.Web.Areas.Config.Controllers
[DiscoAuthorize(Claims.Config.DeviceBatch.ShowTimeline)]
public virtual ActionResult Timeline()
{
var m = new Models.DeviceBatch.TimelineModel();
var m = new TimelineModel();
// UI Extensions
UIExtensions.ExecuteExtensions<ConfigDeviceBatchTimelineModel>(ControllerContext, m);
@@ -79,14 +79,7 @@ namespace Disco.Web.Areas.Config.Controllers
public virtual ActionResult Create()
{
// Default Queue
var m = new CreateModel()
{
DeviceFlag = new DeviceFlag()
{
Icon = DeviceFlagService.RandomUnusedIcon(),
IconColour = DeviceFlagService.RandomUnusedThemeColour()
}
};
var m = new CreateModel();
// UI Extensions
UIExtensions.ExecuteExtensions<ConfigDeviceFlagCreateModel>(ControllerContext, m);
@@ -94,16 +87,17 @@ namespace Disco.Web.Areas.Config.Controllers
return View(m);
}
[DiscoAuthorizeAll(Claims.Config.DeviceFlag.Create, Claims.Config.DeviceFlag.Configure), HttpPost]
[DiscoAuthorizeAll(Claims.Config.DeviceFlag.Create, Claims.Config.DeviceFlag.Configure)]
[HttpPost, ValidateAntiForgeryToken]
public virtual ActionResult Create(CreateModel model)
{
if (ModelState.IsValid)
{
// Check for Existing
var existing = Database.DeviceFlags.Where(m => m.Name == model.DeviceFlag.Name).FirstOrDefault();
var existing = Database.DeviceFlags.Where(m => m.Name == model.Name).FirstOrDefault();
if (existing == null)
{
var flag = DeviceFlagService.CreateDeviceFlag(Database, model.DeviceFlag);
var flag = DeviceFlagService.CreateDeviceFlag(Database, model.Name, model.Description);
return RedirectToAction(MVC.Config.DeviceFlag.Index(flag.Id));
}
@@ -105,18 +105,10 @@ namespace Disco.Web.Areas.Config.Controllers
}
[DiscoAuthorizeAll(Claims.Config.DeviceProfile.Create, Claims.Config.DeviceProfile.Configure)]
[HttpGet]
public virtual ActionResult Create()
{
var m = new Models.DeviceProfile.CreateModel()
{
DeviceProfile = new DeviceProfile()
{
ComputerNameTemplate = DeviceProfile.DefaultComputerNameTemplate,
ProvisionADAccount = true,
DistributionType = DeviceProfile.DistributionTypes.OneToMany,
OrganisationalUnit = ActiveDirectory.Context.PrimaryDomain.DefaultComputerContainer
}
};
var m = new Models.DeviceProfile.CreateModel();
// UI Extensions
UIExtensions.ExecuteExtensions<ConfigDeviceProfileCreateModel>(ControllerContext, m);
@@ -124,20 +116,30 @@ namespace Disco.Web.Areas.Config.Controllers
return View(m);
}
[DiscoAuthorizeAll(Claims.Config.DeviceProfile.Create, Claims.Config.DeviceProfile.Configure), HttpPost]
[DiscoAuthorizeAll(Claims.Config.DeviceProfile.Create, Claims.Config.DeviceProfile.Configure)]
[HttpPost, ValidateAntiForgeryToken]
public virtual ActionResult Create(Models.DeviceProfile.CreateModel model)
{
if (ModelState.IsValid)
{
// Check for Existing
var existing = Database.DeviceProfiles.Where(m => m.Name == model.DeviceProfile.Name).FirstOrDefault();
if (existing == null)
var existingName = Database.DeviceProfiles.Any(m => m.Name.Equals(model.Name, StringComparison.OrdinalIgnoreCase));
if (!existingName)
{
model.DeviceProfile.ProvisionADAccount = true;
var deviceProfile = new DeviceProfile()
{
Name = model.Name,
ShortName = model.ShortName,
Description = model.Description,
ProvisionADAccount = true,
ComputerNameTemplate = DeviceProfile.DefaultComputerNameTemplate,
DistributionType = DeviceProfile.DistributionTypes.OneToMany,
OrganisationalUnit = ActiveDirectory.Context.PrimaryDomain.DefaultComputerContainer
};
Database.DeviceProfiles.Add(model.DeviceProfile);
Database.DeviceProfiles.Add(deviceProfile);
Database.SaveChanges();
return RedirectToAction(MVC.Config.DeviceProfile.Index(model.DeviceProfile.Id));
return RedirectToAction(MVC.Config.DeviceProfile.Index(deviceProfile.Id));
}
else
{
@@ -23,7 +23,7 @@ namespace Disco.Web.Areas.Config.Controllers
public partial class DocumentTemplateController : AuthorizedDatabaseController
{
[DiscoAuthorize(Claims.Config.DocumentTemplate.Show)]
public virtual ActionResult Index(string id, string bulkGenerateId = null, string bulkGenerateFilename = null)
public virtual ActionResult Index(string id, Guid? bulkGenerateId = null, string bulkGenerateFilename = null)
{
if (string.IsNullOrEmpty(id))
{
@@ -76,6 +76,7 @@ namespace Disco.Web.Areas.Config.Controllers
}
}
[DiscoAuthorize(Claims.Config.DocumentTemplate.Show)]
public virtual ActionResult ShowPackage(string id)
{
// Document Template Package
@@ -139,7 +140,8 @@ namespace Disco.Web.Areas.Config.Controllers
return View(m);
}
[DiscoAuthorizeAll(Claims.Config.DocumentTemplate.Create, Claims.Config.DocumentTemplate.Configure), HttpPost]
[DiscoAuthorizeAll(Claims.Config.DocumentTemplate.Create, Claims.Config.DocumentTemplate.Configure)]
[HttpPost, ValidateAntiForgeryToken]
public virtual ActionResult Create(CreateModel model)
{
model.UpdateModel(Database);
@@ -147,27 +149,30 @@ namespace Disco.Web.Areas.Config.Controllers
if (ModelState.IsValid)
{
// Check for Existing
var existing = Database.DocumentTemplates.Where(m => m.Id == model.DocumentTemplate.Id).FirstOrDefault();
var existing = Database.DocumentTemplates.Where(m => m.Id == model.Id).FirstOrDefault();
if (existing == null)
{
Database.DocumentTemplates.Add(model.DocumentTemplate);
if (model.DocumentTemplate.Scope == DocumentTemplate.DocumentTemplateScopes.Job)
var template = new DocumentTemplate()
{
model.DocumentTemplate.JobSubTypes = model.GetJobSubTypes();
}
Id = model.Id,
Description = model.Description,
Scope = model.Scope,
};
if (model.Scope == DocumentTemplate.DocumentTemplateScopes.Job)
template.JobSubTypes = model.GetJobSubTypes();
Database.DocumentTemplates.Add(template);
Database.SaveChanges();
// Save Template
model.DocumentTemplate.SavePdfTemplate(Database, model.Template.InputStream);
template.SavePdfTemplate(Database, model.Template.InputStream);
return RedirectToAction(MVC.Config.DocumentTemplate.Index(model.DocumentTemplate.Id));
return RedirectToAction(MVC.Config.DocumentTemplate.Index(template.Id));
}
else
{
ModelState.AddModelError("Id", "A Document Template with this Id already exists.");
ModelState.AddModelError(nameof(DocumentTemplate.Id), "A Document Template with this Id already exists.");
}
}
@@ -188,18 +193,19 @@ namespace Disco.Web.Areas.Config.Controllers
return View(m);
}
[DiscoAuthorizeAll(Claims.Config.DocumentTemplate.Create, Claims.Config.DocumentTemplate.Configure), HttpPost]
[DiscoAuthorizeAll(Claims.Config.DocumentTemplate.Create, Claims.Config.DocumentTemplate.Configure)]
[HttpPost, ValidateAntiForgeryToken]
public virtual ActionResult CreatePackage(CreatePackageModel model)
{
if (ModelState.IsValid)
{
// Check for Existing
var existing = DocumentTemplatePackages.GetPackage(model.Package.Id);
var existing = DocumentTemplatePackages.GetPackage(model.Id);
if (existing == null)
{
DocumentTemplatePackages.CreatePackage(model.Package);
DocumentTemplatePackages.CreatePackage(model.Id, model.Description, model.Scope);
return RedirectToAction(MVC.Config.DocumentTemplate.ShowPackage(model.Package.Id));
return RedirectToAction(MVC.Config.DocumentTemplate.ShowPackage(model.Id));
}
else
{
@@ -78,18 +78,11 @@ namespace Disco.Web.Areas.Config.Controllers
}
[DiscoAuthorizeAll(Claims.Config.JobQueue.Create, Claims.Config.JobQueue.Configure)]
[HttpGet]
public virtual ActionResult Create()
{
// Default Queue
var m = new Models.JobQueue.CreateModel()
{
JobQueue = new JobQueue()
{
Icon = JobQueueService.RandomUnusedIcon(),
IconColour = JobQueueService.RandomUnusedThemeColour(),
Priority = JobQueuePriority.Normal
}
};
var m = new Models.JobQueue.CreateModel();
// UI Extensions
UIExtensions.ExecuteExtensions<ConfigJobQueueCreateModel>(ControllerContext, m);
@@ -97,16 +90,17 @@ namespace Disco.Web.Areas.Config.Controllers
return View(m);
}
[DiscoAuthorizeAll(Claims.Config.JobQueue.Create, Claims.Config.JobQueue.Configure), HttpPost]
[DiscoAuthorizeAll(Claims.Config.JobQueue.Create, Claims.Config.JobQueue.Configure)]
[HttpPost, ValidateAntiForgeryToken]
public virtual ActionResult Create(Models.JobQueue.CreateModel model)
{
if (ModelState.IsValid)
{
// Check for Existing
var existing = Database.JobQueues.Where(m => m.Name == model.JobQueue.Name).FirstOrDefault();
if (existing == null)
var nameExists = Database.JobQueues.Any(m => m.Name.Equals(model.Name, StringComparison.Ordinal));
if (!nameExists)
{
var token = JobQueueService.CreateJobQueue(Database, model.JobQueue);
var token = JobQueueService.CreateJobQueue(Database, model.Name, model.Description);
return RedirectToAction(MVC.Config.JobQueue.Index(token.JobQueue.Id));
}
@@ -23,7 +23,8 @@ namespace Disco.Web.Areas.Config.Controllers
}
#region Plugin Configuration
[DiscoAuthorize(Claims.Config.Plugin.Configure), HttpPost, ValidateInput(false)]
[DiscoAuthorize(Claims.Config.Plugin.Configure), ValidateInput(false)]
[HttpPost, ValidateAntiForgeryToken]
public virtual ActionResult Configure(string PluginId, FormCollection form)
{
if (string.IsNullOrEmpty(PluginId))
@@ -1,5 +1,4 @@
using Disco.Models.Areas.Config.UI.UserFlag;
using Disco.Models.Repository;
using Disco.Models.Services.Users.UserFlags;
using Disco.Models.UI.Config.UserFlag;
using Disco.Services.Authorization;
@@ -76,17 +75,11 @@ namespace Disco.Web.Areas.Config.Controllers
}
[DiscoAuthorizeAll(Claims.Config.UserFlag.Create, Claims.Config.UserFlag.Configure)]
[HttpGet]
public virtual ActionResult Create()
{
// Default Queue
var m = new CreateModel()
{
UserFlag = new UserFlag()
{
Icon = UserFlagService.RandomUnusedIcon(),
IconColour = UserFlagService.RandomUnusedThemeColour()
}
};
var m = new CreateModel();
// UI Extensions
UIExtensions.ExecuteExtensions<ConfigUserFlagCreateModel>(ControllerContext, m);
@@ -94,22 +87,23 @@ namespace Disco.Web.Areas.Config.Controllers
return View(m);
}
[DiscoAuthorizeAll(Claims.Config.UserFlag.Create, Claims.Config.UserFlag.Configure), HttpPost]
[DiscoAuthorizeAll(Claims.Config.UserFlag.Create, Claims.Config.UserFlag.Configure)]
[HttpPost, ValidateAntiForgeryToken]
public virtual ActionResult Create(CreateModel model)
{
if (ModelState.IsValid)
{
// Check for Existing
var existing = Database.UserFlags.Where(m => m.Name == model.UserFlag.Name).FirstOrDefault();
if (existing == null)
var nameExists = Database.UserFlags.Any(m => m.Name.Equals(model.Name, StringComparison.Ordinal));
if (!nameExists)
{
var flag = UserFlagService.CreateUserFlag(Database, model.UserFlag);
var flag = UserFlagService.CreateUserFlag(Database, model.Name, model.Description);
return RedirectToAction(MVC.Config.UserFlag.Index(flag.Id));
}
else
{
ModelState.AddModelError("Name", "A User Flag with this name already exists.");
ModelState.AddModelError(nameof(CreateModel.Name), "A User Flag with this name already exists.");
}
}