// ========================================================================== // Squidex Headless CMS // ========================================================================== // Copyright (c) Squidex UG (haftungsbeschränkt) // All rights reserved. Licensed under the MIT license. // ========================================================================== using System.Threading.Tasks; using Microsoft.AspNetCore.Mvc; using Microsoft.Net.Http.Headers; using Squidex.Areas.Api.Controllers.Apps.Models; using Squidex.Domain.Apps.Entities.Apps; using Squidex.Domain.Apps.Entities.Apps.Commands; using Squidex.Domain.Apps.Entities.Apps.Invitation; using Squidex.Domain.Apps.Entities.Apps.Services; using Squidex.Infrastructure.Commands; using Squidex.Shared; using Squidex.Web; namespace Squidex.Areas.Api.Controllers.Apps { /// /// Manages and configures apps. /// [ApiExplorerSettings(GroupName = nameof(Apps))] public sealed class AppContributorsController : ApiController { private readonly IAppPlansProvider appPlansProvider; public AppContributorsController(ICommandBus commandBus, IAppPlansProvider appPlansProvider) : base(commandBus) { this.appPlansProvider = appPlansProvider; } /// /// Get app contributors. /// /// The name of the app. /// /// 200 => App contributors returned. /// 404 => App not found. /// [HttpGet] [Route("apps/{app}/contributors/")] [ProducesResponseType(typeof(ContributorsDto), 200)] [ApiPermission(Permissions.AppContributorsRead)] [ApiCosts(0)] public IActionResult GetContributors(string app) { var response = ContributorsDto.FromApp(App, appPlansProvider, this, false); Response.Headers[HeaderNames.ETag] = App.Version.ToString(); return Ok(response); } /// /// Assign contributor to app. /// /// The name of the app. /// Contributor object that needs to be added to the app. /// /// 201 => User assigned to app. /// 400 => User is already assigned to the app or not found. /// 404 => App not found. /// [HttpPost] [Route("apps/{app}/contributors/")] [ProducesResponseType(typeof(ContributorsDto), 200)] [ProducesResponseType(typeof(ErrorDto), 400)] [ApiPermission(Permissions.AppContributorsAssign)] [ApiCosts(1)] public async Task PostContributor(string app, [FromBody] AssignContributorDto request) { var command = request.ToCommand(); var context = await CommandBus.PublishAsync(command); var response = (ContributorsDto)null; if (context.PlainResult is IAppEntity newApp) { response = ContributorsDto.FromApp(newApp, appPlansProvider, this, false); } else if (context.PlainResult is InvitedResult invited) { response = ContributorsDto.FromApp(invited.App, appPlansProvider, this, true); } return CreatedAtAction(nameof(GetContributors), new { app }, response); } /// /// Remove contributor from app. /// /// The name of the app. /// The id of the contributor. /// /// 200 => User removed from app. /// 400 => User is not assigned to the app. /// 404 => Contributor or app not found. /// [HttpDelete] [Route("apps/{app}/contributors/{id}/")] [ProducesResponseType(typeof(ContributorsDto), 200)] [ProducesResponseType(typeof(ErrorDto), 400)] [ApiPermission(Permissions.AppContributorsRevoke)] [ApiCosts(1)] public async Task DeleteContributor(string app, string id) { var command = new RemoveContributor { ContributorId = id }; var response = await InvokeCommandAsync(command); return Ok(response); } private async Task InvokeCommandAsync(ICommand command) { var context = await CommandBus.PublishAsync(command); var result = context.Result(); var response = ContributorsDto.FromApp(result, appPlansProvider, this, false); return response; } } }