mirror of https://github.com/abpframework/abp.git
72 changed files with 2767 additions and 421 deletions
@ -1,3 +1,3 @@ |
|||
{ |
|||
"ConnectionString": "Server=localhost;Database=VoloDocs;Trusted_Connection=True;TrustServerCertificate=True" |
|||
"ConnectionString": "Server=localhost;Database=VoloDocs;user=sa;password=admin@123456;TrustServerCertificate=True" |
|||
} |
|||
@ -0,0 +1,12 @@ |
|||
using System; |
|||
|
|||
namespace Volo.Docs.Admin.Projects; |
|||
|
|||
public class DeletePdfFileInput |
|||
{ |
|||
public Guid Id { get; set; } |
|||
|
|||
public string Version { get; set; } |
|||
|
|||
public string LanguageCode { get; set; } |
|||
} |
|||
File diff suppressed because it is too large
@ -0,0 +1,47 @@ |
|||
@page |
|||
@using Microsoft.AspNetCore.Mvc.Localization |
|||
@using Volo.Abp.AspNetCore.Mvc.UI.Bootstrap.TagHelpers.Modal |
|||
@using Volo.Docs.Admin.Pages.Docs.Admin.Projects; |
|||
@using Volo.Docs.Localization |
|||
@model GeneratePdfModal |
|||
@inject IHtmlLocalizer<DocsResource> L |
|||
@{ |
|||
Layout = null; |
|||
} |
|||
|
|||
<abp-modal> |
|||
<abp-modal-header title="@(L["GeneratePdf"].Value + " - " + Model.ViewModel.ShortName)"></abp-modal-header> |
|||
<abp-modal-body> |
|||
<input id="ProjectId" name="ProjectId" value="@Model.ViewModel.ProjectId" hidden/> |
|||
<input id="ShortName" name="ShortName" value="@Model.ViewModel.ShortName" hidden/> |
|||
<div class="mb-3"> |
|||
<label class="form-label" for="Version">@L["Version"]</label> |
|||
<select name="Version" id="Version" class="form-select mt-2"> |
|||
@foreach (var version in Model.ViewModel.Versions) |
|||
{ |
|||
<option value="@version.Value">@version.Value</option> |
|||
} |
|||
</select> |
|||
</div> |
|||
<div class="mb-3"> |
|||
<label class="form-label" for="Language">@L["Language"]</label> |
|||
<select name="Language" id="Language" class="form-select mt-2"> |
|||
@foreach (var language in Model.ViewModel.Languages) |
|||
{ |
|||
<option value="@language.Value">@language.Value</option> |
|||
} |
|||
</select> |
|||
</div> |
|||
<div class="form-check mb-3"> |
|||
<label class="form-check-label" for="ForceToGenerate"> |
|||
<input id="ForceToGenerate" type="checkbox" class="form-check-input" /> |
|||
@L["ForceToGenerateNewPdf"] |
|||
</label> |
|||
</div> |
|||
</abp-modal-body> |
|||
<abp-modal-footer buttons="@(AbpModalButtons.None)"> |
|||
<button type="button" class="btn btn-sm btn-link" data-bs-dismiss="modal">@L["Close"]</button> |
|||
<button type="button" class="btn btn-sm btn-outline-primary" id="GeneratePdfBtn" data-busy-text="@L["Generating"].Value"><span>@L["GeneratePdf"]</span></button> |
|||
<button type="button" class="btn btn-sm btn-primary" id="GenerateAndDownloadPdfBtn">@L["GenerateAndDownloadPdf"]</button> |
|||
</abp-modal-footer> |
|||
</abp-modal> |
|||
@ -0,0 +1,62 @@ |
|||
using System; |
|||
using System.Collections.Generic; |
|||
using System.Linq; |
|||
using System.Threading.Tasks; |
|||
using Microsoft.AspNetCore.Mvc; |
|||
using Microsoft.AspNetCore.Mvc.Rendering; |
|||
using Volo.Docs.Admin.Projects; |
|||
using Volo.Docs.Common.Documents; |
|||
using Volo.Docs.Common.Projects; |
|||
using Volo.Docs.Projects; |
|||
|
|||
namespace Volo.Docs.Admin.Pages.Docs.Admin.Projects; |
|||
|
|||
public class GeneratePdfModal : DocsAdminPageModel |
|||
{ |
|||
protected IDocumentPdfGeneratorAppService DocumentPdfGeneratorAppService { get; } |
|||
protected IProjectAppService ProjectAppService { get; } |
|||
protected IProjectAdminAppService ProjectAdminAppService { get; } |
|||
|
|||
public GeneratePdfViewModel ViewModel { get; set; } |
|||
|
|||
public GeneratePdfModal( |
|||
IDocumentPdfGeneratorAppService documentPdfGeneratorAppService, |
|||
IProjectAppService projectAppService, |
|||
IProjectAdminAppService projectAdminAppService) |
|||
{ |
|||
DocumentPdfGeneratorAppService = documentPdfGeneratorAppService; |
|||
ProjectAppService = projectAppService; |
|||
ProjectAdminAppService = projectAdminAppService; |
|||
} |
|||
|
|||
public virtual async Task<IActionResult> OnGetAsync(Guid id) |
|||
{ |
|||
var project = await ProjectAdminAppService.GetAsync(id); |
|||
var versions = await ProjectAppService.GetVersionsAsync(project.ShortName); |
|||
if(versions.Items.Count == 0) |
|||
{ |
|||
versions.Items = |
|||
[ |
|||
new VersionInfoDto { Name = ProjectConsts.Latest, DisplayName = ProjectConsts.Latest } |
|||
]; |
|||
} |
|||
var languages = await ProjectAppService.GetLanguageListAsync(project.ShortName, versions.Items.FirstOrDefault()?.Name); |
|||
ViewModel = new GeneratePdfViewModel |
|||
{ |
|||
ProjectId = id, |
|||
ShortName = project.ShortName, |
|||
Versions = versions.Items.Select(x => new SelectListItem(x.DisplayName, x.Name)).ToList(), |
|||
Languages = languages.Languages.Select(x => new SelectListItem(x.DisplayName, x.Code)).ToList() |
|||
}; |
|||
|
|||
return Page(); |
|||
} |
|||
|
|||
public class GeneratePdfViewModel |
|||
{ |
|||
public Guid ProjectId { get; set; } |
|||
public string ShortName { get; set; } |
|||
public List<SelectListItem> Versions { get; set; } |
|||
public List<SelectListItem> Languages { get; set; } |
|||
} |
|||
} |
|||
@ -0,0 +1,67 @@ |
|||
var abp = abp || {}; |
|||
$(function () { |
|||
abp.modals.projectGeneratePdf = function () { |
|||
|
|||
var projectAppService = volo.docs.projects.docsProject; |
|||
var pdfGeneratorAppService = volo.docs.documents.docsDocumentPdfGenerator; |
|||
var projectAdminAppService = volo.docs.admin.projectsAdmin; |
|||
|
|||
var initModal = function (publicApi, args) { |
|||
|
|||
}; |
|||
|
|||
$("#Versions").change(function () { |
|||
var shortname = $("#ShortName").val(); |
|||
var version = $("#Version").val(); |
|||
projectAppService.getLanguageList(shortname, version).done(function (result) { |
|||
$("#Language").empty(); |
|||
$.each(result.languages, function (index, item) { |
|||
$("#Language").append($(`<option value="${item.code}">${item.displayName}</option>`)); |
|||
}); |
|||
}); |
|||
}) |
|||
|
|||
$("#GeneratePdfBtn").click(function () { |
|||
var $btn = $(this); |
|||
$btn.buttonBusy(true); |
|||
var input = { |
|||
projectId: $("#ProjectId").val(), |
|||
version: $("#Version").val(), |
|||
languageCode: $("#Language").val(), |
|||
} |
|||
tryDeletePdfFile(input); |
|||
pdfGeneratorAppService.generatePdf(input, { |
|||
abpHandleError : false, |
|||
error: function (jqXHR) { |
|||
if (jqXHR.status === 200) { |
|||
abp.message.success("PDF generated successfully."); |
|||
$btn.buttonBusy(false); |
|||
} else { |
|||
abp.ajax.handleErrorStatusCode(jqXHR.status); |
|||
} |
|||
} |
|||
}); |
|||
}) |
|||
|
|||
$("#GenerateAndDownloadPdfBtn").click(function () { |
|||
var input = { |
|||
projectId: $("#ProjectId").val(), |
|||
version: $("#Version").val(), |
|||
languageCode: $("#Language").val(), |
|||
} |
|||
tryDeletePdfFile(input); |
|||
window.open(abp.appPath + 'api/docs/documents/pdf' + abp.utils.buildQueryString([{ name: 'projectId', value: input.projectId }, { name: 'version', value: input.version }, { name: 'languageCode', value: input.languageCode }]), '_blank'); |
|||
}) |
|||
|
|||
function tryDeletePdfFile(input) { |
|||
var forceToGenerate = $("#ForceToGenerate").is(":checked"); |
|||
if(forceToGenerate) { |
|||
projectAdminAppService.deletePdfFile(input); |
|||
} |
|||
} |
|||
|
|||
return { |
|||
initModal: initModal, |
|||
}; |
|||
}; |
|||
}); |
|||
@ -0,0 +1,68 @@ |
|||
/* This file is automatically generated by ABP framework to use MVC Controllers from javascript. */ |
|||
|
|||
|
|||
// module docs-common
|
|||
|
|||
(function(){ |
|||
|
|||
// controller volo.docs.documents.docsDocumentPdfGenerator
|
|||
|
|||
(function(){ |
|||
|
|||
abp.utils.createNamespace(window, 'volo.docs.documents.docsDocumentPdfGenerator'); |
|||
|
|||
volo.docs.documents.docsDocumentPdfGenerator.generatePdf = function(input, ajaxParams) { |
|||
return abp.ajax($.extend(true, { |
|||
url: abp.appPath + 'api/docs/documents/pdf' + abp.utils.buildQueryString([{ name: 'projectId', value: input.projectId }, { name: 'version', value: input.version }, { name: 'languageCode', value: input.languageCode }]) + '', |
|||
type: 'GET' |
|||
}, ajaxParams)); |
|||
}; |
|||
|
|||
})(); |
|||
|
|||
// controller volo.docs.projects.docsProject
|
|||
|
|||
(function(){ |
|||
|
|||
abp.utils.createNamespace(window, 'volo.docs.projects.docsProject'); |
|||
|
|||
volo.docs.projects.docsProject.getList = function(ajaxParams) { |
|||
return abp.ajax($.extend(true, { |
|||
url: abp.appPath + 'api/docs/projects', |
|||
type: 'GET' |
|||
}, ajaxParams)); |
|||
}; |
|||
|
|||
volo.docs.projects.docsProject.get = function(shortName, ajaxParams) { |
|||
return abp.ajax($.extend(true, { |
|||
url: abp.appPath + 'api/docs/projects/' + shortName + '', |
|||
type: 'GET' |
|||
}, ajaxParams)); |
|||
}; |
|||
|
|||
volo.docs.projects.docsProject.getDefaultLanguageCode = function(shortName, version, ajaxParams) { |
|||
return abp.ajax($.extend(true, { |
|||
url: abp.appPath + 'api/docs/projects/' + shortName + '/defaultLanguage' + abp.utils.buildQueryString([{ name: 'version', value: version }]) + '', |
|||
type: 'GET' |
|||
}, { dataType: 'text' }, ajaxParams)); |
|||
}; |
|||
|
|||
volo.docs.projects.docsProject.getVersions = function(shortName, ajaxParams) { |
|||
return abp.ajax($.extend(true, { |
|||
url: abp.appPath + 'api/docs/projects/' + shortName + '/versions', |
|||
type: 'GET' |
|||
}, ajaxParams)); |
|||
}; |
|||
|
|||
volo.docs.projects.docsProject.getLanguageList = function(shortName, version, ajaxParams) { |
|||
return abp.ajax($.extend(true, { |
|||
url: abp.appPath + 'api/docs/projects/' + shortName + '/' + version + '/languageList', |
|||
type: 'GET' |
|||
}, ajaxParams)); |
|||
}; |
|||
|
|||
})(); |
|||
|
|||
})(); |
|||
|
|||
|
|||
@ -1,4 +1,4 @@ |
|||
namespace Volo.Docs.Projects |
|||
namespace Volo.Docs.Common.Projects |
|||
{ |
|||
public class VersionInfoDto |
|||
{ |
|||
@ -0,0 +1,14 @@ |
|||
using Volo.Abp.Application.Services; |
|||
using Volo.Docs.Localization; |
|||
|
|||
namespace Volo.Docs.Common |
|||
{ |
|||
public abstract class DocsCommonAppServiceBase : ApplicationService |
|||
{ |
|||
protected DocsCommonAppServiceBase() |
|||
{ |
|||
ObjectMapperContext = typeof(DocsCommonApplicationModule); |
|||
LocalizationResource = typeof(DocsResource); |
|||
} |
|||
} |
|||
} |
|||
@ -0,0 +1,15 @@ |
|||
using AutoMapper; |
|||
using Volo.Docs.Common.Projects; |
|||
using Volo.Docs.Projects; |
|||
|
|||
namespace Volo.Docs.Common |
|||
{ |
|||
public class DocsCommonApplicationAutoMapperProfile : Profile |
|||
{ |
|||
public DocsCommonApplicationAutoMapperProfile() |
|||
{ |
|||
CreateMap<Project, ProjectDto>(); |
|||
CreateMap<VersionInfo, VersionInfoDto>(); |
|||
} |
|||
} |
|||
} |
|||
@ -0,0 +1,28 @@ |
|||
// This file is automatically generated by ABP framework to use MVC Controllers from CSharp
|
|||
using System; |
|||
using System.Collections.Generic; |
|||
using System.Threading.Tasks; |
|||
using Volo.Abp; |
|||
using Volo.Abp.Application.Dtos; |
|||
using Volo.Abp.Content; |
|||
using Volo.Abp.DependencyInjection; |
|||
using Volo.Abp.Http.Client; |
|||
using Volo.Abp.Http.Client.ClientProxying; |
|||
using Volo.Abp.Http.Modeling; |
|||
using Volo.Docs.Common.Documents; |
|||
|
|||
// ReSharper disable once CheckNamespace
|
|||
namespace Volo.Docs.Documents; |
|||
|
|||
[Dependency(ReplaceServices = true)] |
|||
[ExposeServices(typeof(IDocumentPdfGeneratorAppService), typeof(DocsDocumentPdfGeneratorClientProxy))] |
|||
public partial class DocsDocumentPdfGeneratorClientProxy : ClientProxyBase<IDocumentPdfGeneratorAppService>, IDocumentPdfGeneratorAppService |
|||
{ |
|||
public virtual async Task<IRemoteStreamContent> GeneratePdfAsync(DocumentPdfGeneratorInput input) |
|||
{ |
|||
return await RequestAsync<IRemoteStreamContent>(nameof(GeneratePdfAsync), new ClientProxyRequestTypeValue |
|||
{ |
|||
{ typeof(DocumentPdfGeneratorInput), input } |
|||
}); |
|||
} |
|||
} |
|||
@ -0,0 +1,7 @@ |
|||
// This file is part of DocsDocumentPdfGeneratorClientProxy, you can customize it here
|
|||
// ReSharper disable once CheckNamespace
|
|||
namespace Volo.Docs.Documents; |
|||
|
|||
public partial class DocsDocumentPdfGeneratorClientProxy |
|||
{ |
|||
} |
|||
@ -0,0 +1,420 @@ |
|||
{ |
|||
"modules": { |
|||
"docs-common": { |
|||
"rootPath": "docs-common", |
|||
"remoteServiceName": "AbpDocsCommon", |
|||
"controllers": { |
|||
"Volo.Docs.Documents.DocsDocumentPdfGeneratorController": { |
|||
"controllerName": "DocsDocumentPdfGenerator", |
|||
"controllerGroupName": "Document", |
|||
"isRemoteService": true, |
|||
"isIntegrationService": false, |
|||
"apiVersion": null, |
|||
"type": "Volo.Docs.Documents.DocsDocumentPdfGeneratorController", |
|||
"interfaces": [ |
|||
{ |
|||
"type": "Volo.Docs.Common.Documents.IDocumentPdfGeneratorAppService", |
|||
"name": "IDocumentPdfGeneratorAppService", |
|||
"methods": [ |
|||
{ |
|||
"name": "GeneratePdfAsync", |
|||
"parametersOnMethod": [ |
|||
{ |
|||
"name": "input", |
|||
"typeAsString": "Volo.Docs.Common.Documents.DocumentPdfGeneratorInput, Volo.Docs.Common.Application.Contracts", |
|||
"type": "Volo.Docs.Common.Documents.DocumentPdfGeneratorInput", |
|||
"typeSimple": "Volo.Docs.Common.Documents.DocumentPdfGeneratorInput", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
} |
|||
], |
|||
"returnValue": { |
|||
"type": "Volo.Abp.Content.IRemoteStreamContent", |
|||
"typeSimple": "Volo.Abp.Content.IRemoteStreamContent" |
|||
} |
|||
} |
|||
] |
|||
} |
|||
], |
|||
"actions": { |
|||
"GeneratePdfAsyncByInput": { |
|||
"uniqueName": "GeneratePdfAsyncByInput", |
|||
"name": "GeneratePdfAsync", |
|||
"httpMethod": "GET", |
|||
"url": "api/docs/documents/pdf", |
|||
"supportedVersions": [], |
|||
"parametersOnMethod": [ |
|||
{ |
|||
"name": "input", |
|||
"typeAsString": "Volo.Docs.Common.Documents.DocumentPdfGeneratorInput, Volo.Docs.Common.Application.Contracts", |
|||
"type": "Volo.Docs.Common.Documents.DocumentPdfGeneratorInput", |
|||
"typeSimple": "Volo.Docs.Common.Documents.DocumentPdfGeneratorInput", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
} |
|||
], |
|||
"parameters": [ |
|||
{ |
|||
"nameOnMethod": "input", |
|||
"name": "ProjectId", |
|||
"jsonName": null, |
|||
"type": "System.Guid", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null, |
|||
"constraintTypes": null, |
|||
"bindingSourceId": "ModelBinding", |
|||
"descriptorName": "input" |
|||
}, |
|||
{ |
|||
"nameOnMethod": "input", |
|||
"name": "Version", |
|||
"jsonName": null, |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null, |
|||
"constraintTypes": null, |
|||
"bindingSourceId": "ModelBinding", |
|||
"descriptorName": "input" |
|||
}, |
|||
{ |
|||
"nameOnMethod": "input", |
|||
"name": "LanguageCode", |
|||
"jsonName": null, |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null, |
|||
"constraintTypes": null, |
|||
"bindingSourceId": "ModelBinding", |
|||
"descriptorName": "input" |
|||
} |
|||
], |
|||
"returnValue": { |
|||
"type": "Volo.Abp.Content.IRemoteStreamContent", |
|||
"typeSimple": "Volo.Abp.Content.IRemoteStreamContent" |
|||
}, |
|||
"allowAnonymous": null, |
|||
"implementFrom": "Volo.Docs.Common.Documents.IDocumentPdfGeneratorAppService" |
|||
} |
|||
} |
|||
}, |
|||
"Volo.Docs.Projects.DocsProjectController": { |
|||
"controllerName": "DocsProject", |
|||
"controllerGroupName": "Project", |
|||
"isRemoteService": true, |
|||
"isIntegrationService": false, |
|||
"apiVersion": null, |
|||
"type": "Volo.Docs.Projects.DocsProjectController", |
|||
"interfaces": [ |
|||
{ |
|||
"type": "Volo.Docs.Common.Projects.IProjectAppService", |
|||
"name": "IProjectAppService", |
|||
"methods": [ |
|||
{ |
|||
"name": "GetListAsync", |
|||
"parametersOnMethod": [], |
|||
"returnValue": { |
|||
"type": "Volo.Abp.Application.Dtos.ListResultDto<Volo.Docs.Common.Projects.ProjectDto>", |
|||
"typeSimple": "Volo.Abp.Application.Dtos.ListResultDto<Volo.Docs.Common.Projects.ProjectDto>" |
|||
} |
|||
}, |
|||
{ |
|||
"name": "GetAsync", |
|||
"parametersOnMethod": [ |
|||
{ |
|||
"name": "shortName", |
|||
"typeAsString": "System.String, System.Private.CoreLib", |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
} |
|||
], |
|||
"returnValue": { |
|||
"type": "Volo.Docs.Common.Projects.ProjectDto", |
|||
"typeSimple": "Volo.Docs.Common.Projects.ProjectDto" |
|||
} |
|||
}, |
|||
{ |
|||
"name": "GetVersionsAsync", |
|||
"parametersOnMethod": [ |
|||
{ |
|||
"name": "shortName", |
|||
"typeAsString": "System.String, System.Private.CoreLib", |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
} |
|||
], |
|||
"returnValue": { |
|||
"type": "Volo.Abp.Application.Dtos.ListResultDto<Volo.Docs.Common.Projects.VersionInfoDto>", |
|||
"typeSimple": "Volo.Abp.Application.Dtos.ListResultDto<Volo.Docs.Common.Projects.VersionInfoDto>" |
|||
} |
|||
}, |
|||
{ |
|||
"name": "GetDefaultLanguageCodeAsync", |
|||
"parametersOnMethod": [ |
|||
{ |
|||
"name": "shortName", |
|||
"typeAsString": "System.String, System.Private.CoreLib", |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
}, |
|||
{ |
|||
"name": "version", |
|||
"typeAsString": "System.String, System.Private.CoreLib", |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
} |
|||
], |
|||
"returnValue": { |
|||
"type": "System.String", |
|||
"typeSimple": "string" |
|||
} |
|||
}, |
|||
{ |
|||
"name": "GetLanguageListAsync", |
|||
"parametersOnMethod": [ |
|||
{ |
|||
"name": "shortName", |
|||
"typeAsString": "System.String, System.Private.CoreLib", |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
}, |
|||
{ |
|||
"name": "version", |
|||
"typeAsString": "System.String, System.Private.CoreLib", |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
} |
|||
], |
|||
"returnValue": { |
|||
"type": "Volo.Docs.Documents.LanguageConfig", |
|||
"typeSimple": "Volo.Docs.Documents.LanguageConfig" |
|||
} |
|||
} |
|||
] |
|||
} |
|||
], |
|||
"actions": { |
|||
"GetListAsync": { |
|||
"uniqueName": "GetListAsync", |
|||
"name": "GetListAsync", |
|||
"httpMethod": "GET", |
|||
"url": "api/docs/projects", |
|||
"supportedVersions": [], |
|||
"parametersOnMethod": [], |
|||
"parameters": [], |
|||
"returnValue": { |
|||
"type": "Volo.Abp.Application.Dtos.ListResultDto<Volo.Docs.Common.Projects.ProjectDto>", |
|||
"typeSimple": "Volo.Abp.Application.Dtos.ListResultDto<Volo.Docs.Common.Projects.ProjectDto>" |
|||
}, |
|||
"allowAnonymous": null, |
|||
"implementFrom": "Volo.Docs.Common.Projects.IProjectAppService" |
|||
}, |
|||
"GetAsyncByShortName": { |
|||
"uniqueName": "GetAsyncByShortName", |
|||
"name": "GetAsync", |
|||
"httpMethod": "GET", |
|||
"url": "api/docs/projects/{shortName}", |
|||
"supportedVersions": [], |
|||
"parametersOnMethod": [ |
|||
{ |
|||
"name": "shortName", |
|||
"typeAsString": "System.String, System.Private.CoreLib", |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
} |
|||
], |
|||
"parameters": [ |
|||
{ |
|||
"nameOnMethod": "shortName", |
|||
"name": "shortName", |
|||
"jsonName": null, |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null, |
|||
"constraintTypes": [], |
|||
"bindingSourceId": "Path", |
|||
"descriptorName": "" |
|||
} |
|||
], |
|||
"returnValue": { |
|||
"type": "Volo.Docs.Common.Projects.ProjectDto", |
|||
"typeSimple": "Volo.Docs.Common.Projects.ProjectDto" |
|||
}, |
|||
"allowAnonymous": null, |
|||
"implementFrom": "Volo.Docs.Common.Projects.IProjectAppService" |
|||
}, |
|||
"GetDefaultLanguageCodeAsyncByShortNameAndVersion": { |
|||
"uniqueName": "GetDefaultLanguageCodeAsyncByShortNameAndVersion", |
|||
"name": "GetDefaultLanguageCodeAsync", |
|||
"httpMethod": "GET", |
|||
"url": "api/docs/projects/{shortName}/defaultLanguage", |
|||
"supportedVersions": [], |
|||
"parametersOnMethod": [ |
|||
{ |
|||
"name": "shortName", |
|||
"typeAsString": "System.String, System.Private.CoreLib", |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
}, |
|||
{ |
|||
"name": "version", |
|||
"typeAsString": "System.String, System.Private.CoreLib", |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
} |
|||
], |
|||
"parameters": [ |
|||
{ |
|||
"nameOnMethod": "shortName", |
|||
"name": "shortName", |
|||
"jsonName": null, |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null, |
|||
"constraintTypes": [], |
|||
"bindingSourceId": "Path", |
|||
"descriptorName": "" |
|||
}, |
|||
{ |
|||
"nameOnMethod": "version", |
|||
"name": "version", |
|||
"jsonName": null, |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null, |
|||
"constraintTypes": null, |
|||
"bindingSourceId": "ModelBinding", |
|||
"descriptorName": "" |
|||
} |
|||
], |
|||
"returnValue": { |
|||
"type": "System.String", |
|||
"typeSimple": "string" |
|||
}, |
|||
"allowAnonymous": null, |
|||
"implementFrom": "Volo.Docs.Common.Projects.IProjectAppService" |
|||
}, |
|||
"GetVersionsAsyncByShortName": { |
|||
"uniqueName": "GetVersionsAsyncByShortName", |
|||
"name": "GetVersionsAsync", |
|||
"httpMethod": "GET", |
|||
"url": "api/docs/projects/{shortName}/versions", |
|||
"supportedVersions": [], |
|||
"parametersOnMethod": [ |
|||
{ |
|||
"name": "shortName", |
|||
"typeAsString": "System.String, System.Private.CoreLib", |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
} |
|||
], |
|||
"parameters": [ |
|||
{ |
|||
"nameOnMethod": "shortName", |
|||
"name": "shortName", |
|||
"jsonName": null, |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null, |
|||
"constraintTypes": [], |
|||
"bindingSourceId": "Path", |
|||
"descriptorName": "" |
|||
} |
|||
], |
|||
"returnValue": { |
|||
"type": "Volo.Abp.Application.Dtos.ListResultDto<Volo.Docs.Common.Projects.VersionInfoDto>", |
|||
"typeSimple": "Volo.Abp.Application.Dtos.ListResultDto<Volo.Docs.Common.Projects.VersionInfoDto>" |
|||
}, |
|||
"allowAnonymous": null, |
|||
"implementFrom": "Volo.Docs.Common.Projects.IProjectAppService" |
|||
}, |
|||
"GetLanguageListAsyncByShortNameAndVersion": { |
|||
"uniqueName": "GetLanguageListAsyncByShortNameAndVersion", |
|||
"name": "GetLanguageListAsync", |
|||
"httpMethod": "GET", |
|||
"url": "api/docs/projects/{shortName}/{version}/languageList", |
|||
"supportedVersions": [], |
|||
"parametersOnMethod": [ |
|||
{ |
|||
"name": "shortName", |
|||
"typeAsString": "System.String, System.Private.CoreLib", |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
}, |
|||
{ |
|||
"name": "version", |
|||
"typeAsString": "System.String, System.Private.CoreLib", |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null |
|||
} |
|||
], |
|||
"parameters": [ |
|||
{ |
|||
"nameOnMethod": "shortName", |
|||
"name": "shortName", |
|||
"jsonName": null, |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null, |
|||
"constraintTypes": [], |
|||
"bindingSourceId": "Path", |
|||
"descriptorName": "" |
|||
}, |
|||
{ |
|||
"nameOnMethod": "version", |
|||
"name": "version", |
|||
"jsonName": null, |
|||
"type": "System.String", |
|||
"typeSimple": "string", |
|||
"isOptional": false, |
|||
"defaultValue": null, |
|||
"constraintTypes": [], |
|||
"bindingSourceId": "Path", |
|||
"descriptorName": "" |
|||
} |
|||
], |
|||
"returnValue": { |
|||
"type": "Volo.Docs.Documents.LanguageConfig", |
|||
"typeSimple": "Volo.Docs.Documents.LanguageConfig" |
|||
}, |
|||
"allowAnonymous": null, |
|||
"implementFrom": "Volo.Docs.Common.Projects.IProjectAppService" |
|||
} |
|||
} |
|||
} |
|||
} |
|||
} |
|||
}, |
|||
"types": {} |
|||
} |
|||
@ -0,0 +1,25 @@ |
|||
using Microsoft.Extensions.DependencyInjection; |
|||
using Volo.Abp.Http.Client; |
|||
using Volo.Abp.Modularity; |
|||
using Volo.Abp.VirtualFileSystem; |
|||
using Volo.Docs.Common; |
|||
|
|||
namespace Volo.Docs |
|||
{ |
|||
[DependsOn( |
|||
typeof(DocsCommonApplicationContractsModule), |
|||
typeof(AbpHttpClientModule) |
|||
)] |
|||
public class DocsCommonHttpApiClientModule : AbpModule |
|||
{ |
|||
public override void ConfigureServices(ServiceConfigurationContext context) |
|||
{ |
|||
context.Services.AddStaticHttpClientProxies(typeof(DocsCommonApplicationContractsModule).Assembly, DocsCommonRemoteServiceConsts.RemoteServiceName); |
|||
|
|||
Configure<AbpVirtualFileSystemOptions>(options => |
|||
{ |
|||
options.FileSets.AddEmbedded<DocsCommonHttpApiClientModule>(); |
|||
}); |
|||
} |
|||
} |
|||
} |
|||
@ -0,0 +1,50 @@ |
|||
using System; |
|||
using System.IO; |
|||
using System.Threading.Tasks; |
|||
using Microsoft.Extensions.Caching.Distributed; |
|||
using Microsoft.Extensions.Options; |
|||
using Volo.Abp.BlobStoring; |
|||
using Volo.Abp.Caching; |
|||
using Volo.Abp.DependencyInjection; |
|||
using Volo.Docs.Projects; |
|||
|
|||
namespace Volo.Docs.Documents.Pdf; |
|||
|
|||
public class BlobDocumentPdfFileStore : IDocumentPdfFileStore, ITransientDependency |
|||
{ |
|||
protected IBlobContainer<DocsDocumentPdfContainer> BlobContainer { get; } |
|||
protected IDistributedCache<DocsDocumentPdfCacheItem> Cache { get; } |
|||
protected IOptions<DocsDocumentPdfGeneratorOptions> Options { get; } |
|||
|
|||
public BlobDocumentPdfFileStore( |
|||
IBlobContainer<DocsDocumentPdfContainer> blobContainer, |
|||
IDistributedCache<DocsDocumentPdfCacheItem> cache, |
|||
IOptions<DocsDocumentPdfGeneratorOptions> options) |
|||
{ |
|||
BlobContainer = blobContainer; |
|||
Cache = cache; |
|||
Options = options; |
|||
} |
|||
|
|||
public virtual async Task SetAsync(Project project, string version, string languageCode, Stream stream) |
|||
{ |
|||
await BlobContainer.SaveAsync(Options.Value.CalculatePdfFileName(project, version, languageCode), stream); |
|||
|
|||
await Cache.SetAsync(DocsDocumentPdfCacheItem.CalculateCacheKey(project.Id, version, languageCode), new DocsDocumentPdfCacheItem(), |
|||
new DistributedCacheEntryOptions |
|||
{ |
|||
AbsoluteExpiration = DateTimeOffset.Now.Add(Options.Value.PdfFileCacheExpiration) |
|||
}); |
|||
} |
|||
|
|||
public virtual async Task<Stream> GetOrNullAsync(Project project, string version, string languageCode) |
|||
{ |
|||
var cache = await Cache.GetAsync(DocsDocumentPdfCacheItem.CalculateCacheKey(project.Id, version, languageCode)); |
|||
if (cache == null) |
|||
{ |
|||
return null; |
|||
} |
|||
|
|||
return await BlobContainer.GetOrNullAsync(Options.Value.CalculatePdfFileName(project, version, languageCode)); |
|||
} |
|||
} |
|||
@ -0,0 +1,11 @@ |
|||
using System; |
|||
|
|||
namespace Volo.Docs.Documents.Pdf; |
|||
|
|||
public class DocsDocumentPdfCacheItem |
|||
{ |
|||
public static string CalculateCacheKey(Guid projectId, string version, string languageCode) |
|||
{ |
|||
return $"{projectId}_{version}_{languageCode}"; |
|||
} |
|||
} |
|||
@ -1,6 +1,6 @@ |
|||
using Volo.Abp.BlobStoring; |
|||
|
|||
namespace Volo.Docs.Common.Documents; |
|||
namespace Volo.Docs.Documents.Pdf; |
|||
|
|||
[BlobContainerName("docs-document-pdf")] |
|||
public class DocsDocumentPdfContainer |
|||
@ -1,24 +1,38 @@ |
|||
namespace Volo.Docs.Common.Documents; |
|||
using System; |
|||
using Volo.Docs.Projects; |
|||
|
|||
namespace Volo.Docs.Documents.Pdf; |
|||
|
|||
public class DocsDocumentPdfGeneratorOptions |
|||
{ |
|||
public const string StylePlaceholder = "{{style-placeholder}}"; |
|||
public const string ContentPlaceholder = "{{content-placeholder}}"; |
|||
|
|||
/// <summary>
|
|||
/// The HTML layout for the PDF document.
|
|||
/// </summary>
|
|||
public string HtmlLayout { get; set; } |
|||
public string HtmlStyles { get; set; } |
|||
|
|||
public string BaseUrl { get; set; } |
|||
|
|||
public string CoverPagePath { get; set; } |
|||
public TimeSpan PdfFileCacheExpiration { get; set; } = TimeSpan.FromDays(1); |
|||
public Func<Project, string, string, string> CalculatePdfFileName { get; set; } = (project, version, languageCode) => |
|||
{ |
|||
return $"{project.ShortName}_{version}_{languageCode}.pdf"; |
|||
}; |
|||
|
|||
public DocsDocumentPdfGeneratorOptions() |
|||
{ |
|||
HtmlLayout = @"
|
|||
HtmlLayout = $@"
|
|||
<!DOCTYPE html> |
|||
<head> |
|||
<meta charset='utf-8' /> |
|||
<style> |
|||
{{style-placeholder}} |
|||
{StylePlaceholder} |
|||
</style> |
|||
</head> |
|||
<body> |
|||
{{content-placeholder}} |
|||
{ContentPlaceholder} |
|||
</body> |
|||
</html>";
|
|||
|
|||
@ -0,0 +1,12 @@ |
|||
using System.IO; |
|||
using System.Threading.Tasks; |
|||
using Volo.Docs.Projects; |
|||
|
|||
namespace Volo.Docs.Documents.Pdf; |
|||
|
|||
public interface IDocumentPdfFileStore |
|||
{ |
|||
Task SetAsync(Project project, string version, string languageCode, Stream stream); |
|||
|
|||
Task<Stream> GetOrNullAsync(Project project, string version, string languageCode); |
|||
} |
|||
@ -1,11 +1,10 @@ |
|||
using System.Threading.Tasks; |
|||
using Volo.Abp.Content; |
|||
using Volo.Abp.DependencyInjection; |
|||
using Volo.Docs.Projects; |
|||
|
|||
namespace Volo.Docs.Common.Documents; |
|||
namespace Volo.Docs.Documents.Pdf; |
|||
|
|||
public interface IDocumentPdfGenerator : ITransientDependency |
|||
public interface IDocumentPdfGenerator |
|||
{ |
|||
Task<IRemoteStreamContent> GenerateAsync(Project project, string version, string languageCode); |
|||
} |
|||
@ -0,0 +1,10 @@ |
|||
using System.Collections.Generic; |
|||
using System.IO; |
|||
using System.Threading.Tasks; |
|||
|
|||
namespace Volo.Docs.Documents.Pdf; |
|||
|
|||
public interface IPdfRenderer |
|||
{ |
|||
Task<MemoryStream> GeneratePdfAsync(string htmlContent, List<PdfDocumentNode> pdfDocumentNodes); |
|||
} |
|||
@ -0,0 +1,73 @@ |
|||
using System; |
|||
using System.Collections.Generic; |
|||
using System.IO; |
|||
using System.Text; |
|||
using System.Threading.Tasks; |
|||
using iText.Html2pdf; |
|||
using iText.Kernel.Pdf; |
|||
using iText.Kernel.Pdf.Action; |
|||
using Microsoft.Extensions.Options; |
|||
using Volo.Abp.DependencyInjection; |
|||
using ITextDocument = iText.Layout.Document; |
|||
|
|||
namespace Volo.Docs.Documents.Pdf.IText; |
|||
|
|||
public class ITextPdfRenderer : IPdfRenderer ,ITransientDependency |
|||
{ |
|||
protected IOptions<DocsDocumentPdfGeneratorOptions> Options { get; } |
|||
|
|||
public ITextPdfRenderer(IOptions<DocsDocumentPdfGeneratorOptions> options) |
|||
{ |
|||
Options = options; |
|||
} |
|||
|
|||
public virtual Task<MemoryStream> GeneratePdfAsync(string htmlContent, List<PdfDocumentNode> pdfDocumentNodes) |
|||
{ |
|||
var pdfStream = new MemoryStream(); |
|||
var pdfWrite = new PdfWriter(pdfStream); |
|||
var pdfDocument = new PdfDocument(pdfWrite); |
|||
var textDocument = new ITextDocument(pdfDocument); |
|||
pdfWrite.SetCloseStream(false); |
|||
|
|||
var htmlBuilder = new StringBuilder(); |
|||
htmlBuilder.Append(Options.Value.HtmlLayout); |
|||
htmlBuilder.Replace(DocsDocumentPdfGeneratorOptions.StylePlaceholder, Options.Value.HtmlStyles); |
|||
htmlBuilder.Replace(DocsDocumentPdfGeneratorOptions.ContentPlaceholder, htmlContent); |
|||
|
|||
var converter = new ConverterProperties(); |
|||
var tagWorkerFactory = new HtmlIdTagWorkerFactory(pdfDocument); |
|||
converter.SetTagWorkerFactory(tagWorkerFactory); |
|||
|
|||
HtmlConverter.ConvertToDocument(htmlBuilder.ToString(), pdfDocument, converter); |
|||
|
|||
tagWorkerFactory.AddNamedDestinations(); |
|||
var pdfOutlines = pdfDocument.GetOutlines(false); |
|||
BuildPdfOutlines(pdfOutlines, pdfDocumentNodes); |
|||
|
|||
textDocument.Close(); |
|||
pdfStream.Position = 0; |
|||
return Task.FromResult(pdfStream); |
|||
} |
|||
|
|||
private void BuildPdfOutlines(PdfOutline parentOutline, List<PdfDocumentNode> pdfDocumentNodes) |
|||
{ |
|||
foreach (var pdfDocumentNode in pdfDocumentNodes) |
|||
{ |
|||
if (pdfDocumentNode.IgnoreOnOutline) |
|||
{ |
|||
continue; |
|||
} |
|||
|
|||
var outline = parentOutline.AddOutline(pdfDocumentNode.Title); |
|||
if (!pdfDocumentNode.Id.IsNullOrWhiteSpace()) |
|||
{ |
|||
outline.AddAction(PdfAction.CreateGoTo(pdfDocumentNode.Id)); |
|||
} |
|||
|
|||
if (pdfDocumentNode.HasChildren) |
|||
{ |
|||
BuildPdfOutlines(outline, pdfDocumentNode.Children); |
|||
} |
|||
} |
|||
} |
|||
} |
|||
@ -0,0 +1,16 @@ |
|||
using System.Collections.Generic; |
|||
using System.Linq; |
|||
using Volo.Docs.Documents.Rendering; |
|||
|
|||
namespace Volo.Docs.Documents.Pdf; |
|||
|
|||
public class PdfDocumentNode |
|||
{ |
|||
public Document Document { get; set; } |
|||
public string Title { get; set; } |
|||
public string Id { get; set; } |
|||
public List<PdfDocumentNode> Children { get; set; } = []; |
|||
public DocumentRenderParameters RenderParameters { get; set; } |
|||
public bool HasChildren => Children.Any(); |
|||
public bool IgnoreOnOutline { get; set; } |
|||
} |
|||
@ -0,0 +1,68 @@ |
|||
/* This file is automatically generated by ABP framework to use MVC Controllers from javascript. */ |
|||
|
|||
|
|||
// module docs-common
|
|||
|
|||
(function(){ |
|||
|
|||
// controller volo.docs.documents.docsDocumentPdfGenerator
|
|||
|
|||
(function(){ |
|||
|
|||
abp.utils.createNamespace(window, 'volo.docs.documents.docsDocumentPdfGenerator'); |
|||
|
|||
volo.docs.documents.docsDocumentPdfGenerator.generatePdf = function(input, ajaxParams) { |
|||
return abp.ajax($.extend(true, { |
|||
url: abp.appPath + 'api/docs/documents/pdf' + abp.utils.buildQueryString([{ name: 'projectId', value: input.projectId }, { name: 'version', value: input.version }, { name: 'languageCode', value: input.languageCode }]) + '', |
|||
type: 'GET' |
|||
}, ajaxParams)); |
|||
}; |
|||
|
|||
})(); |
|||
|
|||
// controller volo.docs.projects.docsProject
|
|||
|
|||
(function(){ |
|||
|
|||
abp.utils.createNamespace(window, 'volo.docs.projects.docsProject'); |
|||
|
|||
volo.docs.projects.docsProject.getList = function(ajaxParams) { |
|||
return abp.ajax($.extend(true, { |
|||
url: abp.appPath + 'api/docs/projects', |
|||
type: 'GET' |
|||
}, ajaxParams)); |
|||
}; |
|||
|
|||
volo.docs.projects.docsProject.get = function(shortName, ajaxParams) { |
|||
return abp.ajax($.extend(true, { |
|||
url: abp.appPath + 'api/docs/projects/' + shortName + '', |
|||
type: 'GET' |
|||
}, ajaxParams)); |
|||
}; |
|||
|
|||
volo.docs.projects.docsProject.getDefaultLanguageCode = function(shortName, version, ajaxParams) { |
|||
return abp.ajax($.extend(true, { |
|||
url: abp.appPath + 'api/docs/projects/' + shortName + '/defaultLanguage' + abp.utils.buildQueryString([{ name: 'version', value: version }]) + '', |
|||
type: 'GET' |
|||
}, { dataType: 'text' }, ajaxParams)); |
|||
}; |
|||
|
|||
volo.docs.projects.docsProject.getVersions = function(shortName, ajaxParams) { |
|||
return abp.ajax($.extend(true, { |
|||
url: abp.appPath + 'api/docs/projects/' + shortName + '/versions', |
|||
type: 'GET' |
|||
}, ajaxParams)); |
|||
}; |
|||
|
|||
volo.docs.projects.docsProject.getLanguageList = function(shortName, version, ajaxParams) { |
|||
return abp.ajax($.extend(true, { |
|||
url: abp.appPath + 'api/docs/projects/' + shortName + '/' + version + '/languageList', |
|||
type: 'GET' |
|||
}, ajaxParams)); |
|||
}; |
|||
|
|||
})(); |
|||
|
|||
})(); |
|||
|
|||
|
|||
Loading…
Reference in new issue