diff --git a/Directory.Packages.props b/Directory.Packages.props index 09c9a476fd..7263869bdf 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -34,6 +34,9 @@ + + + @@ -182,4 +185,4 @@ - + \ No newline at end of file diff --git a/docs/en/docs-nav.json b/docs/en/docs-nav.json index fc3844317d..d031e87466 100644 --- a/docs/en/docs-nav.json +++ b/docs/en/docs-nav.json @@ -83,47 +83,59 @@ { "text": "Overview", "path": "tutorials/book-store", - "isIndex": true + "isIndex": true, + "isInSeries": true }, { "text": "1: Creating the Server Side", - "path": "tutorials/book-store/part-01.md" + "path": "tutorials/book-store/part-01.md", + "isInSeries": true + }, { "text": "2: The Book List Page", - "path": "tutorials/book-store/part-02.md" + "path": "tutorials/book-store/part-02.md", + "isInSeries": true }, { "text": "3: Creating, Updating and Deleting Books", - "path": "tutorials/book-store/part-03.md" + "path": "tutorials/book-store/part-03.md", + "isInSeries": true }, { "text": "4: Integration Tests", - "path": "tutorials/book-store/part-04.md" + "path": "tutorials/book-store/part-04.md", + "isInSeries": true }, { "text": "5: Authorization", - "path": "tutorials/book-store/part-05.md" + "path": "tutorials/book-store/part-05.md", + "isInSeries": true }, { "text": "6: Authors: Domain Layer", - "path": "tutorials/book-store/part-06.md" + "path": "tutorials/book-store/part-06.md", + "isInSeries": true }, { "text": "7: Authors: Database Integration", - "path": "tutorials/book-store/part-07.md" + "path": "tutorials/book-store/part-07.md", + "isInSeries": true }, { "text": "8: Authors: Application Layer", - "path": "tutorials/book-store/part-08.md" + "path": "tutorials/book-store/part-08.md", + "isInSeries": true }, { "text": "9: Authors: User Interface", - "path": "tutorials/book-store/part-09.md" + "path": "tutorials/book-store/part-09.md", + "isInSeries": true }, { "text": "10: Book to Author Relation", - "path": "tutorials/book-store/part-10.md" + "path": "tutorials/book-store/part-10.md", + "isInSeries": true } ] }, @@ -135,27 +147,33 @@ { "text": "Overview", "path": "tutorials/book-store-with-abp-suite", - "isIndex": true + "isIndex": true, + "isInSeries": true }, { "text": "1: Creating the Solution", - "path": "tutorials/book-store-with-abp-suite/part-01.md" + "path": "tutorials/book-store-with-abp-suite/part-01.md", + "isInSeries": true }, { "text": "2: Creating the Books", - "path": "tutorials/book-store-with-abp-suite/part-02.md" + "path": "tutorials/book-store-with-abp-suite/part-02.md", + "isInSeries": true }, { "text": "3: Creating the Authors", - "path": "tutorials/book-store-with-abp-suite/part-03.md" + "path": "tutorials/book-store-with-abp-suite/part-03.md", + "isInSeries": true }, { "text": "4: Book to Author Relation", - "path": "tutorials/book-store-with-abp-suite/part-04.md" + "path": "tutorials/book-store-with-abp-suite/part-04.md", + "isInSeries": true }, { "text": "5: Customizing the Generated Code", - "path": "tutorials/book-store-with-abp-suite/part-05.md" + "path": "tutorials/book-store-with-abp-suite/part-05.md", + "isInSeries": true } ] }, @@ -2070,19 +2088,23 @@ "items": [ { "text": "Deploy to Azure Web App Service", - "path": "solution-templates/layered-web-application/deployment/azure-deployment/azure-deployment.md" + "path": "solution-templates/layered-web-application/deployment/azure-deployment/azure-deployment.md", + "isInSeries": true }, { "text": "Creating an Azure Web App Service Environment", - "path": "solution-templates/layered-web-application/deployment/azure-deployment/step1-create-azure-resources.md" + "path": "solution-templates/layered-web-application/deployment/azure-deployment/step1-create-azure-resources.md", + "isInSeries": true }, { "text": "Customizing the Configuration of Your ABP Application", - "path": "solution-templates/layered-web-application/deployment/azure-deployment/step2-configuration-application.md" + "path": "solution-templates/layered-web-application/deployment/azure-deployment/step2-configuration-application.md", + "isInSeries": true }, { "text": "Deploying Application With GitHub Actions", - "path": "solution-templates/layered-web-application/deployment/azure-deployment/step3-deployment-github-action.md" + "path": "solution-templates/layered-web-application/deployment/azure-deployment/step3-deployment-github-action.md", + "isInSeries": true } ] }, diff --git a/modules/docs/Volo.Docs.sln b/modules/docs/Volo.Docs.sln index 6bb8d84d0a..af9282dca3 100644 --- a/modules/docs/Volo.Docs.sln +++ b/modules/docs/Volo.Docs.sln @@ -63,6 +63,16 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Volo.Docs.MongoDB.Tests", " EndProject Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Volo.Docs.Installer", "src\Volo.Docs.Installer\Volo.Docs.Installer.csproj", "{50B9AC1D-C03E-47AA-9ED8-E7986BCFABA1}" EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Volo.Docs.Common.Application", "src\Volo.Docs.Common.Application\Volo.Docs.Common.Application.csproj", "{914EDEC4-EFCE-46D5-B6E0-A928B1907307}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Volo.Docs.Common.Application.Contracts", "src\Volo.Docs.Common.Application.Contracts\Volo.Docs.Common.Application.Contracts.csproj", "{8CA19527-6870-4617-B6D1-EA8CAF224DF4}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "common", "common", "{F778B2C3-2E6D-4CF3-ACA7-10E21E6A7961}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Volo.Docs.Common.HttpApi", "src\Volo.Docs.Common.HttpApi\Volo.Docs.Common.HttpApi.csproj", "{052C076D-56FF-4DFA-838B-48BD30A1DB0A}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Volo.Docs.Common.HttpApi.Client", "src\Volo.Docs.Common.HttpApi.Client\Volo.Docs.Common.HttpApi.Client.csproj", "{349C36A0-552D-44A3-AC74-03A4828D43AB}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -165,6 +175,22 @@ Global {50B9AC1D-C03E-47AA-9ED8-E7986BCFABA1}.Debug|Any CPU.Build.0 = Debug|Any CPU {50B9AC1D-C03E-47AA-9ED8-E7986BCFABA1}.Release|Any CPU.ActiveCfg = Release|Any CPU {50B9AC1D-C03E-47AA-9ED8-E7986BCFABA1}.Release|Any CPU.Build.0 = Release|Any CPU + {914EDEC4-EFCE-46D5-B6E0-A928B1907307}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {914EDEC4-EFCE-46D5-B6E0-A928B1907307}.Debug|Any CPU.Build.0 = Debug|Any CPU + {914EDEC4-EFCE-46D5-B6E0-A928B1907307}.Release|Any CPU.ActiveCfg = Release|Any CPU + {914EDEC4-EFCE-46D5-B6E0-A928B1907307}.Release|Any CPU.Build.0 = Release|Any CPU + {8CA19527-6870-4617-B6D1-EA8CAF224DF4}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {8CA19527-6870-4617-B6D1-EA8CAF224DF4}.Debug|Any CPU.Build.0 = Debug|Any CPU + {8CA19527-6870-4617-B6D1-EA8CAF224DF4}.Release|Any CPU.ActiveCfg = Release|Any CPU + {8CA19527-6870-4617-B6D1-EA8CAF224DF4}.Release|Any CPU.Build.0 = Release|Any CPU + {052C076D-56FF-4DFA-838B-48BD30A1DB0A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {052C076D-56FF-4DFA-838B-48BD30A1DB0A}.Debug|Any CPU.Build.0 = Debug|Any CPU + {052C076D-56FF-4DFA-838B-48BD30A1DB0A}.Release|Any CPU.ActiveCfg = Release|Any CPU + {052C076D-56FF-4DFA-838B-48BD30A1DB0A}.Release|Any CPU.Build.0 = Release|Any CPU + {349C36A0-552D-44A3-AC74-03A4828D43AB}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {349C36A0-552D-44A3-AC74-03A4828D43AB}.Debug|Any CPU.Build.0 = Debug|Any CPU + {349C36A0-552D-44A3-AC74-03A4828D43AB}.Release|Any CPU.ActiveCfg = Release|Any CPU + {349C36A0-552D-44A3-AC74-03A4828D43AB}.Release|Any CPU.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE @@ -197,6 +223,11 @@ Global {DBE846CD-1BED-4F2C-ABF2-94F6240BCB9B} = {A982A58E-1E92-4764-9F56-39E7AABB8556} {C5E2A2A3-D54D-4C2E-97BA-EA50A49ED7AD} = {59D430A9-AC61-4457-8338-5DA0705ABB5D} {50B9AC1D-C03E-47AA-9ED8-E7986BCFABA1} = {A982A58E-1E92-4764-9F56-39E7AABB8556} + {F778B2C3-2E6D-4CF3-ACA7-10E21E6A7961} = {42416152-5BAB-4706-93A6-57A19E71FE14} + {914EDEC4-EFCE-46D5-B6E0-A928B1907307} = {F778B2C3-2E6D-4CF3-ACA7-10E21E6A7961} + {8CA19527-6870-4617-B6D1-EA8CAF224DF4} = {F778B2C3-2E6D-4CF3-ACA7-10E21E6A7961} + {052C076D-56FF-4DFA-838B-48BD30A1DB0A} = {F778B2C3-2E6D-4CF3-ACA7-10E21E6A7961} + {349C36A0-552D-44A3-AC74-03A4828D43AB} = {F778B2C3-2E6D-4CF3-ACA7-10E21E6A7961} EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {13691265-2547-4FFF-B757-E8FACB05679D} diff --git a/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20241231072012_Initial.Designer.cs b/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20250411070040_initial.Designer.cs similarity index 93% rename from modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20241231072012_Initial.Designer.cs rename to modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20250411070040_initial.Designer.cs index ad7dfa9576..325052b498 100644 --- a/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20241231072012_Initial.Designer.cs +++ b/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20250411070040_initial.Designer.cs @@ -13,8 +13,8 @@ using VoloDocs.EntityFrameworkCore; namespace Migrations { [DbContext(typeof(VoloDocsDbContext))] - [Migration("20241231072012_Initial")] - partial class Initial + [Migration("20250411070040_initial")] + partial class initial { /// protected override void BuildTargetModel(ModelBuilder modelBuilder) @@ -22,11 +22,88 @@ namespace Migrations #pragma warning disable 612, 618 modelBuilder .HasAnnotation("_Abp_DatabaseProvider", EfCoreDatabaseProvider.SqlServer) - .HasAnnotation("ProductVersion", "9.0.0") + .HasAnnotation("ProductVersion", "9.0.2") .HasAnnotation("Relational:MaxIdentifierLength", 128); SqlServerModelBuilderExtensions.UseIdentityColumns(modelBuilder); + modelBuilder.Entity("Volo.Abp.BlobStoring.Database.DatabaseBlob", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("ContainerId") + .HasColumnType("uniqueidentifier"); + + b.Property("Content") + .HasMaxLength(2147483647) + .HasColumnType("varbinary(max)"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.HasIndex("ContainerId"); + + b.HasIndex("TenantId", "ContainerId", "Name"); + + b.ToTable("AbpBlobs", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.BlobStoring.Database.DatabaseBlobContainer", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.HasIndex("TenantId", "Name"); + + b.ToTable("AbpBlobContainers", (string)null); + }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityClaimType", b => { b.Property("Id") @@ -1119,6 +1196,15 @@ namespace Migrations b.ToTable("DocsProjects", (string)null); }); + modelBuilder.Entity("Volo.Abp.BlobStoring.Database.DatabaseBlob", b => + { + b.HasOne("Volo.Abp.BlobStoring.Database.DatabaseBlobContainer", null) + .WithMany() + .HasForeignKey("ContainerId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityRoleClaim", b => { b.HasOne("Volo.Abp.Identity.IdentityRole", null) diff --git a/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20241231072012_Initial.cs b/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20250411070040_initial.cs similarity index 93% rename from modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20241231072012_Initial.cs rename to modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20250411070040_initial.cs index 25791fabf4..1c03234da9 100644 --- a/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20241231072012_Initial.cs +++ b/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20250411070040_initial.cs @@ -6,11 +6,26 @@ using Microsoft.EntityFrameworkCore.Migrations; namespace Migrations { /// - public partial class Initial : Migration + public partial class initial : Migration { /// protected override void Up(MigrationBuilder migrationBuilder) { + migrationBuilder.CreateTable( + name: "AbpBlobContainers", + columns: table => new + { + Id = table.Column(type: "uniqueidentifier", nullable: false), + TenantId = table.Column(type: "uniqueidentifier", nullable: true), + Name = table.Column(type: "nvarchar(128)", maxLength: 128, nullable: false), + ExtraProperties = table.Column(type: "nvarchar(max)", nullable: false), + ConcurrencyStamp = table.Column(type: "nvarchar(40)", maxLength: 40, nullable: false) + }, + constraints: table => + { + table.PrimaryKey("PK_AbpBlobContainers", x => x.Id); + }); + migrationBuilder.CreateTable( name: "AbpClaimTypes", columns: table => new @@ -336,6 +351,29 @@ namespace Migrations table.PrimaryKey("PK_DocsProjects", x => x.Id); }); + migrationBuilder.CreateTable( + name: "AbpBlobs", + columns: table => new + { + Id = table.Column(type: "uniqueidentifier", nullable: false), + ContainerId = table.Column(type: "uniqueidentifier", nullable: false), + TenantId = table.Column(type: "uniqueidentifier", nullable: true), + Name = table.Column(type: "nvarchar(256)", maxLength: 256, nullable: false), + Content = table.Column(type: "varbinary(max)", maxLength: 2147483647, nullable: true), + ExtraProperties = table.Column(type: "nvarchar(max)", nullable: false), + ConcurrencyStamp = table.Column(type: "nvarchar(40)", maxLength: 40, nullable: false) + }, + constraints: table => + { + table.PrimaryKey("PK_AbpBlobs", x => x.Id); + table.ForeignKey( + name: "FK_AbpBlobs_AbpBlobContainers_ContainerId", + column: x => x.ContainerId, + principalTable: "AbpBlobContainers", + principalColumn: "Id", + onDelete: ReferentialAction.Cascade); + }); + migrationBuilder.CreateTable( name: "AbpOrganizationUnitRoles", columns: table => new @@ -520,6 +558,21 @@ namespace Migrations onDelete: ReferentialAction.Cascade); }); + migrationBuilder.CreateIndex( + name: "IX_AbpBlobContainers_TenantId_Name", + table: "AbpBlobContainers", + columns: new[] { "TenantId", "Name" }); + + migrationBuilder.CreateIndex( + name: "IX_AbpBlobs_ContainerId", + table: "AbpBlobs", + column: "ContainerId"); + + migrationBuilder.CreateIndex( + name: "IX_AbpBlobs_TenantId_ContainerId_Name", + table: "AbpBlobs", + columns: new[] { "TenantId", "ContainerId", "Name" }); + migrationBuilder.CreateIndex( name: "IX_AbpLinkUsers_SourceUserId_SourceTenantId_TargetUserId_TargetTenantId", table: "AbpLinkUsers", @@ -668,6 +721,9 @@ namespace Migrations /// protected override void Down(MigrationBuilder migrationBuilder) { + migrationBuilder.DropTable( + name: "AbpBlobs"); + migrationBuilder.DropTable( name: "AbpClaimTypes"); @@ -725,6 +781,9 @@ namespace Migrations migrationBuilder.DropTable( name: "DocsProjects"); + migrationBuilder.DropTable( + name: "AbpBlobContainers"); + migrationBuilder.DropTable( name: "AbpOrganizationUnits"); diff --git a/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20250425082043_add_pdf_file.Designer.cs b/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20250425082043_add_pdf_file.Designer.cs new file mode 100644 index 0000000000..c284a80f8b --- /dev/null +++ b/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20250425082043_add_pdf_file.Designer.cs @@ -0,0 +1,1376 @@ +// +using System; +using Microsoft.EntityFrameworkCore; +using Microsoft.EntityFrameworkCore.Infrastructure; +using Microsoft.EntityFrameworkCore.Metadata; +using Microsoft.EntityFrameworkCore.Migrations; +using Microsoft.EntityFrameworkCore.Storage.ValueConversion; +using Volo.Abp.EntityFrameworkCore; +using VoloDocs.EntityFrameworkCore; + +#nullable disable + +namespace Migrations +{ + [DbContext(typeof(VoloDocsDbContext))] + [Migration("20250425082043_add_pdf_file")] + partial class add_pdf_file + { + /// + protected override void BuildTargetModel(ModelBuilder modelBuilder) + { +#pragma warning disable 612, 618 + modelBuilder + .HasAnnotation("_Abp_DatabaseProvider", EfCoreDatabaseProvider.SqlServer) + .HasAnnotation("ProductVersion", "9.0.2") + .HasAnnotation("Relational:MaxIdentifierLength", 128); + + SqlServerModelBuilderExtensions.UseIdentityColumns(modelBuilder); + + modelBuilder.Entity("Volo.Abp.BlobStoring.Database.DatabaseBlob", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("ContainerId") + .HasColumnType("uniqueidentifier"); + + b.Property("Content") + .HasMaxLength(2147483647) + .HasColumnType("varbinary(max)"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.HasIndex("ContainerId"); + + b.HasIndex("TenantId", "ContainerId", "Name"); + + b.ToTable("AbpBlobs", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.BlobStoring.Database.DatabaseBlobContainer", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.HasIndex("TenantId", "Name"); + + b.ToTable("AbpBlobContainers", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityClaimType", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("CreationTime") + .HasColumnType("datetime2") + .HasColumnName("CreationTime"); + + b.Property("Description") + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("IsStatic") + .HasColumnType("bit"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("Regex") + .HasMaxLength(512) + .HasColumnType("nvarchar(512)"); + + b.Property("RegexDescription") + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("Required") + .HasColumnType("bit"); + + b.Property("ValueType") + .HasColumnType("int"); + + b.HasKey("Id"); + + b.ToTable("AbpClaimTypes", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityLinkUser", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("SourceTenantId") + .HasColumnType("uniqueidentifier"); + + b.Property("SourceUserId") + .HasColumnType("uniqueidentifier"); + + b.Property("TargetTenantId") + .HasColumnType("uniqueidentifier"); + + b.Property("TargetUserId") + .HasColumnType("uniqueidentifier"); + + b.HasKey("Id"); + + b.HasIndex("SourceUserId", "SourceTenantId", "TargetUserId", "TargetTenantId") + .IsUnique() + .HasFilter("[SourceTenantId] IS NOT NULL AND [TargetTenantId] IS NOT NULL"); + + b.ToTable("AbpLinkUsers", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityRole", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("CreationTime") + .HasColumnType("datetime2") + .HasColumnName("CreationTime"); + + b.Property("EntityVersion") + .HasColumnType("int"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("IsDefault") + .HasColumnType("bit") + .HasColumnName("IsDefault"); + + b.Property("IsPublic") + .HasColumnType("bit") + .HasColumnName("IsPublic"); + + b.Property("IsStatic") + .HasColumnType("bit") + .HasColumnName("IsStatic"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("NormalizedName") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.HasIndex("NormalizedName"); + + b.ToTable("AbpRoles", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityRoleClaim", b => + { + b.Property("Id") + .HasColumnType("uniqueidentifier"); + + b.Property("ClaimType") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("ClaimValue") + .HasMaxLength(1024) + .HasColumnType("nvarchar(1024)"); + + b.Property("RoleId") + .HasColumnType("uniqueidentifier"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.HasIndex("RoleId"); + + b.ToTable("AbpRoleClaims", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentitySecurityLog", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("Action") + .HasMaxLength(96) + .HasColumnType("nvarchar(96)"); + + b.Property("ApplicationName") + .HasMaxLength(96) + .HasColumnType("nvarchar(96)"); + + b.Property("BrowserInfo") + .HasMaxLength(512) + .HasColumnType("nvarchar(512)"); + + b.Property("ClientId") + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("ClientIpAddress") + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("CorrelationId") + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("CreationTime") + .HasColumnType("datetime2"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("Identity") + .HasMaxLength(96) + .HasColumnType("nvarchar(96)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.Property("TenantName") + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("UserId") + .HasColumnType("uniqueidentifier"); + + b.Property("UserName") + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.HasKey("Id"); + + b.HasIndex("TenantId", "Action"); + + b.HasIndex("TenantId", "ApplicationName"); + + b.HasIndex("TenantId", "Identity"); + + b.HasIndex("TenantId", "UserId"); + + b.ToTable("AbpSecurityLogs", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentitySession", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("ClientId") + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("Device") + .IsRequired() + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("DeviceInfo") + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("ExtraProperties") + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("IpAddresses") + .HasMaxLength(2048) + .HasColumnType("nvarchar(2048)"); + + b.Property("LastAccessed") + .HasColumnType("datetime2"); + + b.Property("SessionId") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("SignedIn") + .HasColumnType("datetime2"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.Property("UserId") + .HasColumnType("uniqueidentifier"); + + b.HasKey("Id"); + + b.HasIndex("Device"); + + b.HasIndex("SessionId"); + + b.HasIndex("TenantId", "UserId"); + + b.ToTable("AbpSessions", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUser", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("AccessFailedCount") + .ValueGeneratedOnAdd() + .HasColumnType("int") + .HasDefaultValue(0) + .HasColumnName("AccessFailedCount"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("CreationTime") + .HasColumnType("datetime2") + .HasColumnName("CreationTime"); + + b.Property("CreatorId") + .HasColumnType("uniqueidentifier") + .HasColumnName("CreatorId"); + + b.Property("DeleterId") + .HasColumnType("uniqueidentifier") + .HasColumnName("DeleterId"); + + b.Property("DeletionTime") + .HasColumnType("datetime2") + .HasColumnName("DeletionTime"); + + b.Property("Email") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)") + .HasColumnName("Email"); + + b.Property("EmailConfirmed") + .ValueGeneratedOnAdd() + .HasColumnType("bit") + .HasDefaultValue(false) + .HasColumnName("EmailConfirmed"); + + b.Property("EntityVersion") + .HasColumnType("int"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("IsActive") + .HasColumnType("bit") + .HasColumnName("IsActive"); + + b.Property("IsDeleted") + .ValueGeneratedOnAdd() + .HasColumnType("bit") + .HasDefaultValue(false) + .HasColumnName("IsDeleted"); + + b.Property("IsExternal") + .ValueGeneratedOnAdd() + .HasColumnType("bit") + .HasDefaultValue(false) + .HasColumnName("IsExternal"); + + b.Property("LastModificationTime") + .HasColumnType("datetime2") + .HasColumnName("LastModificationTime"); + + b.Property("LastModifierId") + .HasColumnType("uniqueidentifier") + .HasColumnName("LastModifierId"); + + b.Property("LastPasswordChangeTime") + .HasColumnType("datetimeoffset"); + + b.Property("LockoutEnabled") + .ValueGeneratedOnAdd() + .HasColumnType("bit") + .HasDefaultValue(false) + .HasColumnName("LockoutEnabled"); + + b.Property("LockoutEnd") + .HasColumnType("datetimeoffset"); + + b.Property("Name") + .HasMaxLength(64) + .HasColumnType("nvarchar(64)") + .HasColumnName("Name"); + + b.Property("NormalizedEmail") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)") + .HasColumnName("NormalizedEmail"); + + b.Property("NormalizedUserName") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)") + .HasColumnName("NormalizedUserName"); + + b.Property("PasswordHash") + .HasMaxLength(256) + .HasColumnType("nvarchar(256)") + .HasColumnName("PasswordHash"); + + b.Property("PhoneNumber") + .HasMaxLength(16) + .HasColumnType("nvarchar(16)") + .HasColumnName("PhoneNumber"); + + b.Property("PhoneNumberConfirmed") + .ValueGeneratedOnAdd() + .HasColumnType("bit") + .HasDefaultValue(false) + .HasColumnName("PhoneNumberConfirmed"); + + b.Property("SecurityStamp") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)") + .HasColumnName("SecurityStamp"); + + b.Property("ShouldChangePasswordOnNextLogin") + .HasColumnType("bit"); + + b.Property("Surname") + .HasMaxLength(64) + .HasColumnType("nvarchar(64)") + .HasColumnName("Surname"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.Property("TwoFactorEnabled") + .ValueGeneratedOnAdd() + .HasColumnType("bit") + .HasDefaultValue(false) + .HasColumnName("TwoFactorEnabled"); + + b.Property("UserName") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)") + .HasColumnName("UserName"); + + b.HasKey("Id"); + + b.HasIndex("Email"); + + b.HasIndex("NormalizedEmail"); + + b.HasIndex("NormalizedUserName"); + + b.HasIndex("UserName"); + + b.ToTable("AbpUsers", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserClaim", b => + { + b.Property("Id") + .HasColumnType("uniqueidentifier"); + + b.Property("ClaimType") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("ClaimValue") + .HasMaxLength(1024) + .HasColumnType("nvarchar(1024)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.Property("UserId") + .HasColumnType("uniqueidentifier"); + + b.HasKey("Id"); + + b.HasIndex("UserId"); + + b.ToTable("AbpUserClaims", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserDelegation", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("EndTime") + .HasColumnType("datetime2"); + + b.Property("SourceUserId") + .HasColumnType("uniqueidentifier"); + + b.Property("StartTime") + .HasColumnType("datetime2"); + + b.Property("TargetUserId") + .HasColumnType("uniqueidentifier"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.ToTable("AbpUserDelegations", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserLogin", b => + { + b.Property("UserId") + .HasColumnType("uniqueidentifier"); + + b.Property("LoginProvider") + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("ProviderDisplayName") + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("ProviderKey") + .IsRequired() + .HasMaxLength(196) + .HasColumnType("nvarchar(196)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("UserId", "LoginProvider"); + + b.HasIndex("LoginProvider", "ProviderKey"); + + b.ToTable("AbpUserLogins", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserOrganizationUnit", b => + { + b.Property("OrganizationUnitId") + .HasColumnType("uniqueidentifier"); + + b.Property("UserId") + .HasColumnType("uniqueidentifier"); + + b.Property("CreationTime") + .HasColumnType("datetime2") + .HasColumnName("CreationTime"); + + b.Property("CreatorId") + .HasColumnType("uniqueidentifier") + .HasColumnName("CreatorId"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("OrganizationUnitId", "UserId"); + + b.HasIndex("UserId", "OrganizationUnitId"); + + b.ToTable("AbpUserOrganizationUnits", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserRole", b => + { + b.Property("UserId") + .HasColumnType("uniqueidentifier"); + + b.Property("RoleId") + .HasColumnType("uniqueidentifier"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("UserId", "RoleId"); + + b.HasIndex("RoleId", "UserId"); + + b.ToTable("AbpUserRoles", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserToken", b => + { + b.Property("UserId") + .HasColumnType("uniqueidentifier"); + + b.Property("LoginProvider") + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("Name") + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.Property("Value") + .HasColumnType("nvarchar(max)"); + + b.HasKey("UserId", "LoginProvider", "Name"); + + b.ToTable("AbpUserTokens", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.OrganizationUnit", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("Code") + .IsRequired() + .HasMaxLength(95) + .HasColumnType("nvarchar(95)") + .HasColumnName("Code"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("CreationTime") + .HasColumnType("datetime2") + .HasColumnName("CreationTime"); + + b.Property("CreatorId") + .HasColumnType("uniqueidentifier") + .HasColumnName("CreatorId"); + + b.Property("DeleterId") + .HasColumnType("uniqueidentifier") + .HasColumnName("DeleterId"); + + b.Property("DeletionTime") + .HasColumnType("datetime2") + .HasColumnName("DeletionTime"); + + b.Property("DisplayName") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)") + .HasColumnName("DisplayName"); + + b.Property("EntityVersion") + .HasColumnType("int"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("IsDeleted") + .ValueGeneratedOnAdd() + .HasColumnType("bit") + .HasDefaultValue(false) + .HasColumnName("IsDeleted"); + + b.Property("LastModificationTime") + .HasColumnType("datetime2") + .HasColumnName("LastModificationTime"); + + b.Property("LastModifierId") + .HasColumnType("uniqueidentifier") + .HasColumnName("LastModifierId"); + + b.Property("ParentId") + .HasColumnType("uniqueidentifier"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.HasIndex("Code"); + + b.HasIndex("ParentId"); + + b.ToTable("AbpOrganizationUnits", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.Identity.OrganizationUnitRole", b => + { + b.Property("OrganizationUnitId") + .HasColumnType("uniqueidentifier"); + + b.Property("RoleId") + .HasColumnType("uniqueidentifier"); + + b.Property("CreationTime") + .HasColumnType("datetime2") + .HasColumnName("CreationTime"); + + b.Property("CreatorId") + .HasColumnType("uniqueidentifier") + .HasColumnName("CreatorId"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("OrganizationUnitId", "RoleId"); + + b.HasIndex("RoleId", "OrganizationUnitId"); + + b.ToTable("AbpOrganizationUnitRoles", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.PermissionManagement.PermissionDefinitionRecord", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("DisplayName") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("ExtraProperties") + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("GroupName") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("IsEnabled") + .HasColumnType("bit"); + + b.Property("MultiTenancySide") + .HasColumnType("tinyint"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("ParentName") + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("Providers") + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("StateCheckers") + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.HasKey("Id"); + + b.HasIndex("GroupName"); + + b.HasIndex("Name") + .IsUnique(); + + b.ToTable("AbpPermissions", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.PermissionManagement.PermissionGrant", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("ProviderKey") + .IsRequired() + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("ProviderName") + .IsRequired() + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.HasIndex("TenantId", "Name", "ProviderName", "ProviderKey") + .IsUnique() + .HasFilter("[TenantId] IS NOT NULL"); + + b.ToTable("AbpPermissionGrants", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.PermissionManagement.PermissionGroupDefinitionRecord", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("DisplayName") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("ExtraProperties") + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.HasKey("Id"); + + b.HasIndex("Name") + .IsUnique(); + + b.ToTable("AbpPermissionGroups", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.SettingManagement.Setting", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("ProviderKey") + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("ProviderName") + .HasMaxLength(64) + .HasColumnType("nvarchar(64)"); + + b.Property("Value") + .IsRequired() + .HasMaxLength(2048) + .HasColumnType("nvarchar(2048)"); + + b.HasKey("Id"); + + b.HasIndex("Name", "ProviderName", "ProviderKey") + .IsUnique() + .HasFilter("[ProviderName] IS NOT NULL AND [ProviderKey] IS NOT NULL"); + + b.ToTable("AbpSettings", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.SettingManagement.SettingDefinitionRecord", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("DefaultValue") + .HasMaxLength(2048) + .HasColumnType("nvarchar(2048)"); + + b.Property("Description") + .HasMaxLength(512) + .HasColumnType("nvarchar(512)"); + + b.Property("DisplayName") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("ExtraProperties") + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("IsEncrypted") + .HasColumnType("bit"); + + b.Property("IsInherited") + .HasColumnType("bit"); + + b.Property("IsVisibleToClients") + .HasColumnType("bit"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("Providers") + .HasMaxLength(1024) + .HasColumnType("nvarchar(1024)"); + + b.HasKey("Id"); + + b.HasIndex("Name") + .IsUnique(); + + b.ToTable("AbpSettingDefinitions", (string)null); + }); + + modelBuilder.Entity("Volo.Docs.Documents.Document", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("Content") + .IsRequired() + .HasColumnType("nvarchar(max)"); + + b.Property("CreationTime") + .HasColumnType("datetime2"); + + b.Property("EditLink") + .HasMaxLength(2048) + .HasColumnType("nvarchar(2048)"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("FileName") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("Format") + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("LanguageCode") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("LastCachedTime") + .HasColumnType("datetime2"); + + b.Property("LastSignificantUpdateTime") + .HasColumnType("datetime2"); + + b.Property("LastUpdatedTime") + .HasColumnType("datetime2"); + + b.Property("LocalDirectory") + .HasMaxLength(512) + .HasColumnType("nvarchar(512)"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(255) + .HasColumnType("nvarchar(255)"); + + b.Property("ProjectId") + .HasColumnType("uniqueidentifier"); + + b.Property("RawRootUrl") + .HasMaxLength(2048) + .HasColumnType("nvarchar(2048)"); + + b.Property("RootUrl") + .HasMaxLength(2048) + .HasColumnType("nvarchar(2048)"); + + b.Property("Version") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.HasKey("Id"); + + b.ToTable("DocsDocuments", (string)null); + }); + + modelBuilder.Entity("Volo.Docs.Documents.DocumentContributor", b => + { + b.Property("DocumentId") + .HasColumnType("uniqueidentifier"); + + b.Property("Username") + .HasColumnType("nvarchar(450)"); + + b.Property("AvatarUrl") + .HasColumnType("nvarchar(max)"); + + b.Property("CommitCount") + .HasColumnType("int"); + + b.Property("UserProfileUrl") + .HasColumnType("nvarchar(max)"); + + b.HasKey("DocumentId", "Username"); + + b.ToTable("DocsDocumentContributors", (string)null); + }); + + modelBuilder.Entity("Volo.Docs.Projects.Project", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("DefaultDocumentName") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("DocumentStoreType") + .HasColumnType("nvarchar(max)"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("Format") + .HasColumnType("nvarchar(max)"); + + b.Property("LatestVersionBranchName") + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("MainWebsiteUrl") + .HasColumnType("nvarchar(max)"); + + b.Property("MinimumVersion") + .HasColumnType("nvarchar(max)"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("NavigationDocumentName") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("ParametersDocumentName") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("ShortName") + .IsRequired() + .HasMaxLength(32) + .HasColumnType("nvarchar(32)"); + + b.HasKey("Id"); + + b.ToTable("DocsProjects", (string)null); + }); + + modelBuilder.Entity("Volo.Docs.Projects.ProjectPdfFile", b => + { + b.Property("ProjectId") + .HasColumnType("uniqueidentifier"); + + b.Property("FileName") + .HasColumnType("nvarchar(450)"); + + b.Property("CreationTime") + .HasColumnType("datetime2") + .HasColumnName("CreationTime"); + + b.Property("LanguageCode") + .HasColumnType("nvarchar(max)"); + + b.Property("LastModificationTime") + .HasColumnType("datetime2") + .HasColumnName("LastModificationTime"); + + b.Property("Version") + .HasColumnType("nvarchar(max)"); + + b.HasKey("ProjectId", "FileName"); + + b.ToTable("DocsProjectPdfFiles", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.BlobStoring.Database.DatabaseBlob", b => + { + b.HasOne("Volo.Abp.BlobStoring.Database.DatabaseBlobContainer", null) + .WithMany() + .HasForeignKey("ContainerId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityRoleClaim", b => + { + b.HasOne("Volo.Abp.Identity.IdentityRole", null) + .WithMany("Claims") + .HasForeignKey("RoleId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserClaim", b => + { + b.HasOne("Volo.Abp.Identity.IdentityUser", null) + .WithMany("Claims") + .HasForeignKey("UserId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserLogin", b => + { + b.HasOne("Volo.Abp.Identity.IdentityUser", null) + .WithMany("Logins") + .HasForeignKey("UserId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserOrganizationUnit", b => + { + b.HasOne("Volo.Abp.Identity.OrganizationUnit", null) + .WithMany() + .HasForeignKey("OrganizationUnitId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + + b.HasOne("Volo.Abp.Identity.IdentityUser", null) + .WithMany("OrganizationUnits") + .HasForeignKey("UserId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserRole", b => + { + b.HasOne("Volo.Abp.Identity.IdentityRole", null) + .WithMany() + .HasForeignKey("RoleId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + + b.HasOne("Volo.Abp.Identity.IdentityUser", null) + .WithMany("Roles") + .HasForeignKey("UserId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUserToken", b => + { + b.HasOne("Volo.Abp.Identity.IdentityUser", null) + .WithMany("Tokens") + .HasForeignKey("UserId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + + modelBuilder.Entity("Volo.Abp.Identity.OrganizationUnit", b => + { + b.HasOne("Volo.Abp.Identity.OrganizationUnit", null) + .WithMany() + .HasForeignKey("ParentId"); + }); + + modelBuilder.Entity("Volo.Abp.Identity.OrganizationUnitRole", b => + { + b.HasOne("Volo.Abp.Identity.OrganizationUnit", null) + .WithMany("Roles") + .HasForeignKey("OrganizationUnitId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + + b.HasOne("Volo.Abp.Identity.IdentityRole", null) + .WithMany() + .HasForeignKey("RoleId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + + modelBuilder.Entity("Volo.Docs.Documents.DocumentContributor", b => + { + b.HasOne("Volo.Docs.Documents.Document", null) + .WithMany("Contributors") + .HasForeignKey("DocumentId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + + modelBuilder.Entity("Volo.Docs.Projects.ProjectPdfFile", b => + { + b.HasOne("Volo.Docs.Projects.Project", null) + .WithMany("PdfFiles") + .HasForeignKey("ProjectId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityRole", b => + { + b.Navigation("Claims"); + }); + + modelBuilder.Entity("Volo.Abp.Identity.IdentityUser", b => + { + b.Navigation("Claims"); + + b.Navigation("Logins"); + + b.Navigation("OrganizationUnits"); + + b.Navigation("Roles"); + + b.Navigation("Tokens"); + }); + + modelBuilder.Entity("Volo.Abp.Identity.OrganizationUnit", b => + { + b.Navigation("Roles"); + }); + + modelBuilder.Entity("Volo.Docs.Documents.Document", b => + { + b.Navigation("Contributors"); + }); + + modelBuilder.Entity("Volo.Docs.Projects.Project", b => + { + b.Navigation("PdfFiles"); + }); +#pragma warning restore 612, 618 + } + } +} diff --git a/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20250425082043_add_pdf_file.cs b/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20250425082043_add_pdf_file.cs new file mode 100644 index 0000000000..2f9f296c25 --- /dev/null +++ b/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/20250425082043_add_pdf_file.cs @@ -0,0 +1,44 @@ +using System; +using Microsoft.EntityFrameworkCore.Migrations; + +#nullable disable + +namespace Migrations +{ + /// + public partial class add_pdf_file : Migration + { + /// + protected override void Up(MigrationBuilder migrationBuilder) + { + migrationBuilder.CreateTable( + name: "DocsProjectPdfFiles", + columns: table => new + { + ProjectId = table.Column(type: "uniqueidentifier", nullable: false), + FileName = table.Column(type: "nvarchar(450)", nullable: false), + Version = table.Column(type: "nvarchar(max)", nullable: true), + LanguageCode = table.Column(type: "nvarchar(max)", nullable: true), + CreationTime = table.Column(type: "datetime2", nullable: false), + LastModificationTime = table.Column(type: "datetime2", nullable: true) + }, + constraints: table => + { + table.PrimaryKey("PK_DocsProjectPdfFiles", x => new { x.ProjectId, x.FileName }); + table.ForeignKey( + name: "FK_DocsProjectPdfFiles_DocsProjects_ProjectId", + column: x => x.ProjectId, + principalTable: "DocsProjects", + principalColumn: "Id", + onDelete: ReferentialAction.Cascade); + }); + } + + /// + protected override void Down(MigrationBuilder migrationBuilder) + { + migrationBuilder.DropTable( + name: "DocsProjectPdfFiles"); + } + } +} diff --git a/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/VoloDocsDbContextModelSnapshot.cs b/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/VoloDocsDbContextModelSnapshot.cs index 17e18940bb..14f36cafb1 100644 --- a/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/VoloDocsDbContextModelSnapshot.cs +++ b/modules/docs/app/VoloDocs.EntityFrameworkCore/Migrations/VoloDocsDbContextModelSnapshot.cs @@ -19,11 +19,88 @@ namespace Migrations #pragma warning disable 612, 618 modelBuilder .HasAnnotation("_Abp_DatabaseProvider", EfCoreDatabaseProvider.SqlServer) - .HasAnnotation("ProductVersion", "9.0.0") + .HasAnnotation("ProductVersion", "9.0.2") .HasAnnotation("Relational:MaxIdentifierLength", 128); SqlServerModelBuilderExtensions.UseIdentityColumns(modelBuilder); + modelBuilder.Entity("Volo.Abp.BlobStoring.Database.DatabaseBlob", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("ContainerId") + .HasColumnType("uniqueidentifier"); + + b.Property("Content") + .HasMaxLength(2147483647) + .HasColumnType("varbinary(max)"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(256) + .HasColumnType("nvarchar(256)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.HasIndex("ContainerId"); + + b.HasIndex("TenantId", "ContainerId", "Name"); + + b.ToTable("AbpBlobs", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.BlobStoring.Database.DatabaseBlobContainer", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("uniqueidentifier"); + + b.Property("ConcurrencyStamp") + .IsConcurrencyToken() + .IsRequired() + .HasMaxLength(40) + .HasColumnType("nvarchar(40)") + .HasColumnName("ConcurrencyStamp"); + + b.Property("ExtraProperties") + .IsRequired() + .HasColumnType("nvarchar(max)") + .HasColumnName("ExtraProperties"); + + b.Property("Name") + .IsRequired() + .HasMaxLength(128) + .HasColumnType("nvarchar(128)"); + + b.Property("TenantId") + .HasColumnType("uniqueidentifier") + .HasColumnName("TenantId"); + + b.HasKey("Id"); + + b.HasIndex("TenantId", "Name"); + + b.ToTable("AbpBlobContainers", (string)null); + }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityClaimType", b => { b.Property("Id") @@ -1116,6 +1193,42 @@ namespace Migrations b.ToTable("DocsProjects", (string)null); }); + modelBuilder.Entity("Volo.Docs.Projects.ProjectPdfFile", b => + { + b.Property("ProjectId") + .HasColumnType("uniqueidentifier"); + + b.Property("FileName") + .HasColumnType("nvarchar(450)"); + + b.Property("CreationTime") + .HasColumnType("datetime2") + .HasColumnName("CreationTime"); + + b.Property("LanguageCode") + .HasColumnType("nvarchar(max)"); + + b.Property("LastModificationTime") + .HasColumnType("datetime2") + .HasColumnName("LastModificationTime"); + + b.Property("Version") + .HasColumnType("nvarchar(max)"); + + b.HasKey("ProjectId", "FileName"); + + b.ToTable("DocsProjectPdfFiles", (string)null); + }); + + modelBuilder.Entity("Volo.Abp.BlobStoring.Database.DatabaseBlob", b => + { + b.HasOne("Volo.Abp.BlobStoring.Database.DatabaseBlobContainer", null) + .WithMany() + .HasForeignKey("ContainerId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityRoleClaim", b => { b.HasOne("Volo.Abp.Identity.IdentityRole", null) @@ -1213,6 +1326,15 @@ namespace Migrations .IsRequired(); }); + modelBuilder.Entity("Volo.Docs.Projects.ProjectPdfFile", b => + { + b.HasOne("Volo.Docs.Projects.Project", null) + .WithMany("PdfFiles") + .HasForeignKey("ProjectId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); + modelBuilder.Entity("Volo.Abp.Identity.IdentityRole", b => { b.Navigation("Claims"); @@ -1240,6 +1362,11 @@ namespace Migrations { b.Navigation("Contributors"); }); + + modelBuilder.Entity("Volo.Docs.Projects.Project", b => + { + b.Navigation("PdfFiles"); + }); #pragma warning restore 612, 618 } } diff --git a/modules/docs/app/VoloDocs.EntityFrameworkCore/VoloDocs.EntityFrameworkCore.csproj b/modules/docs/app/VoloDocs.EntityFrameworkCore/VoloDocs.EntityFrameworkCore.csproj index 38f85e7541..f7a6f89231 100644 --- a/modules/docs/app/VoloDocs.EntityFrameworkCore/VoloDocs.EntityFrameworkCore.csproj +++ b/modules/docs/app/VoloDocs.EntityFrameworkCore/VoloDocs.EntityFrameworkCore.csproj @@ -13,6 +13,7 @@ + diff --git a/modules/docs/app/VoloDocs.EntityFrameworkCore/VoloDocsDbContext.cs b/modules/docs/app/VoloDocs.EntityFrameworkCore/VoloDocsDbContext.cs index fb6aca4e19..08ca58dd72 100644 --- a/modules/docs/app/VoloDocs.EntityFrameworkCore/VoloDocsDbContext.cs +++ b/modules/docs/app/VoloDocs.EntityFrameworkCore/VoloDocsDbContext.cs @@ -1,4 +1,5 @@ using Microsoft.EntityFrameworkCore; +using Volo.Abp.BlobStoring.Database.EntityFrameworkCore; using Volo.Abp.EntityFrameworkCore; using Volo.Abp.Identity.EntityFrameworkCore; using Volo.Abp.PermissionManagement.EntityFrameworkCore; @@ -23,6 +24,7 @@ namespace VoloDocs.EntityFrameworkCore modelBuilder.ConfigureSettingManagement(); modelBuilder.ConfigureIdentity(); modelBuilder.ConfigureDocs(); + modelBuilder.ConfigureBlobStoring(); } } } diff --git a/modules/docs/app/VoloDocs.EntityFrameworkCore/VoloDocsEntityFrameworkCoreModule.cs b/modules/docs/app/VoloDocs.EntityFrameworkCore/VoloDocsEntityFrameworkCoreModule.cs index 44acea9a58..f94ec123bf 100644 --- a/modules/docs/app/VoloDocs.EntityFrameworkCore/VoloDocsEntityFrameworkCoreModule.cs +++ b/modules/docs/app/VoloDocs.EntityFrameworkCore/VoloDocsEntityFrameworkCoreModule.cs @@ -1,4 +1,5 @@ -using Volo.Abp.EntityFrameworkCore.SqlServer; +using Volo.Abp.BlobStoring.Database.EntityFrameworkCore; +using Volo.Abp.EntityFrameworkCore.SqlServer; using Volo.Abp.Identity.EntityFrameworkCore; using Volo.Abp.Modularity; using Volo.Abp.PermissionManagement.EntityFrameworkCore; @@ -12,6 +13,7 @@ namespace VoloDocs.EntityFrameworkCore typeof(AbpIdentityEntityFrameworkCoreModule), typeof(AbpPermissionManagementEntityFrameworkCoreModule), typeof(AbpSettingManagementEntityFrameworkCoreModule), + typeof(BlobStoringDatabaseEntityFrameworkCoreModule), typeof(AbpEntityFrameworkCoreSqlServerModule))] public class VoloDocsEntityFrameworkCoreModule : AbpModule { diff --git a/modules/docs/app/VoloDocs.Migrator/appsettings.json b/modules/docs/app/VoloDocs.Migrator/appsettings.json index b554a47fed..9668adc1e2 100644 --- a/modules/docs/app/VoloDocs.Migrator/appsettings.json +++ b/modules/docs/app/VoloDocs.Migrator/appsettings.json @@ -1,3 +1,3 @@ { - "ConnectionString": "Server=localhost;Database=VoloDocs;Trusted_Connection=True;TrustServerCertificate=True" + "ConnectionString": "Server=localhost;Database=VoloDocs;Trusted_Connection=True;TrustServerCertificate=True", } \ No newline at end of file diff --git a/modules/docs/app/VoloDocs.Web/Pages/Index.cshtml.cs b/modules/docs/app/VoloDocs.Web/Pages/Index.cshtml.cs index c335612ec4..512900e637 100644 --- a/modules/docs/app/VoloDocs.Web/Pages/Index.cshtml.cs +++ b/modules/docs/app/VoloDocs.Web/Pages/Index.cshtml.cs @@ -5,7 +5,7 @@ using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.RazorPages; using Microsoft.Extensions.Options; using Volo.Docs; -using Volo.Docs.Projects; +using Volo.Docs.Common.Projects; namespace VoloDocs.Web.Pages { diff --git a/modules/docs/app/VoloDocs.Web/VoloDocsWebModule.cs b/modules/docs/app/VoloDocs.Web/VoloDocsWebModule.cs index 743944c6d3..297a15c88d 100644 --- a/modules/docs/app/VoloDocs.Web/VoloDocsWebModule.cs +++ b/modules/docs/app/VoloDocs.Web/VoloDocsWebModule.cs @@ -32,10 +32,14 @@ using Localization.Resources.AbpUi; using Microsoft.AspNetCore.Http; using Microsoft.Extensions.Hosting; using Volo.Abp.Account; +using Volo.Abp.BlobStoring; +using Volo.Abp.BlobStoring.Database; using Volo.Abp.PermissionManagement.HttpApi; using Volo.Abp.Validation.Localization; using Volo.Docs.Documents.FullSearch.Elastic; using Volo.Abp.Caching.StackExchangeRedis; +using Volo.Docs.Common.Documents; +using Volo.Docs.Projects.Pdf; namespace VoloDocs.Web { @@ -82,7 +86,7 @@ namespace VoloDocs.Web // options.SingleProjectMode.ProjectName = "abp"; // options.MultiLanguageMode = false; // }); - + Configure(options => { options.Enable = false; @@ -170,6 +174,22 @@ namespace VoloDocs.Web options.EnableGoogleProgrammableSearchEngine = true; options.GoogleSearchEngineId = "77c7266532da1427f"; }); + + Configure(options => + { + options.BaseUrl = configuration["App:selfUrl"]; + options.IndexPagePath = "Index.md"; + options.CalculatePdfFileTitle = project => project.ShortName == "abp" ? "ABP Documentation" : null; + options.DocumentContentNormalizer = content => content.Replace("", "No").Replace("", "Yes"); + }); + + Configure(options => + { + options.Containers.ConfigureDefault(container => + { + container.UseDatabase(); + }); + }); } public override void OnApplicationInitialization(ApplicationInitializationContext context) diff --git a/modules/docs/app/VoloDocs.Web/appsettings.json b/modules/docs/app/VoloDocs.Web/appsettings.json index 21a2883937..38400900f4 100644 --- a/modules/docs/app/VoloDocs.Web/appsettings.json +++ b/modules/docs/app/VoloDocs.Web/appsettings.json @@ -1,4 +1,7 @@ { + "App": { + "selfUrl": "https://localhost:5001" + }, "Kestrel": { "EndPoints": { "Https": { diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo.Docs.Admin.Application.Contracts.csproj b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo.Docs.Admin.Application.Contracts.csproj index a49d9146db..796a4a83c4 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo.Docs.Admin.Application.Contracts.csproj +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo.Docs.Admin.Application.Contracts.csproj @@ -18,6 +18,7 @@ + diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/DocsAdminApplicationContractsModule.cs b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/DocsAdminApplicationContractsModule.cs index 0962a28aef..1e20041974 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/DocsAdminApplicationContractsModule.cs +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/DocsAdminApplicationContractsModule.cs @@ -4,6 +4,7 @@ using Volo.Abp.Authorization.Permissions; using Volo.Abp.Localization; using Volo.Abp.Modularity; using Volo.Abp.VirtualFileSystem; +using Volo.Docs.Common; using Volo.Docs.Localization; namespace Volo.Docs.Admin @@ -11,7 +12,8 @@ namespace Volo.Docs.Admin [DependsOn( typeof(DocsDomainSharedModule), typeof(AbpDddApplicationContractsModule), - typeof(AbpAuthorizationAbstractionsModule) + typeof(AbpAuthorizationAbstractionsModule), + typeof(DocsCommonApplicationContractsModule) )] public class DocsAdminApplicationContractsModule : AbpModule { diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/DocsAdminPermissionDefinitionProvider.cs b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/DocsAdminPermissionDefinitionProvider.cs index 6f9bb6407e..0ce42e3143 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/DocsAdminPermissionDefinitionProvider.cs +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/DocsAdminPermissionDefinitionProvider.cs @@ -14,6 +14,7 @@ namespace Volo.Docs.Admin projects.AddChild(DocsAdminPermissions.Projects.Update, L("Permission:Edit")); projects.AddChild(DocsAdminPermissions.Projects.Delete, L("Permission:Delete")); projects.AddChild(DocsAdminPermissions.Projects.Create, L("Permission:Create")); + projects.AddChild(DocsAdminPermissions.Projects.ManagePdfFiles, L("Permission:ManagePdfFiles")); group.AddPermission(DocsAdminPermissions.Documents.Default, L("Permission:Documents")); } diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/DocsAdminPermissions.cs b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/DocsAdminPermissions.cs index e6043241ea..f5d9a94410 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/DocsAdminPermissions.cs +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/DocsAdminPermissions.cs @@ -12,6 +12,7 @@ namespace Volo.Docs.Admin public const string Delete = Default + ".Delete"; public const string Update = Default + ".Update"; public const string Create = Default + ".Create"; + public const string ManagePdfFiles = Default + ".ManagePdfFiles"; } public static class Documents diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/ar.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/ar.json index 458d1592f0..bd93067140 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/ar.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/ar.json @@ -57,6 +57,15 @@ "LastCachedTime": "وقت ذاكرة التخزين", "Project": "مشروع ", "AdvancedFilters": "مرشحات متقدمة", - "RemoveCacheAndReIndexConfirmation": "ستتم إزالة المستند \"{0}\" من ذاكرة التخزين المؤقت وإعادة فهرسته. هل تؤكد؟" + "RemoveCacheAndReIndexConfirmation": "ستتم إزالة المستند \"{0}\" من ذاكرة التخزين المؤقت وإعادة فهرسته. هل تؤكد؟", + "GeneratePdf": "توليد PDF", + "Generating": "يتم توليد...", + "Language": "اللغة", + "ForceToGenerateNewPdf": "قوة لتوليد PDF جديد", + "PdfGeneratedSuccessfully": "تم توليد PDF بنجاح", + "GenerateAndDownloadPdf": "توليد وتحميل PDF", + "PdfFileDeletionWarningMessage": "هل أنت متأكد أنك تريد حذف ملف PDF \"{0}\"?", + "ManagePdfFiles": "إدارة ملفات PDF", + "Permission:ManagePdfFiles": "إدارة ملفات PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/cs.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/cs.json index ff6c135a90..9543166ac4 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/cs.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/cs.json @@ -57,6 +57,15 @@ "LastCachedTime": "Čas uložení v mezipaměti", "Project": "Projekt", "AdvancedFilters": "Pokročilé filtry", - "RemoveCacheAndReIndexConfirmation": "Dokument \"{0}\" bude odstraněn z mezipaměti a znovu zaindexován. Potvrzujete to?" + "RemoveCacheAndReIndexConfirmation": "Dokument \"{0}\" bude odstraněn z mezipaměti a znovu zaindexován. Potvrzujete to?", + "GeneratePdf": "Generovat PDF", + "Generating": "Generování...", + "Language": "Jazyk", + "ForceToGenerateNewPdf": "Vynutit generování nového PDF", + "PdfGeneratedSuccessfully": "PDF generován úspěšně", + "GenerateAndDownloadPdf": "Generovat a stáhnout PDF", + "PdfFileDeletionWarningMessage": "Opravdu chcete odstranit soubor PDF \"{0}\"?", + "ManagePdfFiles": "Správa PDF souborů", + "Permission:ManagePdfFiles": "Správa PDF souborů" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/de-DE.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/de-DE.json index ce7c8cafb0..a69c9283ea 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/de-DE.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/de-DE.json @@ -56,6 +56,15 @@ "FileName": "Dateiname", "LastCachedTime": "Cache-Zeit", "Project": "Projekt", - "RemoveCacheAndReIndexConfirmation": "Das Dokument \"{0}\" wird aus dem Cache entfernt und neu indiziert. Können Sie das bestätigen?" + "RemoveCacheAndReIndexConfirmation": "Das Dokument \"{0}\" wird aus dem Cache entfernt und neu indiziert. Können Sie das bestätigen?", + "GeneratePdf": "PDF generieren", + "Generating": "Generieren...", + "Language": "Sprache", + "ForceToGenerateNewPdf": "Neues PDF erzwingen", + "PdfGeneratedSuccessfully": "PDF erfolgreich generiert", + "GenerateAndDownloadPdf": "PDF generieren und herunterladen", + "PdfFileDeletionWarningMessage": "Sind Sie sicher, dass Sie das PDF-Datei \"{0}\" löschen wollen?", + "ManagePdfFiles": "PDF-Dateien verwalten", + "Permission:ManagePdfFiles": "PDF-Dateien verwalten" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/de.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/de.json index 0fd1c535b2..1278047f50 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/de.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/de.json @@ -57,6 +57,15 @@ "LastCachedTime": "Zwischenspeicher", "Project": "Projekt", "AdvancedFilters": "Erweiterte Filter", - "RemoveCacheAndReIndexConfirmation": "Das Dokument „{0}“ wird aus dem Cache entfernt und neu indiziert. Bestätigen Sie?" + "RemoveCacheAndReIndexConfirmation": "Das Dokument „{0}“ wird aus dem Cache entfernt und neu indiziert. Bestätigen Sie?", + "GeneratePdf": "PDF generieren", + "Generating": "Generieren...", + "Language": "Sprache", + "ForceToGenerateNewPdf": "Neues PDF erzwingen", + "PdfGeneratedSuccessfully": "PDF erfolgreich generiert", + "GenerateAndDownloadPdf": "PDF generieren und herunterladen", + "PdfFileDeletionWarningMessage": "Sind Sie sicher, dass Sie das PDF-Datei \"{0}\" löschen wollen?", + "ManagePdfFiles": "PDF-Dateien verwalten", + "Permission:ManagePdfFiles": "PDF-Dateien verwalten" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/el.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/el.json index c2a3f69a53..ae8108dfb5 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/el.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/el.json @@ -56,6 +56,15 @@ "FileName": "Όνομα αρχείου", "LastCachedTime": "Χρόνος προσωρινής αποθήκευσης", "Project": "Εργο", - "RemoveCacheAndReIndexConfirmation": "Το έγγραφο \"{0}\" θα αφαιρεθεί από την προσωρινή μνήμη και θα αναπροσαρμοστεί εκ νέου. Επιβεβαιώνετε;" + "RemoveCacheAndReIndexConfirmation": "Το έγγραφο \"{0}\" θα αφαιρεθεί από την προσωρινή μνήμη και θα αναπροσαρμοστεί εκ νέου. Επιβεβαιώνετε;", + "GeneratePdf": "Δημιουργία PDF", + "Generating": "Δημιουργία...", + "Language": "Γλώσσα", + "ForceToGenerateNewPdf": "Βάλτε το νέο PDF", + "PdfGeneratedSuccessfully": "Το PDF αναπροσαρμοστεί εκ νέου", + "GenerateAndDownloadPdf": "Δημιουργία και λήψη PDF", + "PdfFileDeletionWarningMessage": "Είστε βέβαιοι ότι θέλετε να διαγράψετε το PDF αρχείο \"{0}\";", + "ManagePdfFiles": "Διαχείρηση PDF αρχείων", + "Permission:ManagePdfFiles": "Διαχείρηση PDF αρχείων" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/en-GB.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/en-GB.json index d72c523ef5..6ed2bb94cd 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/en-GB.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/en-GB.json @@ -56,6 +56,15 @@ "FileName": "File name", "LastCachedTime": "Cache time", "Project": "Project", - "AdvancedFilters": "Advanced Filters" + "AdvancedFilters": "Advanced Filters", + "GeneratePdf": "Generate PDF", + "Generating": "Generating...", + "Language": "Language", + "ForceToGenerateNewPdf": "Force to generate new PDF", + "PdfGeneratedSuccessfully": "PDF generated successfully", + "GenerateAndDownloadPdf": "Generate and download PDF", + "PdfFileDeletionWarningMessage": "Are you sure you want to delete the PDF file \"{0}\"?", + "ManagePdfFiles": "Manage PDF files", + "Permission:ManagePdfFiles": "Manage PDF files" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/en.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/en.json index 5302cdcffb..bc606f7df7 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/en.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/en.json @@ -57,6 +57,15 @@ "LastCachedTime": "Cache time", "Project": "Project", "AdvancedFilters": "Advanced Filters", - "RemoveCacheAndReIndexConfirmation": "The document \"{0}\" will be removed from the cache and re-indexed. Do you confirm?" + "RemoveCacheAndReIndexConfirmation": "The document \"{0}\" will be removed from the cache and re-indexed. Do you confirm?", + "GeneratePdf": "Generate PDF", + "Generating": "Generating...", + "Language": "Language", + "ForceToGenerateNewPdf": "Force to generate new PDF", + "PdfGeneratedSuccessfully": "PDF generated successfully", + "GenerateAndDownloadPdf": "Generate and download PDF", + "PdfFileDeletionWarningMessage": "Are you sure you want to delete the PDF file \"{0}\"?", + "ManagePdfFiles": "Manage PDF files", + "Permission:ManagePdfFiles": "Manage PDF files" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/es.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/es.json index 911fe2745a..79937b772d 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/es.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/es.json @@ -57,6 +57,15 @@ "LastCachedTime": "Última actualización de caché", "Project": "Proyecto", "AdvancedFilters": "Filtros avanzados", - "RemoveCacheAndReIndexConfirmation": "El documento \"{0}\" será eliminado de la caché y reindexado. ¿Lo confirma?" + "RemoveCacheAndReIndexConfirmation": "El documento \"{0}\" será eliminado de la caché y reindexado. ¿Lo confirma?", + "GeneratePdf": "Generar PDF", + "Generating": "Generando...", + "Language": "Idioma", + "ForceToGenerateNewPdf": "Forzar a generar un nuevo PDF", + "PdfGeneratedSuccessfully": "PDF generado correctamente", + "GenerateAndDownloadPdf": "Generar y descargar PDF", + "PdfFileDeletionWarningMessage": "¿Está seguro de querer eliminar el archivo PDF \"{0}\"?", + "ManagePdfFiles": "Administrar archivos PDF", + "Permission:ManagePdfFiles": "Administrar archivos PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/fi.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/fi.json index e3e826c1b7..d227037f32 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/fi.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/fi.json @@ -57,6 +57,15 @@ "LastCachedTime": "Välimuistin aika", "Project": "Projekti", "AdvancedFilters": "Edistyneet suodattimet", - "RemoveCacheAndReIndexConfirmation": "Dokumentti \"{0}\" poistetaan välimuistista ja indeksoidaan uudelleen. Vahvistatko?" + "RemoveCacheAndReIndexConfirmation": "Dokumentti \"{0}\" poistetaan välimuistista ja indeksoidaan uudelleen. Vahvistatko?", + "GeneratePdf": "Generoi PDF", + "Generating": "Generoiminen...", + "Language": "Kieli", + "ForceToGenerateNewPdf": "Vahvista uusi PDF", + "PdfGeneratedSuccessfully": "PDF generoidaan onnistuneesti", + "GenerateAndDownloadPdf": "Generoi ja lataa PDF", + "PdfFileDeletionWarningMessage": "Oletko varma, että haluat poistaa PDF-tiedoston \"{0}\"?", + "ManagePdfFiles": "Hallitse PDF-tiedostoja", + "Permission:ManagePdfFiles": "Hallitse PDF-tiedostoja" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/fr.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/fr.json index b2fdef8201..6efe4fe888 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/fr.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/fr.json @@ -57,6 +57,15 @@ "LastCachedTime": "Temps de cache", "Project": "Projet", "AdvancedFilters": "Filtres avancés", - "RemoveCacheAndReIndexConfirmation": "Le document \"{0}\" sera supprimé du cache et réindexé. Confirmez-vous ?" + "RemoveCacheAndReIndexConfirmation": "Le document \"{0}\" sera supprimé du cache et réindexé. Confirmez-vous ?", + "GeneratePdf": "Générer PDF", + "Generating": "Génération...", + "Language": "Langue", + "ForceToGenerateNewPdf": "Forcer à générer un nouveau PDF", + "PdfGeneratedSuccessfully": "PDF généré avec succès", + "GenerateAndDownloadPdf": "Générer et télécharger PDF", + "PdfFileDeletionWarningMessage": "Êtes-vous sûr de vouloir supprimer le fichier PDF \"{0}\"?", + "ManagePdfFiles": "Gérer les fichiers PDF", + "Permission:ManagePdfFiles": "Gérer les fichiers PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/hi.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/hi.json index adad5e064f..cdca790f20 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/hi.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/hi.json @@ -57,6 +57,15 @@ "LastCachedTime": "कैश समय", "Project": "परियोजना", "AdvancedFilters": "उन्नत फ़िल्टर", - "RemoveCacheAndReIndexConfirmation": "दस्u200Dतावेज़ \"{0}\" को संचय से हटा दिया जाएगा और पुन: अनुक्रमित किया जाएगा। क्या आप पुष्टि करते हैं?" + "RemoveCacheAndReIndexConfirmation": "दस्तावेज़ \"{0}\" को संचय से हटा दिया जाएगा और पुन: अनुक्रमित किया जाएगा। क्या आप पुष्टि करते हैं?", + "GeneratePdf": "PDF उत्पन्न करें", + "Generating": "उत्पन्न कर रहा है...", + "Language": "भाषा", + "ForceToGenerateNewPdf": "नया PDF उत्पन्न करें", + "PdfGeneratedSuccessfully": "PDF सफलतापूर्वक उत्पन्न हो गया", + "GenerateAndDownloadPdf": "PDF उत्पन्न और डाउनलोड करें", + "PdfFileDeletionWarningMessage": "क्या आप वाकई \"{0}\" के PDF फ़ाइल को हटाना चाहते हैं?", + "ManagePdfFiles": "PDF फ़ाइलें प्रबंधित करें", + "Permission:ManagePdfFiles": "PDF फ़ाइलें प्रबंधित करें" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/hr.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/hr.json index cf0a31368f..547484a062 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/hr.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/hr.json @@ -57,6 +57,15 @@ "LastCachedTime": "Vrijeme predmemorije", "Project": "Projekt", "AdvancedFilters": "Napredni filtri", - "RemoveCacheAndReIndexConfirmation": "Dokument \"{0}\" bit će uklonjen iz predmemorije i ponovno indeksiran. Potvrđujete li?" + "RemoveCacheAndReIndexConfirmation": "Dokument \"{0}\" bit će uklonjen iz predmemorije i ponovno indeksiran. Potvrđujete li?", + "GeneratePdf": "Generiraj PDF", + "Generating": "Generiranje...", + "Language": "Jezik", + "ForceToGenerateNewPdf": "Prisili generiranje novog PDF-a", + "PdfGeneratedSuccessfully": "PDF generiran uspješno", + "GenerateAndDownloadPdf": "Generiraj i preuzmi PDF", + "PdfFileDeletionWarningMessage": "Jeste li sigurni da želite izbrisati PDF datoteku \"{0}\"?", + "ManagePdfFiles": "Upravljanje PDF datotekama", + "Permission:ManagePdfFiles": "Upravljanje PDF datotekama" } } diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/hu.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/hu.json index 587f67e72c..581910f9e9 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/hu.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/hu.json @@ -58,6 +58,15 @@ "LastCachedTime": "Cache idő", "Project": "Projekt", "AdvancedFilters": "Speciális szűrők", - "RemoveCacheAndReIndexConfirmation": "A \"{0}\" dokumentumot eltávolítjuk a gyorsítótárból és újraindexeljük. Megerősíti?" + "RemoveCacheAndReIndexConfirmation": "A \"{0}\" dokumentumot eltávolítjuk a gyorsítótárból és újraindexeljük. Megerősíti?", + "GeneratePdf": "PDF generálása", + "Generating": "Generálás...", + "Language": "Nyelv", + "ForceToGenerateNewPdf": "Új PDF generálása", + "PdfGeneratedSuccessfully": "PDF generálás sikeres", + "GenerateAndDownloadPdf": "Generálás és letöltés PDF-ben", + "PdfFileDeletionWarningMessage": "Biztosan törölni szeretné a \"{0}\" PDF fájlt?", + "ManagePdfFiles": "PDF fájlok kezelése", + "Permission:ManagePdfFiles": "PDF fájlok kezelése" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/is.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/is.json index c3e8fa957b..64b41ce3b7 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/is.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/is.json @@ -57,6 +57,15 @@ "LastCachedTime": "Tími geymt í skyndiminni", "Project": "Verkefni", "AdvancedFilters": "Ítarlegar síur", - "RemoveCacheAndReIndexConfirmation": "Skjalið \"{0}\" verður fjarlægt úr skyndiminni og endurtryggt. Staðfestir þú?" + "RemoveCacheAndReIndexConfirmation": "Skjalið \"{0}\" verður fjarlægt úr skyndiminni og endurtryggt. Staðfestir þú?", + "GeneratePdf": "Generate PDF", + "Generating": "Generating...", + "Language": "Language", + "ForceToGenerateNewPdf": "Force to generate new PDF", + "PdfGeneratedSuccessfully": "PDF generated successfully", + "GenerateAndDownloadPdf": "Generate and download PDF", + "PdfFileDeletionWarningMessage": "Are you sure you want to delete the PDF file \"{0}\"?", + "ManagePdfFiles": "Manage PDF files", + "Permission:ManagePdfFiles": "Manage PDF files" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/it.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/it.json index 40f94e8077..29e7d1ba80 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/it.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/it.json @@ -57,6 +57,15 @@ "LastCachedTime": "Tempo di cache", "Project": "Progetto", "AdvancedFilters": "Filtri avanzati", - "RemoveCacheAndReIndexConfirmation": "Il documento \"{0}\" verrà rimosso dalla cache e reindicizzato. Confermate?" + "RemoveCacheAndReIndexConfirmation": "Il documento \"{0}\" verrà rimosso dalla cache e reindicizzato. Confermate?", + "GeneratePdf": "Genera PDF", + "Generating": "Generazione...", + "Language": "Lingua", + "ForceToGenerateNewPdf": "Forza a generare un nuovo PDF", + "PdfGeneratedSuccessfully": "PDF generato con successo", + "GenerateAndDownloadPdf": "Genera e scarica PDF", + "PdfFileDeletionWarningMessage": "Sei sicuro di voler eliminare il file PDF \"{0}\"?", + "ManagePdfFiles": "Gestione file PDF", + "Permission:ManagePdfFiles": "Gestione file PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/nl.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/nl.json index 201d7c5da0..6f43a26ac8 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/nl.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/nl.json @@ -57,6 +57,15 @@ "LastCachedTime": "Cache tijd", "Project": "Project", "AdvancedFilters": "Geavanceerde filters", - "RemoveCacheAndReIndexConfirmation": "Het document \"{0}\" wordt uit de cache verwijderd en opnieuw geïndexeerd. Bevestigt u?" + "RemoveCacheAndReIndexConfirmation": "Het document \"{0}\" wordt uit de cache verwijderd en opnieuw geïndexeerd. Bevestigt u?", + "GeneratePdf": "PDF genereren", + "Generating": "Genereren...", + "Language": "Taal", + "ForceToGenerateNewPdf": "Forceer nieuwe PDF te genereren", + "PdfGeneratedSuccessfully": "PDF succesvol gegenereerd", + "GenerateAndDownloadPdf": "PDF genereren en downloaden", + "PdfFileDeletionWarningMessage": "Weet u zeker dat u het PDF-bestand \"{0}\" wilt verwijderen?", + "ManagePdfFiles": "PDF-bestanden beheren", + "Permission:ManagePdfFiles": "PDF-bestanden beheren" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/pl-PL.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/pl-PL.json index ec9de0de07..a93ee2bd0f 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/pl-PL.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/pl-PL.json @@ -57,6 +57,15 @@ "LastCachedTime": "Czas w pamięci podręcznej", "Project": "Projekt", "AdvancedFilters": "Zaawansowane filtry", - "RemoveCacheAndReIndexConfirmation": "Dokument \"{0}\" zostanie usunięty z pamięci podręcznej i ponownie zaindeksowany. Czy potwierdzasz?" + "RemoveCacheAndReIndexConfirmation": "Dokument \"{0}\" zostanie usunięty z pamięci podręcznej i ponownie zaindeksowany. Czy potwierdzasz?", + "GeneratePdf": "Generuj PDF", + "Generating": "Generowanie...", + "Language": "Język", + "ForceToGenerateNewPdf": "Wymuś generowanie nowego PDF", + "PdfGeneratedSuccessfully": "PDF został pomyślnie wygenerowany", + "GenerateAndDownloadPdf": "Generuj i pobierz PDF", + "PdfFileDeletionWarningMessage": "Czy na pewno chcesz usunąć plik PDF \"{0}\"?", + "ManagePdfFiles": "Zarządzanie plikami PDF", + "Permission:ManagePdfFiles": "Zarządzanie plikami PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/pt-BR.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/pt-BR.json index b34ab4b9ef..ff8be45830 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/pt-BR.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/pt-BR.json @@ -57,6 +57,15 @@ "LastCachedTime": "Tempo de cache", "Project": "Projeto", "AdvancedFilters": "Filtros Avançados", - "RemoveCacheAndReIndexConfirmation": "O documento \"{0}\" será removido do cache e indexado novamente. Você confirma?" + "RemoveCacheAndReIndexConfirmation": "O documento \"{0}\" será removido do cache e indexado novamente. Você confirma?", + "GeneratePdf": "Gerar PDF", + "Generating": "Gerando...", + "Language": "Idioma", + "ForceToGenerateNewPdf": "Forçar para gerar um novo PDF", + "PdfGeneratedSuccessfully": "PDF gerado com sucesso", + "GenerateAndDownloadPdf": "Gerar e baixar PDF", + "PdfFileDeletionWarningMessage": "Tem certeza de que deseja excluir o arquivo PDF \"{0}\"?", + "ManagePdfFiles": "Gerenciar arquivos PDF", + "Permission:ManagePdfFiles": "Gerenciar arquivos PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/ro-RO.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/ro-RO.json index f055110a2f..68f40183d8 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/ro-RO.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/ro-RO.json @@ -57,6 +57,15 @@ "LastCachedTime": "Durată cache", "Project": "Proiect", "AdvancedFilters": "Filtre avansate", - "RemoveCacheAndReIndexConfirmation": "Documentul \"{0}\" va fi eliminat din memoria cache și va fi reindexat. Confirmați?" + "RemoveCacheAndReIndexConfirmation": "Documentul \"{0}\" va fi eliminat din memoria cache și va fi reindexat. Confirmați?", + "GeneratePdf": "Generare PDF", + "Generating": "Generare...", + "Language": "Limba", + "ForceToGenerateNewPdf": "Forțați generarea unui nou PDF", + "PdfGeneratedSuccessfully": "PDF generat cu succes", + "GenerateAndDownloadPdf": "Generare și descărcare PDF", + "PdfFileDeletionWarningMessage": "Sunteți sigur(ă) că doriți să ștergeți fișierul PDF \"{0}\"?", + "ManagePdfFiles": "Gestionare fișiere PDF", + "Permission:ManagePdfFiles": "Gestionare fișiere PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/ru.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/ru.json index 5f9836d957..bc2691121d 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/ru.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/ru.json @@ -57,6 +57,15 @@ "LastCachedTime": "Время кеширования", "Project": "Проект", "AdvancedFilters": "Расширенные фильтры", - "RemoveCacheAndReIndexConfirmation": "Документ \"{0}\" будет удален из кэша и переиндексирован. Вы подтверждаете?" + "RemoveCacheAndReIndexConfirmation": "Документ \"{0}\" будет удален из кэша и переиндексирован. Вы подтверждаете?", + "GeneratePdf": "Генерировать PDF", + "Generating": "Генерация...", + "Language": "Язык", + "ForceToGenerateNewPdf": "Принудительное создание нового PDF", + "PdfGeneratedSuccessfully": "PDF успешно сгенерирован", + "GenerateAndDownloadPdf": "Сгенерировать и скачать PDF", + "PdfFileDeletionWarningMessage": "Вы уверены, что хотите удалить файл PDF \"{0}\"?", + "ManagePdfFiles": "Управление файлами PDF", + "Permission:ManagePdfFiles": "Управление файлами PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/sk.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/sk.json index 53578e22dd..8b06da0e82 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/sk.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/sk.json @@ -57,6 +57,15 @@ "LastCachedTime": "Čas vyrovnávacej pamäte", "Project": "Projekt", "AdvancedFilters": "Pokročilé filtre", - "RemoveCacheAndReIndexConfirmation": "Dokument \"{0}\" sa odstráni z vyrovnávacej pamäte a znovu sa zaindexuje. Potvrdzujete?" + "RemoveCacheAndReIndexConfirmation": "Dokument \"{0}\" sa odstráni z vyrovnávacej pamäte a znovu sa zaindexuje. Potvrdzujete?", + "GeneratePdf": "Generovať PDF", + "Generating": "Generovanie...", + "Language": "Jazyk", + "ForceToGenerateNewPdf": "Vynútiť generovanie nového PDF", + "PdfGeneratedSuccessfully": "PDF generovaný úspešne", + "GenerateAndDownloadPdf": "Generovať a stiahnuť PDF", + "PdfFileDeletionWarningMessage": "Ste si istý, že chcete odstrániť súbor PDF \"{0}\"?", + "ManagePdfFiles": "Správa PDF súborov", + "Permission:ManagePdfFiles": "Správa PDF súborov" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/sl.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/sl.json index 3bcfcd4e85..0fe64f8903 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/sl.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/sl.json @@ -57,6 +57,15 @@ "LastCachedTime": "Čas pred pomnilnika", "Project": "Projekt", "AdvancedFilters": "Napredni filtri", - "RemoveCacheAndReIndexConfirmation": "Dokument »{0}« bo odstranjen iz predpomnilnika in ponovno indeksiran. Ali potrjuješ?" + "RemoveCacheAndReIndexConfirmation": "Dokument »{0}« bo odstranjen iz predpomnilnika in ponovno indeksiran. Ali potrjuješ?", + "GeneratePdf": "Generiraj PDF", + "Generating": "Generiranje...", + "Language": "Jezik", + "ForceToGenerateNewPdf": "Prisili generiranje novega PDF", + "PdfGeneratedSuccessfully": "PDF generiran uspešno", + "GenerateAndDownloadPdf": "Generiraj in prenesi PDF", + "PdfFileDeletionWarningMessage": "Ali ste prepričani, da želite izbrisati datoteko PDF »{0}«?", + "ManagePdfFiles": "Upravljanje datotek PDF", + "Permission:ManagePdfFiles": "Upravljanje datotek PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/sv.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/sv.json index cbde97c756..db67ecb79b 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/sv.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/sv.json @@ -57,6 +57,15 @@ "LastCachedTime": "Cache-tid", "Project": "Projekt", "AdvancedFilters": "Avancerade filter", - "RemoveCacheAndReIndexConfirmation": "Dokumentet \"{0}\" kommer att tas bort från cacheminnet och indexeras på nytt. Kan du bekräfta detta?" + "RemoveCacheAndReIndexConfirmation": "Dokumentet \"{0}\" kommer att tas bort från cacheminnet och indexeras på nytt. Kan du bekräfta detta?", + "GeneratePdf": "Generera PDF", + "Generating": "Genererar...", + "Language": "Språk", + "ForceToGenerateNewPdf": "Force to generate new PDF", + "PdfGeneratedSuccessfully": "PDF generated successfully", + "GenerateAndDownloadPdf": "Generate and download PDF", + "PdfFileDeletionWarningMessage": "Are you sure you want to delete the PDF file \"{0}\"?", + "ManagePdfFiles": "Manage PDF files", + "Permission:ManagePdfFiles": "Manage PDF files" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/tr.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/tr.json index ab600c1db5..42283a4b89 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/tr.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/tr.json @@ -57,6 +57,15 @@ "LastCachedTime": "Önbellek süresi", "Project": "Proje", "AdvancedFilters": "Gelişmiş Filtre", - "RemoveCacheAndReIndexConfirmation": "\"{0}\" belgesi önbellekten kaldırılacak ve yeniden indekslenecektir. Onaylıyor musunuz?" + "RemoveCacheAndReIndexConfirmation": "\"{0}\" belgesi önbellekten kaldırılacak ve yeniden indekslenecektir. Onaylıyor musunuz?", + "GeneratePdf": "PDF oluştur", + "Generating": "Oluşturuluyor...", + "Language": "Dil", + "ForceToGenerateNewPdf": "Yeni bir PDF oluştur", + "PdfGeneratedSuccessfully": "PDF başarıyla oluşturuldu", + "GenerateAndDownloadPdf": "PDF oluştur ve indir", + "PdfFileDeletionWarningMessage": "{0} PDF dosyasını silmek istediğinizden emin misiniz?", + "ManagePdfFiles": "PDF dosyalarını yönet", + "Permission:ManagePdfFiles": "PDF dosyalarını yönet" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/vi.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/vi.json index 9b47a049a9..176b427e59 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/vi.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/vi.json @@ -57,6 +57,15 @@ "LastCachedTime": "Thời gian lưu vào bộ nhớ đệm", "Project": "Dự án", "AdvancedFilters": "Bộ lọc nâng cao", - "RemoveCacheAndReIndexConfirmation": "Tài liệu "{0}" sẽ bị xóa khỏi bộ đệm và được lập chỉ mục lại. Bạn có xác nhận không?" + "RemoveCacheAndReIndexConfirmation": "Tài liệu "{0}" sẽ bị xóa khỏi bộ đệm và được lập chỉ mục lại. Bạn có xác nhận không?", + "GeneratePdf": "Tạo PDF", + "Generating": "Đang tạo...", + "Language": "Ngôn ngữ", + "ForceToGenerateNewPdf": "Tạo PDF mới", + "PdfGeneratedSuccessfully": "PDF đã được tạo thành công", + "GenerateAndDownloadPdf": "Tạo và tải xuống PDF", + "PdfFileDeletionWarningMessage": "Bạn có chắc chắn muốn xóa tệp PDF \"{0}\" không?", + "ManagePdfFiles": "Quản lý tệp PDF", + "Permission:ManagePdfFiles": "Quản lý tệp PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/zh-Hans.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/zh-Hans.json index e5bb9f15b6..137e42e4ae 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/zh-Hans.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/zh-Hans.json @@ -57,6 +57,15 @@ "LastCachedTime": "缓存项", "Project": "项目", "AdvancedFilters": "高级过滤器", - "RemoveCacheAndReIndexConfirmation": "文档“{0}”将从缓存中删除并重新编制索引。 你确认吗?" + "RemoveCacheAndReIndexConfirmation": "文档“{0}”将从缓存中删除并重新编制索引。 你确认吗?", + "GeneratePdf": "生成PDF", + "Generating": "生成中...", + "Language": "语言", + "ForceToGenerateNewPdf": "强制生成新PDF", + "PdfGeneratedSuccessfully": "PDF生成成功", + "GenerateAndDownloadPdf": "生成并下载PDF", + "PdfFileDeletionWarningMessage": "你确定要删除PDF文件“{0}”吗?", + "ManagePdfFiles": "管理PDF文件", + "Permission:ManagePdfFiles": "管理PDF文件" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/zh-Hant.json b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/zh-Hant.json index c246a74646..bfa6e4ea97 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/zh-Hant.json +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Localization/Resources/Docs/ApplicationContracts/zh-Hant.json @@ -55,8 +55,17 @@ "LanguageCode": "語言代碼", "FileName": "文檔名稱", "LastCachedTime": "緩存時間", - "Project": "项目", + "Project": "專案", "AdvancedFilters": "進階過濾器", - "RemoveCacheAndReIndexConfirmation": "文檔“{0}”將從緩存中刪除並重新編制索引。 你確認嗎?" + "RemoveCacheAndReIndexConfirmation": "文檔“{0}”將從緩存中刪除並重新編制索引。 你確認嗎?", + "GeneratePdf": "生成PDF", + "Generating": "生成中...", + "Language": "語言", + "ForceToGenerateNewPdf": "强制生成新PDF", + "PdfGeneratedSuccessfully": "PDF生成成功", + "GenerateAndDownloadPdf": "生成并下载PDF", + "PdfFileDeletionWarningMessage": "你確定要刪除PDF文件“{0}”嗎?", + "ManagePdfFiles": "管理PDF文件", + "Permission:ManagePdfFiles": "管理PDF文件" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/DeletePdfFileInput.cs b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/DeletePdfFileInput.cs new file mode 100644 index 0000000000..6e8e30e57c --- /dev/null +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/DeletePdfFileInput.cs @@ -0,0 +1,12 @@ +using System; + +namespace Volo.Docs.Admin.Projects; + +public class DeletePdfFileInput +{ + public Guid ProjectId { get; set; } + + public string Version { get; set; } + + public string LanguageCode { get; set; } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/GetPdfFilesInput.cs b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/GetPdfFilesInput.cs new file mode 100644 index 0000000000..f8a371dd57 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/GetPdfFilesInput.cs @@ -0,0 +1,9 @@ +using System; +using Volo.Abp.Application.Dtos; + +namespace Volo.Docs.Admin.Projects; + +public class GetPdfFilesInput : PagedAndSortedResultRequestDto +{ + public Guid ProjectId { get; set; } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/IProjectAdminAppService.cs b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/IProjectAdminAppService.cs index 6f3d503f44..41b309f308 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/IProjectAdminAppService.cs +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/IProjectAdminAppService.cs @@ -22,5 +22,9 @@ namespace Volo.Docs.Admin.Projects Task ReindexAllAsync(); Task> GetListWithoutDetailsAsync(); + + Task> GetPdfFilesAsync(GetPdfFilesInput input); + + Task DeletePdfFileAsync(DeletePdfFileInput input); } } diff --git a/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/ProjectPdfFileDto.cs b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/ProjectPdfFileDto.cs new file mode 100644 index 0000000000..4f2d012475 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Admin.Application.Contracts/Volo/Docs/Admin/Projects/ProjectPdfFileDto.cs @@ -0,0 +1,14 @@ +using System; + +namespace Volo.Docs.Admin.Projects; + +[Serializable] +public class ProjectPdfFileDto +{ + public virtual Guid ProjectId { get; set; } + public virtual string FileName { get; set; } + public virtual string Version { get; set; } + public virtual string LanguageCode { get; set; } + public virtual DateTime CreationTime { get; set; } + public virtual DateTime? LastModificationTime { get; set; } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application/Volo.Docs.Admin.Application.csproj b/modules/docs/src/Volo.Docs.Admin.Application/Volo.Docs.Admin.Application.csproj index 3d947ead5e..7279eeee67 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application/Volo.Docs.Admin.Application.csproj +++ b/modules/docs/src/Volo.Docs.Admin.Application/Volo.Docs.Admin.Application.csproj @@ -12,6 +12,7 @@ + diff --git a/modules/docs/src/Volo.Docs.Admin.Application/Volo/Docs/Admin/DocsAdminApplicationAutoMapperProfile.cs b/modules/docs/src/Volo.Docs.Admin.Application/Volo/Docs/Admin/DocsAdminApplicationAutoMapperProfile.cs index 01a7250ce5..366c0ab27b 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application/Volo/Docs/Admin/DocsAdminApplicationAutoMapperProfile.cs +++ b/modules/docs/src/Volo.Docs.Admin.Application/Volo/Docs/Admin/DocsAdminApplicationAutoMapperProfile.cs @@ -16,6 +16,7 @@ namespace Volo.Docs.Admin CreateMap(); CreateMap(); CreateMap(); + CreateMap(); } } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Application/Volo/Docs/Admin/DocsAdminApplicationModule.cs b/modules/docs/src/Volo.Docs.Admin.Application/Volo/Docs/Admin/DocsAdminApplicationModule.cs index 0b78c53973..7e6983d65e 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application/Volo/Docs/Admin/DocsAdminApplicationModule.cs +++ b/modules/docs/src/Volo.Docs.Admin.Application/Volo/Docs/Admin/DocsAdminApplicationModule.cs @@ -3,12 +3,14 @@ using Volo.Abp.Application; using Volo.Abp.AutoMapper; using Volo.Abp.Caching; using Volo.Abp.Modularity; +using Volo.Docs.Common; namespace Volo.Docs.Admin { [DependsOn( typeof(DocsDomainModule), typeof(DocsAdminApplicationContractsModule), + typeof(DocsCommonApplicationModule), typeof(AbpCachingModule), typeof(AbpAutoMapperModule), typeof(AbpDddApplicationModule) diff --git a/modules/docs/src/Volo.Docs.Admin.Application/Volo/Docs/Admin/Projects/ProjectAdminAppService.cs b/modules/docs/src/Volo.Docs.Admin.Application/Volo/Docs/Admin/Projects/ProjectAdminAppService.cs index 3142b821d2..abbb26abe5 100644 --- a/modules/docs/src/Volo.Docs.Admin.Application/Volo/Docs/Admin/Projects/ProjectAdminAppService.cs +++ b/modules/docs/src/Volo.Docs.Admin.Application/Volo/Docs/Admin/Projects/ProjectAdminAppService.cs @@ -3,6 +3,7 @@ using System.Collections.Generic; using System.Linq; using System.Threading.Tasks; using Microsoft.AspNetCore.Authorization; +using Microsoft.Extensions.Options; using Volo.Abp.Application.Dtos; using Volo.Abp.Application.Services; using Volo.Abp.Data; @@ -11,6 +12,7 @@ using Volo.Docs.Documents; using Volo.Docs.Documents.FullSearch.Elastic; using Volo.Docs.Localization; using Volo.Docs.Projects; +using Volo.Docs.Projects.Pdf; namespace Volo.Docs.Admin.Projects { @@ -21,12 +23,14 @@ namespace Volo.Docs.Admin.Projects private readonly IDocumentRepository _documentRepository; private readonly IDocumentFullSearch _elasticSearchService; private readonly IGuidGenerator _guidGenerator; + private readonly IProjectPdfFileStore _projectPdfFileStore; public ProjectAdminAppService( IProjectRepository projectRepository, IDocumentRepository documentRepository, IDocumentFullSearch elasticSearchService, - IGuidGenerator guidGenerator) + IGuidGenerator guidGenerator, + IProjectPdfFileStore projectPdfFileStore) { ObjectMapperContext = typeof(DocsAdminApplicationModule); LocalizationResource = typeof(DocsResource); @@ -35,6 +39,7 @@ namespace Volo.Docs.Admin.Projects _documentRepository = documentRepository; _elasticSearchService = elasticSearchService; _guidGenerator = guidGenerator; + _projectPdfFileStore = projectPdfFileStore; } public virtual async Task> GetListAsync(PagedAndSortedResultRequestDto input) @@ -176,5 +181,25 @@ namespace Volo.Docs.Admin.Projects var projects = await _projectRepository.GetListWithoutDetailsAsync(); return ObjectMapper.Map, List>(projects); } + + [Authorize(DocsAdminPermissions.Projects.ManagePdfFiles)] + public virtual async Task> GetPdfFilesAsync(GetPdfFilesInput input) + { + var project = await _projectRepository.GetAsync(input.ProjectId, includeDetails: true); + + var pdfFiles = project.PdfFiles.Skip(input.SkipCount).Take(input.MaxResultCount).ToList(); + + return new PagedResultDto( + project.PdfFiles.Count, + ObjectMapper.Map, List>(pdfFiles) + ); + } + + [Authorize(DocsAdminPermissions.Projects.ManagePdfFiles)] + public virtual async Task DeletePdfFileAsync(DeletePdfFileInput input) + { + var project = await _projectRepository.GetAsync(input.ProjectId, includeDetails: true); + await _projectPdfFileStore.DeleteAsync(project, input.Version, input.LanguageCode); + } } } diff --git a/modules/docs/src/Volo.Docs.Admin.HttpApi.Client/ClientProxies/Volo/Docs/Admin/ProjectsAdminClientProxy.Generated.cs b/modules/docs/src/Volo.Docs.Admin.HttpApi.Client/ClientProxies/Volo/Docs/Admin/ProjectsAdminClientProxy.Generated.cs index 54f1ec22d5..9437ee487d 100644 --- a/modules/docs/src/Volo.Docs.Admin.HttpApi.Client/ClientProxies/Volo/Docs/Admin/ProjectsAdminClientProxy.Generated.cs +++ b/modules/docs/src/Volo.Docs.Admin.HttpApi.Client/ClientProxies/Volo/Docs/Admin/ProjectsAdminClientProxy.Generated.cs @@ -68,6 +68,22 @@ public partial class ProjectsAdminClientProxy : ClientProxyBase>(nameof(GetListWithoutDetailsAsync)); } + public virtual async Task> GetPdfFilesAsync(GetPdfFilesInput input) + { + return await RequestAsync>(nameof(GetPdfFilesAsync), new ClientProxyRequestTypeValue + { + { typeof(GetPdfFilesInput), input } + }); + } + + public virtual async Task DeletePdfFileAsync(DeletePdfFileInput input) + { + await RequestAsync(nameof(DeletePdfFileAsync), new ClientProxyRequestTypeValue + { + { typeof(DeletePdfFileInput), input } + }); + } + public virtual async Task ReindexAsync(ReindexInput input) { await RequestAsync(nameof(ReindexAsync), new ClientProxyRequestTypeValue diff --git a/modules/docs/src/Volo.Docs.Admin.HttpApi.Client/ClientProxies/docs-admin-generate-proxy.json b/modules/docs/src/Volo.Docs.Admin.HttpApi.Client/ClientProxies/docs-admin-generate-proxy.json new file mode 100644 index 0000000000..636c7b6d25 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Admin.HttpApi.Client/ClientProxies/docs-admin-generate-proxy.json @@ -0,0 +1,1199 @@ +{ + "modules": { + "docs-admin": { + "rootPath": "docs-admin", + "remoteServiceName": "AbpDocsAdmin", + "controllers": { + "Volo.Docs.Admin.DocumentsAdminController": { + "controllerName": "DocumentsAdmin", + "controllerGroupName": "DocumentsAdmin", + "isRemoteService": true, + "isIntegrationService": false, + "apiVersion": null, + "type": "Volo.Docs.Admin.DocumentsAdminController", + "interfaces": [ + { + "type": "Volo.Docs.Admin.Documents.IDocumentAdminAppService", + "name": "IDocumentAdminAppService", + "methods": [ + { + "name": "ClearCacheAsync", + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Documents.ClearCacheInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Documents.ClearCacheInput", + "typeSimple": "Volo.Docs.Admin.Documents.ClearCacheInput", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + } + }, + { + "name": "PullAllAsync", + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Documents.PullAllDocumentInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Documents.PullAllDocumentInput", + "typeSimple": "Volo.Docs.Admin.Documents.PullAllDocumentInput", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + } + }, + { + "name": "PullAsync", + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Documents.PullDocumentInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Documents.PullDocumentInput", + "typeSimple": "Volo.Docs.Admin.Documents.PullDocumentInput", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + } + }, + { + "name": "GetAllAsync", + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Documents.GetAllInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Documents.GetAllInput", + "typeSimple": "Volo.Docs.Admin.Documents.GetAllInput", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "Volo.Abp.Application.Dtos.PagedResultDto", + "typeSimple": "Volo.Abp.Application.Dtos.PagedResultDto" + } + }, + { + "name": "RemoveFromCacheAsync", + "parametersOnMethod": [ + { + "name": "documentId", + "typeAsString": "System.Guid, System.Private.CoreLib", + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + } + }, + { + "name": "ReindexAsync", + "parametersOnMethod": [ + { + "name": "documentId", + "typeAsString": "System.Guid, System.Private.CoreLib", + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + } + }, + { + "name": "GetFilterItemsAsync", + "parametersOnMethod": [], + "returnValue": { + "type": "System.Collections.Generic.List", + "typeSimple": "[Volo.Docs.Admin.Documents.DocumentInfoDto]" + } + }, + { + "name": "GetProjectsAsync", + "parametersOnMethod": [], + "returnValue": { + "type": "System.Collections.Generic.List", + "typeSimple": "[Volo.Docs.Admin.Projects.ProjectWithoutDetailsDto]" + } + } + ] + } + ], + "actions": { + "ClearCacheAsyncByInput": { + "uniqueName": "ClearCacheAsyncByInput", + "name": "ClearCacheAsync", + "httpMethod": "POST", + "url": "api/docs/admin/documents/ClearCache", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Documents.ClearCacheInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Documents.ClearCacheInput", + "typeSimple": "Volo.Docs.Admin.Documents.ClearCacheInput", + "isOptional": false, + "defaultValue": null + } + ], + "parameters": [ + { + "nameOnMethod": "input", + "name": "input", + "jsonName": null, + "type": "Volo.Docs.Admin.Documents.ClearCacheInput", + "typeSimple": "Volo.Docs.Admin.Documents.ClearCacheInput", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "Body", + "descriptorName": "" + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Documents.IDocumentAdminAppService" + }, + "PullAllAsyncByInput": { + "uniqueName": "PullAllAsyncByInput", + "name": "PullAllAsync", + "httpMethod": "POST", + "url": "api/docs/admin/documents/PullAll", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Documents.PullAllDocumentInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Documents.PullAllDocumentInput", + "typeSimple": "Volo.Docs.Admin.Documents.PullAllDocumentInput", + "isOptional": false, + "defaultValue": null + } + ], + "parameters": [ + { + "nameOnMethod": "input", + "name": "input", + "jsonName": null, + "type": "Volo.Docs.Admin.Documents.PullAllDocumentInput", + "typeSimple": "Volo.Docs.Admin.Documents.PullAllDocumentInput", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "Body", + "descriptorName": "" + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Documents.IDocumentAdminAppService" + }, + "PullAsyncByInput": { + "uniqueName": "PullAsyncByInput", + "name": "PullAsync", + "httpMethod": "POST", + "url": "api/docs/admin/documents/Pull", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Documents.PullDocumentInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Documents.PullDocumentInput", + "typeSimple": "Volo.Docs.Admin.Documents.PullDocumentInput", + "isOptional": false, + "defaultValue": null + } + ], + "parameters": [ + { + "nameOnMethod": "input", + "name": "input", + "jsonName": null, + "type": "Volo.Docs.Admin.Documents.PullDocumentInput", + "typeSimple": "Volo.Docs.Admin.Documents.PullDocumentInput", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "Body", + "descriptorName": "" + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Documents.IDocumentAdminAppService" + }, + "GetAllAsyncByInput": { + "uniqueName": "GetAllAsyncByInput", + "name": "GetAllAsync", + "httpMethod": "GET", + "url": "api/docs/admin/documents/GetAll", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Documents.GetAllInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Documents.GetAllInput", + "typeSimple": "Volo.Docs.Admin.Documents.GetAllInput", + "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": "Name", + "jsonName": null, + "type": "System.String", + "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" + }, + { + "nameOnMethod": "input", + "name": "FileName", + "jsonName": null, + "type": "System.String", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "Format", + "jsonName": null, + "type": "System.String", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "CreationTimeMin", + "jsonName": null, + "type": "System.DateTime?", + "typeSimple": "string?", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "CreationTimeMax", + "jsonName": null, + "type": "System.DateTime?", + "typeSimple": "string?", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "LastUpdatedTimeMin", + "jsonName": null, + "type": "System.DateTime?", + "typeSimple": "string?", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "LastUpdatedTimeMax", + "jsonName": null, + "type": "System.DateTime?", + "typeSimple": "string?", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "LastSignificantUpdateTimeMin", + "jsonName": null, + "type": "System.DateTime?", + "typeSimple": "string?", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "LastSignificantUpdateTimeMax", + "jsonName": null, + "type": "System.DateTime?", + "typeSimple": "string?", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "LastCachedTimeMin", + "jsonName": null, + "type": "System.DateTime?", + "typeSimple": "string?", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "LastCachedTimeMax", + "jsonName": null, + "type": "System.DateTime?", + "typeSimple": "string?", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "Sorting", + "jsonName": null, + "type": "System.String", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "SkipCount", + "jsonName": null, + "type": "System.Int32", + "typeSimple": "number", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "MaxResultCount", + "jsonName": null, + "type": "System.Int32", + "typeSimple": "number", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + } + ], + "returnValue": { + "type": "Volo.Abp.Application.Dtos.PagedResultDto", + "typeSimple": "Volo.Abp.Application.Dtos.PagedResultDto" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Documents.IDocumentAdminAppService" + }, + "RemoveFromCacheAsyncByDocumentId": { + "uniqueName": "RemoveFromCacheAsyncByDocumentId", + "name": "RemoveFromCacheAsync", + "httpMethod": "PUT", + "url": "api/docs/admin/documents/RemoveDocumentFromCache", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "documentId", + "typeAsString": "System.Guid, System.Private.CoreLib", + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null + } + ], + "parameters": [ + { + "nameOnMethod": "documentId", + "name": "documentId", + "jsonName": null, + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "" + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Documents.IDocumentAdminAppService" + }, + "ReindexAsyncByDocumentId": { + "uniqueName": "ReindexAsyncByDocumentId", + "name": "ReindexAsync", + "httpMethod": "PUT", + "url": "api/docs/admin/documents/ReindexDocument", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "documentId", + "typeAsString": "System.Guid, System.Private.CoreLib", + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null + } + ], + "parameters": [ + { + "nameOnMethod": "documentId", + "name": "documentId", + "jsonName": null, + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "" + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Documents.IDocumentAdminAppService" + }, + "GetFilterItemsAsync": { + "uniqueName": "GetFilterItemsAsync", + "name": "GetFilterItemsAsync", + "httpMethod": "GET", + "url": "api/docs/admin/documents/GetFilterItems", + "supportedVersions": [], + "parametersOnMethod": [], + "parameters": [], + "returnValue": { + "type": "System.Collections.Generic.List", + "typeSimple": "[Volo.Docs.Admin.Documents.DocumentInfoDto]" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Documents.IDocumentAdminAppService" + }, + "GetProjectsAsync": { + "uniqueName": "GetProjectsAsync", + "name": "GetProjectsAsync", + "httpMethod": "GET", + "url": "api/docs/admin/documents/GetProjects", + "supportedVersions": [], + "parametersOnMethod": [], + "parameters": [], + "returnValue": { + "type": "System.Collections.Generic.List", + "typeSimple": "[Volo.Docs.Admin.Projects.ProjectWithoutDetailsDto]" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Documents.IDocumentAdminAppService" + } + } + }, + "Volo.Docs.Admin.ProjectsAdminController": { + "controllerName": "ProjectsAdmin", + "controllerGroupName": "ProjectsAdmin", + "isRemoteService": true, + "isIntegrationService": false, + "apiVersion": null, + "type": "Volo.Docs.Admin.ProjectsAdminController", + "interfaces": [ + { + "type": "Volo.Docs.Admin.Projects.IProjectAdminAppService", + "name": "IProjectAdminAppService", + "methods": [ + { + "name": "GetListAsync", + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Abp.Application.Dtos.PagedAndSortedResultRequestDto, Volo.Abp.Ddd.Application.Contracts", + "type": "Volo.Abp.Application.Dtos.PagedAndSortedResultRequestDto", + "typeSimple": "Volo.Abp.Application.Dtos.PagedAndSortedResultRequestDto", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "Volo.Abp.Application.Dtos.PagedResultDto", + "typeSimple": "Volo.Abp.Application.Dtos.PagedResultDto" + } + }, + { + "name": "GetAsync", + "parametersOnMethod": [ + { + "name": "id", + "typeAsString": "System.Guid, System.Private.CoreLib", + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "Volo.Docs.Admin.Projects.ProjectDto", + "typeSimple": "Volo.Docs.Admin.Projects.ProjectDto" + } + }, + { + "name": "CreateAsync", + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Projects.CreateProjectDto, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Projects.CreateProjectDto", + "typeSimple": "Volo.Docs.Admin.Projects.CreateProjectDto", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "Volo.Docs.Admin.Projects.ProjectDto", + "typeSimple": "Volo.Docs.Admin.Projects.ProjectDto" + } + }, + { + "name": "UpdateAsync", + "parametersOnMethod": [ + { + "name": "id", + "typeAsString": "System.Guid, System.Private.CoreLib", + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null + }, + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Projects.UpdateProjectDto, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Projects.UpdateProjectDto", + "typeSimple": "Volo.Docs.Admin.Projects.UpdateProjectDto", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "Volo.Docs.Admin.Projects.ProjectDto", + "typeSimple": "Volo.Docs.Admin.Projects.ProjectDto" + } + }, + { + "name": "DeleteAsync", + "parametersOnMethod": [ + { + "name": "id", + "typeAsString": "System.Guid, System.Private.CoreLib", + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + } + }, + { + "name": "ReindexAsync", + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Projects.ReindexInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Projects.ReindexInput", + "typeSimple": "Volo.Docs.Admin.Projects.ReindexInput", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + } + }, + { + "name": "ReindexAllAsync", + "parametersOnMethod": [], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + } + }, + { + "name": "GetListWithoutDetailsAsync", + "parametersOnMethod": [], + "returnValue": { + "type": "System.Collections.Generic.List", + "typeSimple": "[Volo.Docs.Admin.Projects.ProjectWithoutDetailsDto]" + } + }, + { + "name": "GetPdfFilesAsync", + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Projects.GetPdfFilesInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Projects.GetPdfFilesInput", + "typeSimple": "Volo.Docs.Admin.Projects.GetPdfFilesInput", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "Volo.Abp.Application.Dtos.PagedResultDto", + "typeSimple": "Volo.Abp.Application.Dtos.PagedResultDto" + } + }, + { + "name": "DeletePdfFileAsync", + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Projects.DeletePdfFileInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Projects.DeletePdfFileInput", + "typeSimple": "Volo.Docs.Admin.Projects.DeletePdfFileInput", + "isOptional": false, + "defaultValue": null + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + } + } + ] + } + ], + "actions": { + "GetListAsyncByInput": { + "uniqueName": "GetListAsyncByInput", + "name": "GetListAsync", + "httpMethod": "GET", + "url": "api/docs/admin/projects", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Abp.Application.Dtos.PagedAndSortedResultRequestDto, Volo.Abp.Ddd.Application.Contracts", + "type": "Volo.Abp.Application.Dtos.PagedAndSortedResultRequestDto", + "typeSimple": "Volo.Abp.Application.Dtos.PagedAndSortedResultRequestDto", + "isOptional": false, + "defaultValue": null + } + ], + "parameters": [ + { + "nameOnMethod": "input", + "name": "Sorting", + "jsonName": null, + "type": "System.String", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "SkipCount", + "jsonName": null, + "type": "System.Int32", + "typeSimple": "number", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "MaxResultCount", + "jsonName": null, + "type": "System.Int32", + "typeSimple": "number", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + } + ], + "returnValue": { + "type": "Volo.Abp.Application.Dtos.PagedResultDto", + "typeSimple": "Volo.Abp.Application.Dtos.PagedResultDto" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Projects.IProjectAdminAppService" + }, + "GetAsyncById": { + "uniqueName": "GetAsyncById", + "name": "GetAsync", + "httpMethod": "GET", + "url": "api/docs/admin/projects/{id}", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "id", + "typeAsString": "System.Guid, System.Private.CoreLib", + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null + } + ], + "parameters": [ + { + "nameOnMethod": "id", + "name": "id", + "jsonName": null, + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null, + "constraintTypes": [], + "bindingSourceId": "Path", + "descriptorName": "" + } + ], + "returnValue": { + "type": "Volo.Docs.Admin.Projects.ProjectDto", + "typeSimple": "Volo.Docs.Admin.Projects.ProjectDto" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Projects.IProjectAdminAppService" + }, + "CreateAsyncByInput": { + "uniqueName": "CreateAsyncByInput", + "name": "CreateAsync", + "httpMethod": "POST", + "url": "api/docs/admin/projects", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Projects.CreateProjectDto, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Projects.CreateProjectDto", + "typeSimple": "Volo.Docs.Admin.Projects.CreateProjectDto", + "isOptional": false, + "defaultValue": null + } + ], + "parameters": [ + { + "nameOnMethod": "input", + "name": "input", + "jsonName": null, + "type": "Volo.Docs.Admin.Projects.CreateProjectDto", + "typeSimple": "Volo.Docs.Admin.Projects.CreateProjectDto", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "Body", + "descriptorName": "" + } + ], + "returnValue": { + "type": "Volo.Docs.Admin.Projects.ProjectDto", + "typeSimple": "Volo.Docs.Admin.Projects.ProjectDto" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Projects.IProjectAdminAppService" + }, + "UpdateAsyncByIdAndInput": { + "uniqueName": "UpdateAsyncByIdAndInput", + "name": "UpdateAsync", + "httpMethod": "PUT", + "url": "api/docs/admin/projects/{id}", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "id", + "typeAsString": "System.Guid, System.Private.CoreLib", + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null + }, + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Projects.UpdateProjectDto, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Projects.UpdateProjectDto", + "typeSimple": "Volo.Docs.Admin.Projects.UpdateProjectDto", + "isOptional": false, + "defaultValue": null + } + ], + "parameters": [ + { + "nameOnMethod": "id", + "name": "id", + "jsonName": null, + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null, + "constraintTypes": [], + "bindingSourceId": "Path", + "descriptorName": "" + }, + { + "nameOnMethod": "input", + "name": "input", + "jsonName": null, + "type": "Volo.Docs.Admin.Projects.UpdateProjectDto", + "typeSimple": "Volo.Docs.Admin.Projects.UpdateProjectDto", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "Body", + "descriptorName": "" + } + ], + "returnValue": { + "type": "Volo.Docs.Admin.Projects.ProjectDto", + "typeSimple": "Volo.Docs.Admin.Projects.ProjectDto" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Projects.IProjectAdminAppService" + }, + "DeleteAsyncById": { + "uniqueName": "DeleteAsyncById", + "name": "DeleteAsync", + "httpMethod": "DELETE", + "url": "api/docs/admin/projects", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "id", + "typeAsString": "System.Guid, System.Private.CoreLib", + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null + } + ], + "parameters": [ + { + "nameOnMethod": "id", + "name": "id", + "jsonName": null, + "type": "System.Guid", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "" + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Projects.IProjectAdminAppService" + }, + "ReindexAllAsync": { + "uniqueName": "ReindexAllAsync", + "name": "ReindexAllAsync", + "httpMethod": "POST", + "url": "api/docs/admin/projects/ReindexAll", + "supportedVersions": [], + "parametersOnMethod": [], + "parameters": [], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Projects.IProjectAdminAppService" + }, + "GetListWithoutDetailsAsync": { + "uniqueName": "GetListWithoutDetailsAsync", + "name": "GetListWithoutDetailsAsync", + "httpMethod": "GET", + "url": "api/docs/admin/projects/GetListProjectWithoutDetailsAsync", + "supportedVersions": [], + "parametersOnMethod": [], + "parameters": [], + "returnValue": { + "type": "System.Collections.Generic.List", + "typeSimple": "[Volo.Docs.Admin.Projects.ProjectWithoutDetailsDto]" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Projects.IProjectAdminAppService" + }, + "GetPdfFilesAsyncByInput": { + "uniqueName": "GetPdfFilesAsyncByInput", + "name": "GetPdfFilesAsync", + "httpMethod": "GET", + "url": "api/docs/admin/projects/PdfFiles", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Projects.GetPdfFilesInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Projects.GetPdfFilesInput", + "typeSimple": "Volo.Docs.Admin.Projects.GetPdfFilesInput", + "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": "Sorting", + "jsonName": null, + "type": "System.String", + "typeSimple": "string", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "SkipCount", + "jsonName": null, + "type": "System.Int32", + "typeSimple": "number", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, + { + "nameOnMethod": "input", + "name": "MaxResultCount", + "jsonName": null, + "type": "System.Int32", + "typeSimple": "number", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + } + ], + "returnValue": { + "type": "Volo.Abp.Application.Dtos.PagedResultDto", + "typeSimple": "Volo.Abp.Application.Dtos.PagedResultDto" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Projects.IProjectAdminAppService" + }, + "DeletePdfFileAsyncByInput": { + "uniqueName": "DeletePdfFileAsyncByInput", + "name": "DeletePdfFileAsync", + "httpMethod": "DELETE", + "url": "api/docs/admin/projects/DeletePdfFile", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Projects.DeletePdfFileInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Projects.DeletePdfFileInput", + "typeSimple": "Volo.Docs.Admin.Projects.DeletePdfFileInput", + "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": "System.Void", + "typeSimple": "System.Void" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Projects.IProjectAdminAppService" + }, + "ReindexAsyncByInput": { + "uniqueName": "ReindexAsyncByInput", + "name": "ReindexAsync", + "httpMethod": "POST", + "url": "api/docs/admin/projects/Reindex", + "supportedVersions": [], + "parametersOnMethod": [ + { + "name": "input", + "typeAsString": "Volo.Docs.Admin.Projects.ReindexInput, Volo.Docs.Admin.Application.Contracts", + "type": "Volo.Docs.Admin.Projects.ReindexInput", + "typeSimple": "Volo.Docs.Admin.Projects.ReindexInput", + "isOptional": false, + "defaultValue": null + } + ], + "parameters": [ + { + "nameOnMethod": "input", + "name": "input", + "jsonName": null, + "type": "Volo.Docs.Admin.Projects.ReindexInput", + "typeSimple": "Volo.Docs.Admin.Projects.ReindexInput", + "isOptional": false, + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "Body", + "descriptorName": "" + } + ], + "returnValue": { + "type": "System.Void", + "typeSimple": "System.Void" + }, + "allowAnonymous": null, + "implementFrom": "Volo.Docs.Admin.Projects.IProjectAdminAppService" + } + } + } + } + } + }, + "types": {} +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.HttpApi/Volo.Docs.Admin.HttpApi.csproj b/modules/docs/src/Volo.Docs.Admin.HttpApi/Volo.Docs.Admin.HttpApi.csproj index 6d718f03bb..25a0be0294 100644 --- a/modules/docs/src/Volo.Docs.Admin.HttpApi/Volo.Docs.Admin.HttpApi.csproj +++ b/modules/docs/src/Volo.Docs.Admin.HttpApi/Volo.Docs.Admin.HttpApi.csproj @@ -12,6 +12,7 @@ + diff --git a/modules/docs/src/Volo.Docs.Admin.HttpApi/Volo/Docs/Admin/DocsAdminHttpApiModule.cs b/modules/docs/src/Volo.Docs.Admin.HttpApi/Volo/Docs/Admin/DocsAdminHttpApiModule.cs index ed62f35e6f..ba7f1f7fbb 100644 --- a/modules/docs/src/Volo.Docs.Admin.HttpApi/Volo/Docs/Admin/DocsAdminHttpApiModule.cs +++ b/modules/docs/src/Volo.Docs.Admin.HttpApi/Volo/Docs/Admin/DocsAdminHttpApiModule.cs @@ -4,12 +4,14 @@ using Volo.Abp.Localization; using Volo.Abp.Modularity; using Volo.Docs.Localization; using Microsoft.Extensions.DependencyInjection; +using Volo.Docs.Common; namespace Volo.Docs.Admin { [DependsOn( typeof(DocsAdminApplicationContractsModule), - typeof(AbpAspNetCoreMvcModule) + typeof(AbpAspNetCoreMvcModule), + typeof(DocsCommonHttpApiModule) )] public class DocsAdminHttpApiModule : AbpModule { diff --git a/modules/docs/src/Volo.Docs.Admin.HttpApi/Volo/Docs/Admin/ProjectsAdminController.cs b/modules/docs/src/Volo.Docs.Admin.HttpApi/Volo/Docs/Admin/ProjectsAdminController.cs index 5b1cffeae1..e020486887 100644 --- a/modules/docs/src/Volo.Docs.Admin.HttpApi/Volo/Docs/Admin/ProjectsAdminController.cs +++ b/modules/docs/src/Volo.Docs.Admin.HttpApi/Volo/Docs/Admin/ProjectsAdminController.cs @@ -70,6 +70,20 @@ namespace Volo.Docs.Admin return _projectAppService.GetListWithoutDetailsAsync(); } + [HttpGet] + [Route("PdfFiles")] + public Task> GetPdfFilesAsync(GetPdfFilesInput input) + { + return _projectAppService.GetPdfFilesAsync(input); + } + + [HttpDelete] + [Route("DeletePdfFile")] + public Task DeletePdfFileAsync(DeletePdfFileInput input) + { + return _projectAppService.DeletePdfFileAsync(input); + } + [HttpPost] [Route("Reindex")] public Task ReindexAsync(ReindexInput input) diff --git a/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/GeneratePdf.cshtml b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/GeneratePdf.cshtml new file mode 100644 index 0000000000..b8ad9742d8 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/GeneratePdf.cshtml @@ -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 L +@{ + Layout = null; +} + + + + + + +
+ + +
+
+ + +
+
+ +
+
+ + + + + +
\ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/GeneratePdf.cshtml.cs b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/GeneratePdf.cshtml.cs new file mode 100644 index 0000000000..ffd189546c --- /dev/null +++ b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/GeneratePdf.cshtml.cs @@ -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 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 Versions { get; set; } + public List Languages { get; set; } + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/Index.cshtml b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/Index.cshtml index 07582a45dd..1bdbf7467e 100644 --- a/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/Index.cshtml +++ b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/Index.cshtml @@ -20,10 +20,13 @@ @section scripts { + + + } diff --git a/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/ManagePdfFiles.cshtml b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/ManagePdfFiles.cshtml new file mode 100644 index 0000000000..e4d9ecda72 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/ManagePdfFiles.cshtml @@ -0,0 +1,41 @@ +@page +@using Microsoft.AspNetCore.Mvc.Localization +@using Volo.Abp.AspNetCore.Mvc.UI.Bootstrap.TagHelpers.Modal +@using Volo.Docs.Localization +@model Volo.Docs.Admin.Pages.Docs.Admin.Projects.ManagePdfFiles +@inject IHtmlLocalizer L + +@{ + Layout = null; +} + + + + + + + + + + + + + + + + + @L["Actions"] + @L["FileName"] + @L["Version"] + @L["LanguageCode"] + @L["CreationTime"] + @L["LastUpdateTime"] + + + + + + + + + \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/ManagePdfFiles.cshtml.cs b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/ManagePdfFiles.cshtml.cs new file mode 100644 index 0000000000..bb5218419b --- /dev/null +++ b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/ManagePdfFiles.cshtml.cs @@ -0,0 +1,14 @@ +using System.Threading.Tasks; +using Microsoft.AspNetCore.Authorization; +using Microsoft.AspNetCore.Mvc; + +namespace Volo.Docs.Admin.Pages.Docs.Admin.Projects; + +[Authorize(DocsAdminPermissions.Projects.Default)] +public class ManagePdfFiles : DocsAdminPageModel +{ + public virtual Task OnGet() + { + return Task.FromResult(Page()); + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/generatePdf.js b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/generatePdf.js new file mode 100644 index 0000000000..7b7f4b1bbf --- /dev/null +++ b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/generatePdf.js @@ -0,0 +1,81 @@ +var abp = abp || {}; +$(function () { + abp.modals.projectGeneratePdf = function () { + + var l = abp.localization.getResource('Docs'); + 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($(``)); + }); + }); + }) + + $("#GenerateBtn").click(function () { + var $btn = $(this); + $btn.buttonBusy(true); + $("#GenerateAndDownloadPdfBtn").buttonBusy(true); + var input = { + projectId: $("#ProjectId").val(), + version: $("#Version").val(), + languageCode: $("#Language").val(), + } + + function generatePdf(input) { + pdfGeneratorAppService.generatePdf(input, { + abpHandleError : false, + error: function (jqXHR) { + if (jqXHR.status === 200) { + abp.message.success(l('PdfFileDeletedSuccessfully')); + $btn.buttonBusy(false); + $("#GenerateAndDownloadPdfBtn").buttonBusy(false); + } else { + abp.ajax.handleErrorStatusCode(jqXHR.status); + } + } + }); + } + if(shouldForceToGenerate(input)){ + projectAdminAppService.deletePdfFile(input).done(() =>{ + generatePdf(input); + }); + }else{ + generatePdf(input); + } + }) + + $("#GenerateAndDownloadPdfBtn").click(function () { + var input = { + projectId: $("#ProjectId").val(), + version: $("#Version").val(), + languageCode: $("#Language").val(), + } + if(shouldForceToGenerate(input)){ + projectAdminAppService.deletePdfFile(input).done(() =>{ + 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'); + }); + }else{ + 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 shouldForceToGenerate(input) { + return $("#ForceToGenerate").is(":checked"); + } + + return { + initModal: initModal, + }; + }; +}); diff --git a/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/index.js b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/index.js index cf11d50603..12ad8f2d95 100644 --- a/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/index.js +++ b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/index.js @@ -16,6 +16,11 @@ $(function () { modalClass: 'projectPull', }); + var _managePdfFilesModal = new abp.ModalManager({ + viewUrl: abp.appPath + 'Docs/Admin/Projects/ManagePdfFiles', + modalClass: 'projectManagePdfFiles', + }); + var _dataTable = $('#ProjectsTable').DataTable( abp.libs.datatables.normalizeConfiguration({ processing: true, @@ -117,6 +122,17 @@ $(function () { }); }, }, + { + text: l('ManagePdfFiles'), + visible: abp.auth.isGranted( + 'Docs.Admin.Projects.ManagePdfFiles' + ), + action: function (data) { + _managePdfFilesModal.open({ + projectId: data.record.id, + }); + } + } ], }, }, diff --git a/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/managePdfFiles.js b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/managePdfFiles.js new file mode 100644 index 0000000000..8481867f46 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Admin.Web/Pages/Docs/Admin/Projects/managePdfFiles.js @@ -0,0 +1,94 @@ +var abp = abp || {}; +$(function () { + abp.modals.projectManagePdfFiles = function () { + + var l = abp.localization.getResource('Docs'); + var projectAdminAppService = volo.docs.admin.projectsAdmin; + + var _generatePdfModal = new abp.ModalManager({ + viewUrl: abp.appPath + 'Docs/Admin/Projects/GeneratePdf', + modalClass: 'projectGeneratePdf', + }); + + var initModal = function (publicApi, args) { + var _dataTable = $('#ProjectPdfFilesTable').DataTable( + abp.libs.datatables.normalizeConfiguration({ + processing: true, + serverSide: true, + scrollX: true, + paging: true, + searching: false, + autoWidth: false, + scrollCollapse: true, + order: [[2, 'desc']], + ajax: abp.libs.datatables.createAjax( + volo.docs.admin.projectsAdmin.getPdfFiles, + { + projectId : args.projectId + } + ), + columnDefs: [ + { + rowAction: { + items: [ + { + text: l('Delete'), + confirmMessage: function (data) { + return l('PdfFileDeletionWarningMessage', data.record.fileName); + }, + action: function (data) { + projectAdminAppService.deletePdfFile({ + projectId: data.record.projectId, + version: data.record.version, + languageCode: data.record.languageCode + }).then(() => { + _dataTable.ajax.reloadEx(); + abp.notify.success(l('PdfGeneratedSuccessfully')); + }) + }, + } + ], + }, + }, + { + target: 1, + data: 'fileName', + }, + { + target: 2, + data: 'version', + }, + { + target: 3, + data: 'languageCode', + }, + { + target: 4, + data: `creationTime`, + dataFormat: "datetime" + }, + { + target: 5, + data: `lastModificationTime`, + dataFormat: "datetime" + } + ], + }) + ); + + $('#GeneratePdfBtn').click(function () { + _generatePdfModal.open({ + Id: args.projectId, + }); + }); + + _generatePdfModal.onClose(function () { + _dataTable.ajax.reloadEx(); + }); + }; + + return { + initModal: initModal, + }; + }; +}); diff --git a/modules/docs/src/Volo.Docs.Admin.Web/wwwroot/client-proxies/docs-admin-proxy.js b/modules/docs/src/Volo.Docs.Admin.Web/wwwroot/client-proxies/docs-admin-proxy.js index 3a1c6930cf..a1e2aafaca 100644 --- a/modules/docs/src/Volo.Docs.Admin.Web/wwwroot/client-proxies/docs-admin-proxy.js +++ b/modules/docs/src/Volo.Docs.Admin.Web/wwwroot/client-proxies/docs-admin-proxy.js @@ -136,6 +136,21 @@ }, ajaxParams)); }; + volo.docs.admin.projectsAdmin.getPdfFiles = function(input, ajaxParams) { + return abp.ajax($.extend(true, { + url: abp.appPath + 'api/docs/admin/projects/PdfFiles' + abp.utils.buildQueryString([{ name: 'projectId', value: input.projectId }, { name: 'sorting', value: input.sorting }, { name: 'skipCount', value: input.skipCount }, { name: 'maxResultCount', value: input.maxResultCount }]) + '', + type: 'GET' + }, ajaxParams)); + }; + + volo.docs.admin.projectsAdmin.deletePdfFile = function(input, ajaxParams) { + return abp.ajax($.extend(true, { + url: abp.appPath + 'api/docs/admin/projects/DeletePdfFile' + abp.utils.buildQueryString([{ name: 'projectId', value: input.projectId }, { name: 'version', value: input.version }, { name: 'languageCode', value: input.languageCode }]) + '', + type: 'DELETE', + dataType: null + }, ajaxParams)); + }; + volo.docs.admin.projectsAdmin.reindex = function(input, ajaxParams) { return abp.ajax($.extend(true, { url: abp.appPath + 'api/docs/admin/projects/Reindex', diff --git a/modules/docs/src/Volo.Docs.Admin.Web/wwwroot/client-proxies/docs-common-proxy.js b/modules/docs/src/Volo.Docs.Admin.Web/wwwroot/client-proxies/docs-common-proxy.js new file mode 100644 index 0000000000..014e357cba --- /dev/null +++ b/modules/docs/src/Volo.Docs.Admin.Web/wwwroot/client-proxies/docs-common-proxy.js @@ -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)); + }; + + })(); + +})(); + + diff --git a/modules/docs/src/Volo.Docs.Application.Contracts/Volo.Docs.Application.Contracts.csproj b/modules/docs/src/Volo.Docs.Application.Contracts/Volo.Docs.Application.Contracts.csproj index d6d7c37d07..d7bb3b17b1 100644 --- a/modules/docs/src/Volo.Docs.Application.Contracts/Volo.Docs.Application.Contracts.csproj +++ b/modules/docs/src/Volo.Docs.Application.Contracts/Volo.Docs.Application.Contracts.csproj @@ -11,6 +11,7 @@ + diff --git a/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/DocsApplicationContractsModule.cs b/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/DocsApplicationContractsModule.cs index 7a3b9e9ec2..ce00f1a75a 100644 --- a/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/DocsApplicationContractsModule.cs +++ b/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/DocsApplicationContractsModule.cs @@ -1,10 +1,12 @@ using Volo.Abp.Application; using Volo.Abp.Modularity; +using Volo.Docs.Common; namespace Volo.Docs { [DependsOn( typeof(DocsDomainSharedModule), + typeof(DocsCommonApplicationContractsModule), typeof(AbpDddApplicationContractsModule) )] public class DocsApplicationContractsModule : AbpModule diff --git a/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Documents/DocumentWithDetailsDto.cs b/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Documents/DocumentWithDetailsDto.cs index 0364a2e26f..5f559c83e5 100644 --- a/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Documents/DocumentWithDetailsDto.cs +++ b/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Documents/DocumentWithDetailsDto.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using Volo.Docs.Common.Projects; using Volo.Docs.Projects; namespace Volo.Docs.Documents diff --git a/modules/docs/src/Volo.Docs.Application/Volo.Docs.Application.csproj b/modules/docs/src/Volo.Docs.Application/Volo.Docs.Application.csproj index 0bbf42da7e..b7530d7fe8 100644 --- a/modules/docs/src/Volo.Docs.Application/Volo.Docs.Application.csproj +++ b/modules/docs/src/Volo.Docs.Application/Volo.Docs.Application.csproj @@ -12,6 +12,7 @@ + diff --git a/modules/docs/src/Volo.Docs.Application/Volo/Docs/DocsApplicationAutoMapperProfile.cs b/modules/docs/src/Volo.Docs.Application/Volo/Docs/DocsApplicationAutoMapperProfile.cs index fc2eec1759..f2cb5476f7 100644 --- a/modules/docs/src/Volo.Docs.Application/Volo/Docs/DocsApplicationAutoMapperProfile.cs +++ b/modules/docs/src/Volo.Docs.Application/Volo/Docs/DocsApplicationAutoMapperProfile.cs @@ -1,7 +1,8 @@ using AutoMapper; using Volo.Docs.Documents; -using Volo.Docs.Projects; using Volo.Abp.AutoMapper; +using Volo.Docs.Common.Projects; +using Volo.Docs.Projects; namespace Volo.Docs { diff --git a/modules/docs/src/Volo.Docs.Application/Volo/Docs/DocsApplicationModule.cs b/modules/docs/src/Volo.Docs.Application/Volo/Docs/DocsApplicationModule.cs index e6826d54e6..f6d60099ad 100644 --- a/modules/docs/src/Volo.Docs.Application/Volo/Docs/DocsApplicationModule.cs +++ b/modules/docs/src/Volo.Docs.Application/Volo/Docs/DocsApplicationModule.cs @@ -4,6 +4,7 @@ using Volo.Abp.Application; using Volo.Abp.AutoMapper; using Volo.Abp.Caching; using Volo.Abp.Modularity; +using Volo.Docs.Common; using Volo.Docs.Documents; namespace Volo.Docs @@ -13,6 +14,7 @@ namespace Volo.Docs typeof(DocsApplicationContractsModule), typeof(AbpCachingModule), typeof(AbpAutoMapperModule), + typeof(DocsCommonApplicationModule), typeof(AbpDddApplicationModule) )] public class DocsApplicationModule : AbpModule diff --git a/modules/docs/src/Volo.Docs.Application/Volo/Docs/Documents/DocumentAppService.cs b/modules/docs/src/Volo.Docs.Application/Volo/Docs/Documents/DocumentAppService.cs index c426afacbd..e5bbca3f5a 100644 --- a/modules/docs/src/Volo.Docs.Application/Volo/Docs/Documents/DocumentAppService.cs +++ b/modules/docs/src/Volo.Docs.Application/Volo/Docs/Documents/DocumentAppService.cs @@ -14,8 +14,10 @@ using Volo.Abp.Application.Dtos; using Volo.Abp.Caching; using Volo.Abp.Data; using Volo.Docs.Caching; +using Volo.Docs.Common.Projects; using Volo.Docs.Documents.FullSearch.Elastic; using Volo.Docs.Projects; +using Volo.Docs.Utils; using Volo.Extensions; namespace Volo.Docs.Documents @@ -281,7 +283,7 @@ namespace Volo.Docs.Documents private List GetDocumentLinks(NavigationNode node, List documentUrls, string prefix, string shortName, DocumentWithoutDetails document) { - if (!IsExternalLink(node.Path)) + if (!UrlHelper.IsExternalLink(node.Path)) { documentUrls.AddIfNotContains( NormalizePath(prefix, node.Path, shortName, document) @@ -319,17 +321,6 @@ namespace Volo.Docs.Documents : path; } - private static bool IsExternalLink(string path) - { - if (path.IsNullOrEmpty()) - { - return false; - } - - return path.StartsWith("http://", StringComparison.OrdinalIgnoreCase) || - path.StartsWith("https://", StringComparison.OrdinalIgnoreCase); - } - public virtual async Task GetParametersAsync(GetParametersDocumentInput input) { var project = await _projectRepository.GetAsync(input.ProjectId); diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo.Docs.Common.Application.Contracts.csproj b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo.Docs.Common.Application.Contracts.csproj new file mode 100644 index 0000000000..acde6b2a6c --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo.Docs.Common.Application.Contracts.csproj @@ -0,0 +1,33 @@ + + + + + + + netstandard2.0;netstandard2.1;net8.0;net9.0 + Volo.Docs.Common.Application.Contracts + Volo.Docs.Common.Application.Contracts + true + + + + + + + + + + + + + + + + + + + + + + + diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/DocsCommonApplicationContractsModule.cs b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/DocsCommonApplicationContractsModule.cs new file mode 100644 index 0000000000..8e11262d3d --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/DocsCommonApplicationContractsModule.cs @@ -0,0 +1,31 @@ +using Volo.Abp.Application; +using Volo.Abp.Authorization; +using Volo.Abp.Localization; +using Volo.Abp.Modularity; +using Volo.Abp.VirtualFileSystem; +using Volo.Docs.Localization; + +namespace Volo.Docs.Common; + +[DependsOn( + typeof(DocsDomainSharedModule), + typeof(AbpDddApplicationContractsModule), + typeof(AbpAuthorizationAbstractionsModule) +)] +public class DocsCommonApplicationContractsModule : AbpModule +{ + public override void ConfigureServices(ServiceConfigurationContext context) + { + Configure(options => + { + options.FileSets.AddEmbedded(); + }); + + Configure(options => + { + options.Resources + .Get() + .AddVirtualJson("Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts"); + }); + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/DocsCommonPermissionDefinitionProvider.cs b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/DocsCommonPermissionDefinitionProvider.cs new file mode 100644 index 0000000000..0bdfc7fa1d --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/DocsCommonPermissionDefinitionProvider.cs @@ -0,0 +1,21 @@ +using Volo.Abp.Authorization.Permissions; +using Volo.Abp.Localization; +using Volo.Docs.Localization; + +namespace Volo.Docs.Common +{ + public class DocsCommonPermissionDefinitionProvider : PermissionDefinitionProvider + { + public override void Define(IPermissionDefinitionContext context) + { + var group = context.AddGroup(DocsCommonPermissions.GroupName, L("Permission:DocumentManagement.Common")); + + group.AddPermission(DocsCommonPermissions.Projects.PdfGeneration, L("Permission:PdfGeneration")); + } + + private static LocalizableString L(string name) + { + return LocalizableString.Create(name); + } + } +} diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/DocsCommonPermissions.cs b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/DocsCommonPermissions.cs new file mode 100644 index 0000000000..f668f00813 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/DocsCommonPermissions.cs @@ -0,0 +1,19 @@ +using Volo.Abp.Reflection; + +namespace Volo.Docs.Common +{ + public class DocsCommonPermissions + { + public const string GroupName = "Docs.Common"; + + public static class Projects + { + public const string PdfGeneration = GroupName + ".PdfGeneration"; + } + + public static string[] GetAll() + { + return ReflectionHelper.GetPublicConstantsRecursively(typeof(DocsCommonPermissions)); + } + } +} diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/DocsCommonRemoteServiceConsts.cs b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/DocsCommonRemoteServiceConsts.cs new file mode 100644 index 0000000000..6faa6d18fd --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/DocsCommonRemoteServiceConsts.cs @@ -0,0 +1,9 @@ +namespace Volo.Docs.Common +{ + public static class DocsCommonRemoteServiceConsts + { + public const string RemoteServiceName = "AbpDocsCommon"; + + public const string ModuleName = "docs-common"; + } +} diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Documents/DocumentPdfGeneratorInput.cs b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Documents/DocumentPdfGeneratorInput.cs new file mode 100644 index 0000000000..989a0e9c40 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Documents/DocumentPdfGeneratorInput.cs @@ -0,0 +1,12 @@ +using System; + +namespace Volo.Docs.Common.Documents; + +public class DocumentPdfGeneratorInput +{ + public Guid ProjectId { get; set; } + + public string Version { get; set; } + + public string LanguageCode { get; set; } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Documents/IDocumentPdfGeneratorAppService.cs b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Documents/IDocumentPdfGeneratorAppService.cs new file mode 100644 index 0000000000..dc8d87e820 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Documents/IDocumentPdfGeneratorAppService.cs @@ -0,0 +1,10 @@ +using System.Threading.Tasks; +using Volo.Abp.Application.Services; +using Volo.Abp.Content; + +namespace Volo.Docs.Common.Documents; + +public interface IDocumentPdfGeneratorAppService : IApplicationService +{ + Task GeneratePdfAsync(DocumentPdfGeneratorInput input); +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/ar.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/ar.json new file mode 100644 index 0000000000..ff14b26dc6 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/ar.json @@ -0,0 +1,7 @@ +{ + "culture": "ar", + "texts": { + "Permission:DocumentManagement.Common": "إدارة المستندات العامة", + "Permission:PdfGeneration": "إنشاء ملفات PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/cs.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/cs.json new file mode 100644 index 0000000000..7999e95a27 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/cs.json @@ -0,0 +1,7 @@ +{ + "culture": "cs", + "texts": { + "Permission:DocumentManagement.Common": "Správa dokumentů", + "Permission:PdfGeneration": "Generování PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/de-DE.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/de-DE.json new file mode 100644 index 0000000000..0b2c842bb3 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/de-DE.json @@ -0,0 +1,7 @@ +{ + "culture": "de-DE", + "texts": { + "Permission:DocumentManagement.Common": "Dokumentenverwaltung", + "Permission:PdfGeneration": "PDF-Generierung" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/de.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/de.json new file mode 100644 index 0000000000..95d2923d1e --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/de.json @@ -0,0 +1,7 @@ +{ + "culture": "de", + "texts": { + "Permission:DocumentManagement.Common": "Dokumentenverwaltung", + "Permission:PdfGeneration": "PDF-Generierung" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/el.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/el.json new file mode 100644 index 0000000000..3200537f6d --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/el.json @@ -0,0 +1,7 @@ +{ + "culture": "el", + "texts": { + "Permission:DocumentManagement.Common": "Διαχείριση Εγγράφων", + "Permission:PdfGeneration": "Δημιουργία PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/en-GB.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/en-GB.json new file mode 100644 index 0000000000..8f01efadbf --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/en-GB.json @@ -0,0 +1,7 @@ +{ + "culture": "en-GB", + "texts": { + "Permission:DocumentManagement.Common": "Document Management Common", + "Permission:PdfGeneration": "PDF Generation" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/en.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/en.json new file mode 100644 index 0000000000..3901eb8d1c --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/en.json @@ -0,0 +1,7 @@ +{ + "culture": "en", + "texts": { + "Permission:DocumentManagement.Common": "Document Management Common", + "Permission:PdfGeneration": "PDF Generation" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/es.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/es.json new file mode 100644 index 0000000000..707bd71c72 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/es.json @@ -0,0 +1,7 @@ +{ + "culture": "es", + "texts": { + "Permission:DocumentManagement.Common": "Gestión de documentos comunes", + "Permission:PdfGeneration": "Generación de PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/fi.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/fi.json new file mode 100644 index 0000000000..7e3a84ff00 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/fi.json @@ -0,0 +1,7 @@ +{ + "culture": "fi", + "texts": { + "Permission:DocumentManagement.Common": "Tiedostonhallinta", + "Permission:PdfGeneration": "PDF-generointi" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/fr.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/fr.json new file mode 100644 index 0000000000..6eba3e78c1 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/fr.json @@ -0,0 +1,7 @@ +{ + "culture": "fr", + "texts": { + "Permission:DocumentManagement.Common": "Gestion des documents communs", + "Permission:PdfGeneration": "Génération de PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/hi.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/hi.json new file mode 100644 index 0000000000..5208d04868 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/hi.json @@ -0,0 +1,7 @@ +{ + "culture": "hi", + "texts": { + "Permission:DocumentManagement.Common": "सामान्य दस्तावेज़ प्रबंधन", + "Permission:PdfGeneration": "PDF उत्पन्न करना" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/hr.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/hr.json new file mode 100644 index 0000000000..8da0d89a98 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/hr.json @@ -0,0 +1,7 @@ +{ + "culture": "hr", + "texts": { + "Permission:DocumentManagement.Common": "Upravljanje zajedničkih dokumenata", + "Permission:PdfGeneration": "Generiranje PDF-a" + } +} diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/hu.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/hu.json new file mode 100644 index 0000000000..30a2bd39f8 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/hu.json @@ -0,0 +1,7 @@ +{ + "culture": "hu", + "texts": { + "Permission:DocumentManagement.Common": "Általános dokumentumkezelés", + "Permission:PdfGeneration": "PDF generálás" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/is.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/is.json new file mode 100644 index 0000000000..9e0f6b19c9 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/is.json @@ -0,0 +1,7 @@ +{ + "culture": "is", + "texts": { + "Permission:DocumentManagement.Common": "Almennir skjöl", + "Permission:PdfGeneration": "Breyta í PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/it.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/it.json new file mode 100644 index 0000000000..1616e2cecb --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/it.json @@ -0,0 +1,7 @@ +{ + "culture": "it", + "texts": { + "Permission:DocumentManagement.Common": "Gestione documenti comuni", + "Permission:PdfGeneration": "Generazione PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/nl.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/nl.json new file mode 100644 index 0000000000..64e170aaf8 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/nl.json @@ -0,0 +1,7 @@ +{ + "culture": "nl", + "texts": { + "Permission:DocumentManagement.Common": "Algemene documentbeheer", + "Permission:PdfGeneration": "PDF-generatie" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/pl-PL.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/pl-PL.json new file mode 100644 index 0000000000..89c83f4063 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/pl-PL.json @@ -0,0 +1,7 @@ +{ + "culture": "pl-PL", + "texts": { + "Permission:DocumentManagement.Common": "Zarządzanie dokumentami", + "Permission:PdfGeneration": "Generowanie PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/pt-BR.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/pt-BR.json new file mode 100644 index 0000000000..e9c83fc560 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/pt-BR.json @@ -0,0 +1,7 @@ +{ + "culture": "pt-BR", + "texts": { + "Permission:DocumentManagement.Common": "Gerenciamento de documentos comuns", + "Permission:PdfGeneration": "Geração de PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/ro-RO.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/ro-RO.json new file mode 100644 index 0000000000..b5cc16b376 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/ro-RO.json @@ -0,0 +1,7 @@ +{ + "culture": "ro-RO", + "texts": { + "Permission:DocumentManagement.Common": "Gestionarea documentelor comune", + "Permission:PdfGeneration": "Generarea PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/ru.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/ru.json new file mode 100644 index 0000000000..f110638da1 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/ru.json @@ -0,0 +1,7 @@ +{ + "culture": "ru", + "texts": { + "Permission:DocumentManagement.Common": "Общее управление документами", + "Permission:PdfGeneration": "Генерация PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/sk.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/sk.json new file mode 100644 index 0000000000..aca12e8304 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/sk.json @@ -0,0 +1,7 @@ +{ + "culture": "sk", + "texts": { + "Permission:DocumentManagement.Common": "Správa dokumentov", + "Permission:PdfGeneration": "Generovanie PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/sl.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/sl.json new file mode 100644 index 0000000000..1adc834a47 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/sl.json @@ -0,0 +1,7 @@ +{ + "culture": "sl", + "texts": { + "Permission:DocumentManagement.Common": "Skupna dokumentna upravljanja", + "Permission:PdfGeneration": "Generiranje PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/sv.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/sv.json new file mode 100644 index 0000000000..c0df8c8fa9 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/sv.json @@ -0,0 +1,7 @@ +{ + "culture": "sv", + "texts": { + "Permission:DocumentManagement.Common": "Dokumenthantering", + "Permission:PdfGeneration": "PDF-generering" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/tr.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/tr.json new file mode 100644 index 0000000000..19c39d619b --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/tr.json @@ -0,0 +1,7 @@ +{ + "culture": "tr", + "texts": { + "Permission:DocumentManagement.Common": "Genel Belge Yönetimi", + "Permission:PdfGeneration": "PDF Oluşturma" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/vi.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/vi.json new file mode 100644 index 0000000000..e0f7a86c7d --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/vi.json @@ -0,0 +1,7 @@ +{ + "culture": "vi", + "texts": { + "Permission:DocumentManagement.Common": "Quản lý tài liệu chung", + "Permission:PdfGeneration": "Tạo PDF" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/zh-Hans.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/zh-Hans.json new file mode 100644 index 0000000000..f92de5bc99 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/zh-Hans.json @@ -0,0 +1,7 @@ +{ + "culture": "zh-Hans", + "texts": { + "Permission:DocumentManagement.Common": "通用文档管理", + "Permission:PdfGeneration": "PDF生成" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/zh-Hant.json b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/zh-Hant.json new file mode 100644 index 0000000000..82b5257eed --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Localization/Resources/Docs/ApplicationContracts/zh-Hant.json @@ -0,0 +1,7 @@ +{ + "culture": "zh-Hant", + "texts": { + "Permission:DocumentManagement.Common": "通用文件管理", + "Permission:PdfGeneration": "PDF生成" + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Projects/IProjectAppService.cs b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Projects/IProjectAppService.cs similarity index 90% rename from modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Projects/IProjectAppService.cs rename to modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Projects/IProjectAppService.cs index b93fb09e77..b81637c25f 100644 --- a/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Projects/IProjectAppService.cs +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Projects/IProjectAppService.cs @@ -2,8 +2,9 @@ using System.Threading.Tasks; using Volo.Abp.Application.Dtos; using Volo.Abp.Application.Services; using Volo.Docs.Documents; +using Volo.Docs.Projects; -namespace Volo.Docs.Projects +namespace Volo.Docs.Common.Projects { public interface IProjectAppService : IApplicationService { diff --git a/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Projects/ProjectDto.cs b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Projects/ProjectDto.cs similarity index 95% rename from modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Projects/ProjectDto.cs rename to modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Projects/ProjectDto.cs index 2861e60307..5e0890cbe5 100644 --- a/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Projects/ProjectDto.cs +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Projects/ProjectDto.cs @@ -2,7 +2,7 @@ using System; using Volo.Abp.Application.Dtos; using Volo.Abp.Data; -namespace Volo.Docs.Projects +namespace Volo.Docs.Common.Projects { [Serializable] public class ProjectDto : EntityDto, IHasExtraProperties diff --git a/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Projects/VersionInfoDto.cs b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Projects/VersionInfoDto.cs similarity index 77% rename from modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Projects/VersionInfoDto.cs rename to modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Projects/VersionInfoDto.cs index 32ac7bb1c4..59db11e3fa 100644 --- a/modules/docs/src/Volo.Docs.Application.Contracts/Volo/Docs/Projects/VersionInfoDto.cs +++ b/modules/docs/src/Volo.Docs.Common.Application.Contracts/Volo/Docs/Common/Projects/VersionInfoDto.cs @@ -1,4 +1,4 @@ -namespace Volo.Docs.Projects +namespace Volo.Docs.Common.Projects { public class VersionInfoDto { diff --git a/modules/docs/src/Volo.Docs.Common.Application/Volo.Docs.Common.Application.csproj b/modules/docs/src/Volo.Docs.Common.Application/Volo.Docs.Common.Application.csproj new file mode 100644 index 0000000000..545995b902 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application/Volo.Docs.Common.Application.csproj @@ -0,0 +1,20 @@ + + + + + + + net9.0 + Volo.Docs.Common.Application + Volo.Docs.Common.Application + + + + + + + + + + + diff --git a/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/DocsCommonAppServiceBase.cs b/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/DocsCommonAppServiceBase.cs new file mode 100644 index 0000000000..280a0c7c82 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/DocsCommonAppServiceBase.cs @@ -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); + } + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/DocsCommonApplicationAutoMapperProfile.cs b/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/DocsCommonApplicationAutoMapperProfile.cs new file mode 100644 index 0000000000..8175654743 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/DocsCommonApplicationAutoMapperProfile.cs @@ -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(); + CreateMap(); + } + } +} diff --git a/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/DocsCommonApplicationModule.cs b/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/DocsCommonApplicationModule.cs new file mode 100644 index 0000000000..b7eb350930 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/DocsCommonApplicationModule.cs @@ -0,0 +1,25 @@ +using Microsoft.Extensions.DependencyInjection; +using Volo.Abp.Application; +using Volo.Abp.AutoMapper; +using Volo.Abp.Modularity; + +namespace Volo.Docs.Common; + +[DependsOn( + typeof(DocsDomainModule), + typeof(DocsCommonApplicationContractsModule), + typeof(AbpAutoMapperModule), + typeof(AbpDddApplicationModule) +)] +public class DocsCommonApplicationModule : AbpModule +{ + public override void ConfigureServices(ServiceConfigurationContext context) + { + context.Services.AddAutoMapperObjectMapper(); + + Configure(options => + { + options.AddProfile(validate: true); + }); + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/Documents/DocumentPdfGeneratorAppService.cs b/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/Documents/DocumentPdfGeneratorAppService.cs new file mode 100644 index 0000000000..7787185b50 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/Documents/DocumentPdfGeneratorAppService.cs @@ -0,0 +1,29 @@ +using System.Threading.Tasks; +using Microsoft.AspNetCore.Authorization; +using Volo.Abp.Application.Services; +using Volo.Abp.Content; +using Volo.Docs.Projects; +using Volo.Docs.Projects.Pdf; + +namespace Volo.Docs.Common.Documents; + +[Authorize(DocsCommonPermissions.Projects.PdfGeneration)] +public class DocumentPdfGeneratorAppService : ApplicationService, IDocumentPdfGeneratorAppService +{ + protected IProjectPdfGenerator ProjectPdfGenerator { get; } + protected IProjectRepository ProjectRepository { get; } + + public DocumentPdfGeneratorAppService( + IProjectPdfGenerator projectPdfGenerator, + IProjectRepository projectRepository) + { + ProjectPdfGenerator = projectPdfGenerator; + ProjectRepository = projectRepository; + } + + public virtual async Task GeneratePdfAsync(DocumentPdfGeneratorInput input) + { + var project = await ProjectRepository.GetAsync(input.ProjectId, includeDetails: true); + return await ProjectPdfGenerator.GenerateAsync(project, input.Version, input.LanguageCode); + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Application/Volo/Docs/Projects/ProjectAppService.cs b/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/Projects/ProjectAppService.cs similarity index 97% rename from modules/docs/src/Volo.Docs.Application/Volo/Docs/Projects/ProjectAppService.cs rename to modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/Projects/ProjectAppService.cs index 1cca1a102a..96634a300e 100644 --- a/modules/docs/src/Volo.Docs.Application/Volo/Docs/Projects/ProjectAppService.cs +++ b/modules/docs/src/Volo.Docs.Common.Application/Volo/Docs/Common/Projects/ProjectAppService.cs @@ -4,16 +4,15 @@ using System.Linq; using System.Threading.Tasks; using Microsoft.Extensions.Caching.Distributed; using Volo.Abp.Application.Dtos; -using Volo.Abp.Application.Services; using Volo.Abp.Caching; using Volo.Abp.Data; -using Volo.Abp.Guids; using Volo.Docs.Caching; using Volo.Docs.Documents; +using Volo.Docs.Projects; -namespace Volo.Docs.Projects +namespace Volo.Docs.Common.Projects { - public class ProjectAppService : DocsAppServiceBase, IProjectAppService + public class ProjectAppService : DocsCommonAppServiceBase, IProjectAppService { private readonly IProjectRepository _projectRepository; private readonly IDistributedCache> _versionCache; diff --git a/modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/Volo/Docs/Documents/DocsDocumentPdfGeneratorClientProxy.Generated.cs b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/Volo/Docs/Documents/DocsDocumentPdfGeneratorClientProxy.Generated.cs new file mode 100644 index 0000000000..39608380c5 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/Volo/Docs/Documents/DocsDocumentPdfGeneratorClientProxy.Generated.cs @@ -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 +{ + public virtual async Task GeneratePdfAsync(DocumentPdfGeneratorInput input) + { + return await RequestAsync(nameof(GeneratePdfAsync), new ClientProxyRequestTypeValue + { + { typeof(DocumentPdfGeneratorInput), input } + }); + } +} diff --git a/modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/Volo/Docs/Documents/DocsDocumentPdfGeneratorClientProxy.cs b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/Volo/Docs/Documents/DocsDocumentPdfGeneratorClientProxy.cs new file mode 100644 index 0000000000..e14c1c25be --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/Volo/Docs/Documents/DocsDocumentPdfGeneratorClientProxy.cs @@ -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 +{ +} diff --git a/modules/docs/src/Volo.Docs.HttpApi.Client/ClientProxies/Volo/Docs/Projects/DocsProjectClientProxy.Generated.cs b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/Volo/Docs/Projects/DocsProjectClientProxy.Generated.cs similarity index 98% rename from modules/docs/src/Volo.Docs.HttpApi.Client/ClientProxies/Volo/Docs/Projects/DocsProjectClientProxy.Generated.cs rename to modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/Volo/Docs/Projects/DocsProjectClientProxy.Generated.cs index 2caa2e3e93..19170e497e 100644 --- a/modules/docs/src/Volo.Docs.HttpApi.Client/ClientProxies/Volo/Docs/Projects/DocsProjectClientProxy.Generated.cs +++ b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/Volo/Docs/Projects/DocsProjectClientProxy.Generated.cs @@ -8,8 +8,8 @@ using Volo.Abp.DependencyInjection; using Volo.Abp.Http.Client; using Volo.Abp.Http.Client.ClientProxying; using Volo.Abp.Http.Modeling; +using Volo.Docs.Common.Projects; using Volo.Docs.Documents; -using Volo.Docs.Projects; // ReSharper disable once CheckNamespace namespace Volo.Docs.Projects; diff --git a/modules/docs/src/Volo.Docs.HttpApi.Client/ClientProxies/Volo/Docs/Projects/DocsProjectClientProxy.cs b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/Volo/Docs/Projects/DocsProjectClientProxy.cs similarity index 100% rename from modules/docs/src/Volo.Docs.HttpApi.Client/ClientProxies/Volo/Docs/Projects/DocsProjectClientProxy.cs rename to modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/Volo/Docs/Projects/DocsProjectClientProxy.cs diff --git a/modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/docs-common-generate-proxy.json b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/docs-common-generate-proxy.json new file mode 100644 index 0000000000..db7303a427 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/ClientProxies/docs-common-generate-proxy.json @@ -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", + "typeSimple": "Volo.Abp.Application.Dtos.ListResultDto" + } + }, + { + "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", + "typeSimple": "Volo.Abp.Application.Dtos.ListResultDto" + } + }, + { + "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", + "typeSimple": "Volo.Abp.Application.Dtos.ListResultDto" + }, + "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", + "typeSimple": "Volo.Abp.Application.Dtos.ListResultDto" + }, + "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": {} +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.HttpApi.Client/Volo.Docs.Common.HttpApi.Client.csproj b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/Volo.Docs.Common.HttpApi.Client.csproj new file mode 100644 index 0000000000..ff4c3301fc --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/Volo.Docs.Common.HttpApi.Client.csproj @@ -0,0 +1,19 @@ + + + + + + + netstandard2.0;netstandard2.1;net8.0;net9.0 + Volo.Docs.Common.HttpApi.Client + Volo.Docs.Common.HttpApi.Client + + + + + + + + + + diff --git a/modules/docs/src/Volo.Docs.Common.HttpApi.Client/Volo/Docs/DocsCommonHttpApiClientModule.cs b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/Volo/Docs/DocsCommonHttpApiClientModule.cs new file mode 100644 index 0000000000..a139d29ac2 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.HttpApi.Client/Volo/Docs/DocsCommonHttpApiClientModule.cs @@ -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(options => + { + options.FileSets.AddEmbedded(); + }); + } + } +} diff --git a/modules/docs/src/Volo.Docs.Common.HttpApi/Volo.Docs.Common.HttpApi.csproj b/modules/docs/src/Volo.Docs.Common.HttpApi/Volo.Docs.Common.HttpApi.csproj new file mode 100644 index 0000000000..001778b838 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.HttpApi/Volo.Docs.Common.HttpApi.csproj @@ -0,0 +1,18 @@ + + + + + + + net9.0 + Volo.Docs.Common.HttpApi + Volo.Docs.Common.HttpApi + + + + + + + + + diff --git a/modules/docs/src/Volo.Docs.Common.HttpApi/Volo/Docs/DocsCommonHttpApiModule.cs b/modules/docs/src/Volo.Docs.Common.HttpApi/Volo/Docs/DocsCommonHttpApiModule.cs new file mode 100644 index 0000000000..09ff45507b --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.HttpApi/Volo/Docs/DocsCommonHttpApiModule.cs @@ -0,0 +1,35 @@ +using Localization.Resources.AbpUi; +using Microsoft.Extensions.DependencyInjection; +using Volo.Abp.AspNetCore.Mvc; +using Volo.Abp.Localization; +using Volo.Abp.Modularity; +using Volo.Docs.Common; +using Volo.Docs.Localization; + +namespace Volo.Docs +{ + [DependsOn( + typeof(DocsCommonApplicationContractsModule), + typeof(AbpAspNetCoreMvcModule) + )] + public class DocsCommonHttpApiModule : AbpModule + { + public override void PreConfigureServices(ServiceConfigurationContext context) + { + PreConfigure(mvcBuilder => + { + mvcBuilder.AddApplicationPartIfNotExists(typeof(DocsCommonHttpApiModule).Assembly); + }); + } + + public override void ConfigureServices(ServiceConfigurationContext context) + { + Configure(options => + { + options.Resources + .Get() + .AddBaseTypes(typeof(AbpUiResource)); + }); + } + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Common.HttpApi/Volo/Docs/DocsControllerBase.cs b/modules/docs/src/Volo.Docs.Common.HttpApi/Volo/Docs/DocsControllerBase.cs new file mode 100644 index 0000000000..8d730acd4f --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.HttpApi/Volo/Docs/DocsControllerBase.cs @@ -0,0 +1,12 @@ +using Volo.Abp.AspNetCore.Mvc; +using Volo.Docs.Localization; + +namespace Volo.Docs; + +public abstract class DocsControllerBase : AbpControllerBase +{ + protected DocsControllerBase() + { + LocalizationResource = typeof(DocsResource); + } +} diff --git a/modules/docs/src/Volo.Docs.Common.HttpApi/Volo/Docs/Documents/DocsDocumentPdfGeneratorController.cs b/modules/docs/src/Volo.Docs.Common.HttpApi/Volo/Docs/Documents/DocsDocumentPdfGeneratorController.cs new file mode 100644 index 0000000000..31ae2a2f44 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Common.HttpApi/Volo/Docs/Documents/DocsDocumentPdfGeneratorController.cs @@ -0,0 +1,32 @@ +using System.Threading.Tasks; +using Asp.Versioning; +using Microsoft.AspNetCore.Mvc; +using Volo.Abp; +using Volo.Abp.Content; +using Volo.Docs.Common; +using Volo.Docs.Common.Documents; + +namespace Volo.Docs.Documents; + +[RemoteService(Name = DocsCommonRemoteServiceConsts.RemoteServiceName)] +[Area(DocsCommonRemoteServiceConsts.ModuleName)] +[ControllerName("Document")] +[Route("api/docs/documents")] +public class DocsDocumentPdfGeneratorController : DocsControllerBase, IDocumentPdfGeneratorAppService +{ + protected IDocumentPdfGeneratorAppService DocumentPdfGeneratorAppService { get; } + + public DocsDocumentPdfGeneratorController(IDocumentPdfGeneratorAppService documentPdfGeneratorAppService) + { + DocumentPdfGeneratorAppService = documentPdfGeneratorAppService; + } + + [HttpGet] + [Route("pdf")] + public async Task GeneratePdfAsync(DocumentPdfGeneratorInput input) + { + var streamContent = await DocumentPdfGeneratorAppService.GeneratePdfAsync(input); + Response.Headers.ContentDisposition = $"inline; filename=\"{streamContent.FileName}\""; + return streamContent; + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.HttpApi/Volo/Docs/Projects/DocsProjectController.cs b/modules/docs/src/Volo.Docs.Common.HttpApi/Volo/Docs/Projects/DocsProjectController.cs similarity index 90% rename from modules/docs/src/Volo.Docs.HttpApi/Volo/Docs/Projects/DocsProjectController.cs rename to modules/docs/src/Volo.Docs.Common.HttpApi/Volo/Docs/Projects/DocsProjectController.cs index 3a23d379ef..440a215187 100644 --- a/modules/docs/src/Volo.Docs.HttpApi/Volo/Docs/Projects/DocsProjectController.cs +++ b/modules/docs/src/Volo.Docs.Common.HttpApi/Volo/Docs/Projects/DocsProjectController.cs @@ -5,12 +5,14 @@ using Asp.Versioning; using Volo.Abp; using Volo.Abp.Application.Dtos; using Volo.Abp.AspNetCore.Mvc; +using Volo.Docs.Common; +using Volo.Docs.Common.Projects; using Volo.Docs.Documents; namespace Volo.Docs.Projects { - [RemoteService(Name = DocsRemoteServiceConsts.RemoteServiceName)] - [Area(DocsRemoteServiceConsts.ModuleName)] + [RemoteService(Name = DocsCommonRemoteServiceConsts.RemoteServiceName)] + [Area(DocsCommonRemoteServiceConsts.ModuleName)] [ControllerName("Project")] [Route("api/docs/projects")] public class DocsProjectController : AbpControllerBase, IProjectAppService diff --git a/modules/docs/src/Volo.Docs.Domain.Shared/Volo.Docs.Domain.Shared.csproj b/modules/docs/src/Volo.Docs.Domain.Shared/Volo.Docs.Domain.Shared.csproj index 8a4911b9b9..2ce827d009 100644 --- a/modules/docs/src/Volo.Docs.Domain.Shared/Volo.Docs.Domain.Shared.csproj +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo.Docs.Domain.Shared.csproj @@ -11,6 +11,7 @@ + diff --git a/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/DocumentParams.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/DocumentParams.cs new file mode 100644 index 0000000000..0bcdfdb8d1 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/DocumentParams.cs @@ -0,0 +1,23 @@ +using System.Collections.Generic; +using System.Text.Json.Serialization; + +namespace Volo.Docs.Documents; + +public class DocumentParams +{ + [JsonPropertyName("parameters")] + public List Parameters { get; set; } = new(); + + + public class DocumentParameter + { + [JsonPropertyName("name")] + public string Name { get; set; } + + [JsonPropertyName("displayName")] + public string DisplayName { get; set; } + + [JsonPropertyName("values")] + public Dictionary Values { get; set; } + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/NavigationNode.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/NavigationNode.cs index 015f711850..43ebfa9a76 100644 --- a/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/NavigationNode.cs +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/NavigationNode.cs @@ -24,6 +24,12 @@ namespace Volo.Docs.Documents [JsonPropertyName("keywords")] public string[] Keywords { get; set; } + + [JsonPropertyName("ignoreOnDownload")] + public bool IgnoreOnDownload { get; set; } + + [JsonPropertyName("isInSeries")] + public bool IsInSeries { get; set; } public bool IsLeaf => !HasChildItems; diff --git a/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentPartialTemplateContent.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/DocumentPartialTemplateContent.cs similarity index 77% rename from modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentPartialTemplateContent.cs rename to modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/DocumentPartialTemplateContent.cs index 5db9fc8164..66a5d27a16 100644 --- a/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentPartialTemplateContent.cs +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/DocumentPartialTemplateContent.cs @@ -1,4 +1,4 @@ -namespace Volo.Docs.HtmlConverting +namespace Volo.Docs.Documents.Rendering { public class DocumentPartialTemplateContent { diff --git a/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/DocumentPartialTemplateWithValues.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/DocumentPartialTemplateWithValues.cs new file mode 100644 index 0000000000..4ae900256e --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/DocumentPartialTemplateWithValues.cs @@ -0,0 +1,10 @@ +using System.Collections.Generic; + +namespace Volo.Docs.Documents.Rendering; + +public class DocumentPartialTemplateWithValues +{ + public string Path { get; set; } + + public Dictionary Parameters { get; set; } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/DocumentRenderParameters.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/DocumentRenderParameters.cs new file mode 100644 index 0000000000..dc7bf95e62 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/DocumentRenderParameters.cs @@ -0,0 +1,20 @@ +using System.Collections.Generic; + +namespace Volo.Docs.Documents.Rendering +{ + public class DocumentRenderParameters : Dictionary + { + public DocumentRenderParameters() + { + + } + + public DocumentRenderParameters(DocumentRenderParameters renderParameters) + { + foreach (var parameter in renderParameters) + { + Add(parameter.Key, parameter.Value); + } + } + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/IDocumentSectionRenderer.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/IDocumentSectionRenderer.cs new file mode 100644 index 0000000000..9179601545 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/IDocumentSectionRenderer.cs @@ -0,0 +1,12 @@ +using System.Collections.Generic; +using System.Threading.Tasks; +using Volo.Abp.DependencyInjection; + +namespace Volo.Docs.Documents.Rendering; + +public interface IDocumentSectionRenderer : ITransientDependency +{ + Task RenderAsync(string document, DocumentRenderParameters parameters = null, List partialTemplates = null); + + Task>> GetAvailableParametersAsync(string document); +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/ScribanDocumentSectionRenderer.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/ScribanDocumentSectionRenderer.cs new file mode 100644 index 0000000000..02881c5a67 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Documents/Rendering/ScribanDocumentSectionRenderer.cs @@ -0,0 +1,302 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Microsoft.Extensions.Logging; +using Microsoft.Extensions.Logging.Abstractions; +using Scriban; +using Volo.Abp; +using Volo.Extensions; + +namespace Volo.Docs.Documents.Rendering; + +public class ScribanDocumentSectionRenderer : IDocumentSectionRenderer +{ + protected readonly static List DocsJsonSections = + [ + new("````json", "````"), + new("```json", "```") + ]; + + protected const string DocsParam = "//[doc-params]"; + protected const string DocsTemplates = "//[doc-template]"; + protected const string DocsNav = "//[doc-nav]"; + + public ILogger Logger { get; set; } + + public ScribanDocumentSectionRenderer() + { + Logger = NullLogger.Instance; + } + + public async Task RenderAsync( + string document, + DocumentRenderParameters parameters = null, + List partialTemplates = null) + { + if (partialTemplates != null && partialTemplates.Any()) + { + document = SetPartialTemplates(document, partialTemplates); + } + + var scribanTemplate = Template.Parse(document); + + if (parameters == null) + { + return await scribanTemplate.RenderAsync(); + } + + var result = await scribanTemplate.RenderAsync(parameters); + + return RemoveOptionsJson(result, DocsParam, DocsNav); + } + + public Task>> GetAvailableParametersAsync(string document) + { + return GetSectionAsync>>(document, DocsParam); + } + + protected virtual async Task GetSectionAsync(string document, string sectionName) where T : new() + { + try + { + if (!HasJsonSection(document) || !document.Contains(sectionName)) + { + return new T(); + } + + var (jsonBeginningIndex, jsonEndingIndex, insideJsonSection, _) = + GetJsonBeginEndIndexesAndPureJson(document, sectionName); + + if (jsonBeginningIndex < 0 || jsonEndingIndex <= 0 || string.IsNullOrWhiteSpace(insideJsonSection)) + { + return new T(); + } + + var pureJson = insideJsonSection.Replace(sectionName, "").Trim(); + + if (!DocsJsonSerializerHelper.TryDeserialize(pureJson, out var section)) + { + throw new UserFriendlyException($"ERROR-20200327: Cannot validate JSON content for `{sectionName}`!"); + } + + return await Task.FromResult(section); + } + catch (Exception) + { + Logger.LogWarning("Unable to parse parameters of document."); + return new T(); + } + } + + protected static string RemoveOptionsJson(string document, params string[] sectionNames) + { + foreach (var sectionName in sectionNames) + { + var orgDocument = document; + + try + { + if (!HasJsonSection(document) || !document.Contains(sectionName)) + { + continue; + } + + var (jsonBeginningIndex, jsonEndingIndex, insideJsonSection, jsonSection) = + GetJsonBeginEndIndexesAndPureJson(document, sectionName); + + if (jsonBeginningIndex < 0 || jsonEndingIndex <= 0 || string.IsNullOrWhiteSpace(insideJsonSection)) + { + continue; + } + + document = document.Remove( + jsonBeginningIndex - jsonSection.Opener.Length, + (jsonEndingIndex + jsonSection.Closer.Length) - (jsonBeginningIndex - jsonSection.Opener.Length) + ); + } + catch (Exception) + { + document = orgDocument; + } + } + + return document; + } + + protected static bool HasJsonSection(string document) + { + return DocsJsonSections.Any(section => document.Contains(section.Opener) && document.Contains(section.Closer)); + } + + protected static (int, int, string, DocsJsonSection) GetJsonBeginEndIndexesAndPureJson(string document, string sectionName) + { + foreach (var section in DocsJsonSections) + { + var (jsonBeginningIndex, jsonEndingIndex, insideJsonSection) = + section.GetJsonBeginEndIndexesAndPureJson(document, sectionName); + + if (jsonBeginningIndex >= 0 && jsonEndingIndex > 0 && !string.IsNullOrWhiteSpace(insideJsonSection)) + { + return (jsonBeginningIndex, jsonEndingIndex, insideJsonSection, section); + } + } + + return (-1, -1, "", null); + } + + protected static string SetPartialTemplates(string document, IReadOnlyCollection templates) + { + foreach (var section in DocsJsonSections) + { + document = section.SetPartialTemplates(document, templates); + } + + return document; + } + + protected class DocsJsonSection + { + public string Opener { get; } + public string Closer { get; } + + public DocsJsonSection(string opener, string closer) + { + Opener = opener; + Closer = closer; + } + + public (int, int, string) GetJsonBeginEndIndexesAndPureJson(string document, string sectionName) + { + var searchedIndex = 0; + + while (searchedIndex < document.Length) + { + var jsonBeginningIndex = document.Substring(searchedIndex).IndexOf(Opener, StringComparison.Ordinal); + + if (jsonBeginningIndex < 0) + { + return (-1, -1, ""); + } + + jsonBeginningIndex += Opener.Length + searchedIndex; + + var jsonEndingIndex = document.Substring(jsonBeginningIndex).IndexOf(Closer, StringComparison.Ordinal); + if (jsonEndingIndex < 0) + { + return (-1, -1, ""); + } + + jsonEndingIndex += jsonBeginningIndex; + var insideJsonSection = document.Substring(jsonBeginningIndex, jsonEndingIndex - jsonBeginningIndex); + + if (insideJsonSection.IndexOf(sectionName, StringComparison.Ordinal) < 0) + { + searchedIndex = jsonEndingIndex + Closer.Length; + continue; + } + + return (jsonBeginningIndex, jsonEndingIndex, insideJsonSection); + } + + return (-1, -1, ""); + } + + public async Task> GetPartialTemplatesInDocumentAsync(string documentContent) + { + var templates = new List(); + + while (documentContent.Contains(Opener)) + { + var afterJsonOpener = documentContent.Substring( + documentContent.IndexOf(Opener, StringComparison.Ordinal) + Opener.Length + ); + + var betweenJsonOpenerAndCloser = afterJsonOpener.Substring(0, + afterJsonOpener.IndexOf(Closer, StringComparison.Ordinal) + ); + + documentContent = afterJsonOpener.Substring( + afterJsonOpener.IndexOf(Closer, StringComparison.Ordinal) + Closer.Length + ); + + if (!betweenJsonOpenerAndCloser.Contains(DocsTemplates)) + { + continue; + } + + var json = betweenJsonOpenerAndCloser.Substring( + betweenJsonOpenerAndCloser.IndexOf(DocsTemplates, StringComparison.Ordinal) + + DocsTemplates.Length); + + if (!DocsJsonSerializerHelper.TryDeserialize(json, + out var template)) + { + throw new UserFriendlyException( + $"ERROR-20200327: Cannot validate JSON content for `AvailableParameters`!"); + } + + templates.Add(template); + } + + return await Task.FromResult(templates); + } + + public string SetPartialTemplates(string document, IReadOnlyCollection templates) + { + var newDocument = new StringBuilder(); + + while (document.Contains(Opener)) + { + var beforeJson = document.Substring(0, + document.IndexOf(Opener, StringComparison.Ordinal) + Opener.Length + ); + + var afterJsonOpener = document.Substring( + document.IndexOf(Opener, StringComparison.Ordinal) + Opener.Length + ); + + var betweenJsonOpenerAndCloser = afterJsonOpener.Substring(0, + afterJsonOpener.IndexOf(Closer, StringComparison.Ordinal) + ); + + if (!betweenJsonOpenerAndCloser.Contains(DocsTemplates)) + { + document = afterJsonOpener.Substring( + afterJsonOpener.IndexOf(Closer, StringComparison.Ordinal) + Closer.Length + ); + + newDocument.Append(beforeJson + betweenJsonOpenerAndCloser + Closer); + continue; + } + + var json = betweenJsonOpenerAndCloser.Substring( + betweenJsonOpenerAndCloser.IndexOf(DocsTemplates, StringComparison.Ordinal) + + DocsTemplates.Length + ); + + if (DocsJsonSerializerHelper.TryDeserialize(json, + out var documentPartialTemplateWithValuesDto)) + { + var template = + templates.FirstOrDefault(t => t.Path == documentPartialTemplateWithValuesDto.Path); + + var beforeTemplate = document.Substring(0, + document.IndexOf(Opener, StringComparison.Ordinal) + ); + + newDocument.Append(beforeTemplate + template?.Content + Closer); + + document = afterJsonOpener.Substring( + afterJsonOpener.IndexOf(Closer, StringComparison.Ordinal) + Closer.Length + ); + } + } + + newDocument.Append(document); + + return newDocument.ToString(); + } + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentToHtmlConverterFactory.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/HtmlConverting/DocumentToHtmlConverterFactory.cs similarity index 82% rename from modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentToHtmlConverterFactory.cs rename to modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/HtmlConverting/DocumentToHtmlConverterFactory.cs index a6a7978eee..43a239b297 100644 --- a/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentToHtmlConverterFactory.cs +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/HtmlConverting/DocumentToHtmlConverterFactory.cs @@ -19,7 +19,7 @@ namespace Volo.Docs.HtmlConverting Options = options.Value; } - public virtual IDocumentToHtmlConverter Create(string format) + public virtual IDocumentToHtmlConverter Create(string format) { var serviceType = Options.Converters.GetOrDefault(format); if (serviceType == null) @@ -27,7 +27,7 @@ namespace Volo.Docs.HtmlConverting throw new ApplicationException($"Unknown document format: {format}"); } - return (IDocumentToHtmlConverter)ServiceProvider.GetRequiredService(serviceType); + return (IDocumentToHtmlConverter)ServiceProvider.GetRequiredService(serviceType); } } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/HtmlConverting/DocumentToHtmlConverterOptions.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/HtmlConverting/DocumentToHtmlConverterOptions.cs new file mode 100644 index 0000000000..a658140d08 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/HtmlConverting/DocumentToHtmlConverterOptions.cs @@ -0,0 +1,14 @@ +using System; +using System.Collections.Generic; + +namespace Volo.Docs.HtmlConverting; + +public class DocumentToHtmlConverterOptions +{ + public Dictionary Converters { get; set; } + + public DocumentToHtmlConverterOptions() + { + Converters = new Dictionary(); + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/HtmlConverting/IDocumentToHtmlConverter.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/HtmlConverting/IDocumentToHtmlConverter.cs new file mode 100644 index 0000000000..351e34feba --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/HtmlConverting/IDocumentToHtmlConverter.cs @@ -0,0 +1,9 @@ +using Volo.Docs.Documents; +using Volo.Docs.HtmlConverting; + +namespace Volo.Docs.HtmlConverting; + +public interface IDocumentToHtmlConverter +{ + string Convert(TContext context); +} diff --git a/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/HtmlConverting/IDocumentToHtmlConverterFactory.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/HtmlConverting/IDocumentToHtmlConverterFactory.cs new file mode 100644 index 0000000000..0be9f79187 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/HtmlConverting/IDocumentToHtmlConverterFactory.cs @@ -0,0 +1,6 @@ +namespace Volo.Docs.HtmlConverting; + +public interface IDocumentToHtmlConverterFactory +{ + IDocumentToHtmlConverter Create(string format); +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Projects/ProjectConsts.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Projects/ProjectConsts.cs index 3322fb7732..b421cfc631 100644 --- a/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Projects/ProjectConsts.cs +++ b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Projects/ProjectConsts.cs @@ -36,5 +36,7 @@ /// Default value: 128 /// public static int MaxVersionNameLength { get; set; } = 128; + + public static string Latest = "latest"; } } diff --git a/modules/docs/src/Volo.Docs.Web/Utils/UrlHelper.cs b/modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Utils/UrlHelper.cs similarity index 100% rename from modules/docs/src/Volo.Docs.Web/Utils/UrlHelper.cs rename to modules/docs/src/Volo.Docs.Domain.Shared/Volo/Docs/Utils/UrlHelper.cs diff --git a/modules/docs/src/Volo.Docs.Domain/Volo.Docs.Domain.csproj b/modules/docs/src/Volo.Docs.Domain/Volo.Docs.Domain.csproj index 5f2c9b6206..e57312e16b 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo.Docs.Domain.csproj +++ b/modules/docs/src/Volo.Docs.Domain/Volo.Docs.Domain.csproj @@ -20,7 +20,11 @@ - + + + + + @@ -28,6 +32,7 @@ + diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/DocsDomainConsts.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/DocsDomainConsts.cs index ff6bd56ee4..1e8463fe6c 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/DocsDomainConsts.cs +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/DocsDomainConsts.cs @@ -3,5 +3,6 @@ public class DocsDomainConsts { public static string LanguageConfigFileName = "docs-langs.json"; + public static string PdfDocumentToHtmlConverterPrefix = "pdf-"; } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/DocsDomainModule.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/DocsDomainModule.cs index 6e6b222351..502b2f9065 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/DocsDomainModule.cs +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/DocsDomainModule.cs @@ -1,10 +1,11 @@ using System; -using System.Collections.Generic; using System.Threading.Tasks; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Options; using Volo.Abp; using Volo.Abp.AutoMapper; +using Volo.Abp.BlobStoring; +using Volo.Abp.Caching; using Volo.Abp.Domain; using Volo.Abp.Domain.Entities.Events.Distributed; using Volo.Abp.Localization; @@ -16,15 +17,19 @@ using Volo.Docs.Documents.FullSearch.Elastic; using Volo.Docs.FileSystem.Documents; using Volo.Docs.GitHub; using Volo.Docs.GitHub.Documents; +using Volo.Docs.HtmlConverting; using Volo.Docs.Localization; using Volo.Docs.Projects; +using Volo.Docs.Projects.Pdf.Markdig; namespace Volo.Docs { [DependsOn( typeof(DocsDomainSharedModule), typeof(AbpDddDomainModule), - typeof(AbpAutoMapperModule) + typeof(AbpAutoMapperModule), + typeof(AbpBlobStoringModule), + typeof(AbpCachingModule) )] public class DocsDomainModule : AbpModule { @@ -76,6 +81,11 @@ namespace Volo.Docs { client.Timeout = TimeSpan.FromMilliseconds(15000); }); + + Configure(options => + { + options.Converters[DocsDomainConsts.PdfDocumentToHtmlConverterPrefix + MarkdigPdfDocumentToHtmlConverter.Type] = typeof(MarkdigPdfDocumentToHtmlConverter); + }); } public async override Task OnApplicationInitializationAsync(ApplicationInitializationContext context) diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/ar.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/ar.json index 6e01a9af72..f7d3533653 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/ar.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/ar.json @@ -38,6 +38,7 @@ "Search": "بحث", "SearchResults": "نتائج البحث", "SearchInTheAllDocuments": "البحث في جميع الوثائق", - "GoogleTranslate": "ترجمة جوجل" + "GoogleTranslate": "ترجمة جوجل", + "DownloadPDF": "تحميل PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/cs.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/cs.json index c8e6d3d19b..ed6c8767b8 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/cs.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/cs.json @@ -38,6 +38,7 @@ "Search": "Vyhledávání", "SearchResults": "Výsledky vyhledávání", "SearchInTheAllDocuments": "Hledejte ve všech dokumentech", - "GoogleTranslate": "Přeložit do češtiny" + "GoogleTranslate": "Přeložit do češtiny", + "DownloadPDF": "Stáhnout PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/de.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/de.json index 343db45f12..6a614441eb 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/de.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/de.json @@ -38,6 +38,7 @@ "Search": "Suchen", "SearchResults": "Suchergebnisse", "SearchInTheAllDocuments": "Durchsuchen Sie alle Dokumente", - "GoogleTranslate": "Ins Deutsche übersetzen" + "GoogleTranslate": "Ins Deutsche übersetzen", + "DownloadPDF": "PDF herunterladen" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/el.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/el.json index 21bc61b7e5..2a1a72dca2 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/el.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/el.json @@ -37,6 +37,7 @@ "Preview": "προεπισκόπηση", "Search": "Αναζήτηση", "SearchResults": "Αποτελέσματα αναζήτησης", - "GoogleTranslate": "Μετάφραση στα ελληνικά" + "GoogleTranslate": "Μετάφραση στα ελληνικά", + "DownloadPDF": "Κατέβασμα PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/en-GB.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/en-GB.json index ba33bd31d6..d56e8da6df 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/en-GB.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/en-GB.json @@ -35,6 +35,7 @@ "UpdatedExplanation": "Updated in the last two weeks.", "Volo.Docs.Domain:010002": "ShortName {ShortName} already exists.", "Preview": "preview", - "GoogleTranslate": "Google Translate" + "GoogleTranslate": "Google Translate", + "DownloadPDF": "Download PDF" } } diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/en.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/en.json index b4414be0ea..73b07169f8 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/en.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/en.json @@ -43,6 +43,7 @@ "ProjectDeletionWarningMessage": "Project will be deleted.", "Docs_Page_Title": "ABP Documentation", "Docs_Page_Description": "Access comprehensive guides and API references in the ABP Documentation, aiding in development and troubleshooting.", - "GoogleTranslate": "Google Translate" + "GoogleTranslate": "Google Translate", + "DownloadPDF": "Download PDF" } } diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/es.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/es.json index 624d56d631..3dcd97e7fe 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/es.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/es.json @@ -38,6 +38,7 @@ "Search": "Buscar", "SearchResults": "Resultados de la búsqueda", "SearchInTheAllDocuments": "Buscar en todos los documentos", - "GoogleTranslate": "Traducir con Google" + "GoogleTranslate": "Traducir con Google", + "DownloadPDF": "Descargar PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/fi.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/fi.json index 543803bec4..db74d481a0 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/fi.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/fi.json @@ -38,6 +38,7 @@ "Search": "Hae", "SearchResults": "Hakutulokset", "SearchInTheAllDocuments": "Hae kaikista asiakirjoista", - "GoogleTranslate": "Google-käännös" + "GoogleTranslate": "Google-käännös", + "DownloadPDF": "Lataa PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/fr.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/fr.json index 6e8ccfffab..1bab402f73 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/fr.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/fr.json @@ -38,6 +38,7 @@ "Search": "Rechercher", "SearchResults": "Résultats de recherche", "SearchInTheAllDocuments": "Rechercher dans tous les documents", - "GoogleTranslate": "Google Traduction" + "GoogleTranslate": "Google Traduction", + "DownloadPDF": "Télécharger PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/hi.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/hi.json index b79c38b9b8..2ba78ec460 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/hi.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/hi.json @@ -38,6 +38,7 @@ "Search": "खोज", "SearchResults": "खोज परिणाम", "SearchInTheAllDocuments": "सभी दस्तावेज़ों में खोजें", - "GoogleTranslate": "गूगल अनुवाद" + "GoogleTranslate": "गूगल अनुवाद", + "DownloadPDF": "PDF डाउनलोड करें" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/hr.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/hr.json index bf71b7faed..1061dee7ab 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/hr.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/hr.json @@ -38,6 +38,7 @@ "Search": "Pretraga", "SearchResults": "Rezultati pretrage", "SearchInTheAllDocuments": "Traži u svim dokumentima", - "GoogleTranslate": "Google prevoditelj" + "GoogleTranslate": "Google prevoditelj", + "DownloadPDF": "Preuzmi PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/hu.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/hu.json index 1624b1b2d1..b8dee63ca4 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/hu.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/hu.json @@ -38,6 +38,7 @@ "Search": "Keresés", "SearchResults": "Keresési eredmények", "SearchInTheAllDocuments": "Keressen az összes dokumentumban", - "GoogleTranslate": "Google Fordító" + "GoogleTranslate": "Google Fordító", + "DownloadPDF": "PDF letöltése" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/is.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/is.json index 5d96a2fac5..62235d3f62 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/is.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/is.json @@ -38,6 +38,7 @@ "Search": "Leit", "SearchResults": "Leitar niðurstöður", "SearchInTheAllDocuments": "Leitaðu í öllum skjölum", - "GoogleTranslate": "Google þýðing" + "GoogleTranslate": "Google þýðing", + "DownloadPDF": "Sækja PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/it.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/it.json index 3983154519..91ef732c01 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/it.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/it.json @@ -38,6 +38,7 @@ "Search": "Ricerca", "SearchResults": "Risultati della ricerca", "SearchInTheAllDocuments": "Cerca in tutti i documenti", - "GoogleTranslate": "Traduci con Google" + "GoogleTranslate": "Traduci con Google", + "DownloadPDF": "Scarica PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/nl.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/nl.json index f126886009..48a82699d7 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/nl.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/nl.json @@ -38,6 +38,7 @@ "Search": "Zoeken", "SearchResults": "Zoekresultaten", "SearchInTheAllDocuments": "Zoek in alle documenten", - "GoogleTranslate": "Google Vertalen" + "GoogleTranslate": "Google Vertalen", + "DownloadPDF": "PDF downloaden" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/pl-PL.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/pl-PL.json index 5d5c58ea3f..35ae3e6801 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/pl-PL.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/pl-PL.json @@ -38,6 +38,7 @@ "Search": "Szukaj", "SearchResults": "Wyniki wyszukiwania", "SearchInTheAllDocuments": "Szukaj we wszystkich dokumentach", - "GoogleTranslate": "Tłumaczenie na polski" + "GoogleTranslate": "Tłumaczenie na polski", + "DownloadPDF": "Pobierz PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/pt-BR.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/pt-BR.json index 0e4143f9ac..497f0c93e2 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/pt-BR.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/pt-BR.json @@ -38,6 +38,7 @@ "Search": "Procurar", "SearchResults": "Procurar Resultados", "SearchInTheAllDocuments": "Pesquise em todos os documentos", - "GoogleTranslate": "Traduzir com Google" + "GoogleTranslate": "Traduzir com Google", + "DownloadPDF": "Baixar PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/ro-RO.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/ro-RO.json index eaf9016463..155dad0754 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/ro-RO.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/ro-RO.json @@ -38,6 +38,7 @@ "Search": "Caută", "SearchResults": "Rezultatele căutării", "SearchInTheAllDocuments": "Căutați în toate documentele", - "GoogleTranslate": "Traducere Google" + "GoogleTranslate": "Traducere Google", + "DownloadPDF": "Descărcare PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/ru.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/ru.json index ae4b2a564d..2b5a200187 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/ru.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/ru.json @@ -38,6 +38,7 @@ "Search": "Поиск", "SearchResults": "результаты поиска", "SearchInTheAllDocuments": "Искать во всех документах", - "GoogleTranslate": "Google Translate" + "GoogleTranslate": "Google Translate", + "DownloadPDF": "Скачать PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/sk.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/sk.json index 54f981e98f..8f0f246a16 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/sk.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/sk.json @@ -38,6 +38,7 @@ "Search": "Vyhľadať", "SearchResults": "Výsledky vyhľadávania", "SearchInTheAllDocuments": "Vyhľadajte vo všetkých dokumentoch", - "GoogleTranslate": "Google preklad" + "GoogleTranslate": "Google preklad", + "DownloadPDF": "Stiahnuť PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/sl.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/sl.json index 3d326a5127..c182e66b3e 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/sl.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/sl.json @@ -38,6 +38,7 @@ "Search": "Iskanje", "SearchResults": "Rezultati iskanja", "SearchInTheAllDocuments": "Poiščite v vseh dokumentih", - "GoogleTranslate": "Google prevajalnik" + "GoogleTranslate": "Google prevajalnik", + "DownloadPDF": "Prenesi PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/sv.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/sv.json index 2ec28362f0..29db42be57 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/sv.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/sv.json @@ -43,6 +43,7 @@ "ProjectDeletionWarningMessage": "Projektet kommer att raderas.", "Docs_Page_Title": "ABP-dokumentation", "Docs_Page_Description": "Få tillgång till omfattande guider och API-referenser i ABP Documentation, vilket underlättar utveckling och felsökning.", - "GoogleTranslate": "Google Översätt" + "GoogleTranslate": "Google Översätt", + "DownloadPDF": "Ladda ner PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/tr.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/tr.json index 0e9619ce4d..35b08c6a62 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/tr.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/tr.json @@ -37,6 +37,7 @@ "Preview": "ön izleme", "Search": "Arama", "SearchResults": "Arama Sonuçları", - "GoogleTranslate": "Google Çeviri" + "GoogleTranslate": "Google Çeviri", + "DownloadPDF": "PDF İndir" } } diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/vi.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/vi.json index 612bcad36a..d6916d05ad 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/vi.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/vi.json @@ -38,6 +38,7 @@ "Search": "Tìm kiếm", "SearchResults": "kết quả tìm kiếm", "SearchInTheAllDocuments": "Tìm kiếm trong tất cả các tài liệu", - "GoogleTranslate": "Dịch Google" + "GoogleTranslate": "Dịch Google", + "DownloadPDF": "Tải xuống PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/zh-Hans.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/zh-Hans.json index 4aaac66120..d214b9b4a6 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/zh-Hans.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/zh-Hans.json @@ -38,6 +38,7 @@ "Search": "搜索", "SearchResults": "搜索结果", "SearchInTheAllDocuments": "在所有文档中搜索", - "GoogleTranslate": "谷歌翻译" + "GoogleTranslate": "谷歌翻译", + "DownloadPDF": "下载PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/zh-Hant.json b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/zh-Hant.json index 8f2a6ea86e..ee4a291b61 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/zh-Hant.json +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Localization/Domain/zh-Hant.json @@ -38,6 +38,7 @@ "Search": "搜索", "SearchResults": "搜索結果", "SearchInTheAllDocuments": "在所有文件中搜尋", - "GoogleTranslate": "谷歌翻譯" + "GoogleTranslate": "谷歌翻譯", + "DownloadPDF": "下載PDF" } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/IProjectRepository.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/IProjectRepository.cs index db13ea2c8a..9d7443c5b2 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/IProjectRepository.cs +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/IProjectRepository.cs @@ -8,7 +8,7 @@ namespace Volo.Docs.Projects { public interface IProjectRepository : IBasicRepository { - Task> GetListAsync(string sorting, int maxResultCount, int skipCount, CancellationToken cancellationToken = default); + Task> GetListAsync(string sorting, int maxResultCount, int skipCount,bool includeDetails = false, CancellationToken cancellationToken = default); Task> GetListWithoutDetailsAsync(CancellationToken cancellationToken = default); Task GetByShortNameAsync(string shortName, CancellationToken cancellationToken = default); diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/BlobProjectPdfFileStore.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/BlobProjectPdfFileStore.cs new file mode 100644 index 0000000000..315d89c49c --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/BlobProjectPdfFileStore.cs @@ -0,0 +1,74 @@ +using System.IO; +using System.Threading.Tasks; +using Microsoft.Extensions.Options; +using Volo.Abp.BlobStoring; +using Volo.Abp.DependencyInjection; +using Volo.Abp.Timing; + +namespace Volo.Docs.Projects.Pdf; + +public class BlobProjectPdfFileStore : IProjectPdfFileStore, ITransientDependency +{ + protected IBlobContainer BlobContainer { get; } + protected IOptions Options { get; } + protected IProjectRepository ProjectRepository { get; } + protected IClock Clock { get; } + + public BlobProjectPdfFileStore( + IBlobContainer blobContainer, + IOptions options, + IClock clock, IProjectRepository projectRepository) + { + BlobContainer = blobContainer; + Options = options; + Clock = clock; + ProjectRepository = projectRepository; + } + + public virtual async Task SetAsync(Project project, string version, string languageCode, Stream stream) + { + var fileName = Options.Value.CalculatePdfFileName(project, version, languageCode); + await BlobContainer.SaveAsync(fileName, stream, true); + + var pdfFile = project.FindPdfFile(fileName); + if(pdfFile == null) + { + project.AddPdfFile(project.Id, fileName, version, languageCode); + } + else + { + pdfFile.LastModificationTime = Clock.Now; + } + + await ProjectRepository.UpdateAsync(project); + } + + public virtual async Task GetOrNullAsync(Project project, string version, string languageCode) + { + var fileName = Options.Value.CalculatePdfFileName(project, version, languageCode); + + var pdfFile = project.FindPdfFile(fileName); + if (pdfFile == null) + { + return null; + } + + var lastModificationTime = pdfFile.LastModificationTime ?? pdfFile.CreationTime; + if(lastModificationTime.Add(Options.Value.PdfFileCacheExpiration) <= Clock.Now) + { + return null; + } + + return await BlobContainer.GetOrNullAsync(Options.Value.CalculatePdfFileName(project, version, languageCode)); + } + + public virtual async Task DeleteAsync(Project project, string version, string languageCode) + { + var fileName = Options.Value.CalculatePdfFileName(project, version, languageCode); + + await BlobContainer.DeleteAsync(fileName); + project.RemovePdfFile(fileName); + await ProjectRepository.UpdateAsync(project); + + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/DocsProjectPdfContainer.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/DocsProjectPdfContainer.cs new file mode 100644 index 0000000000..554ed42601 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/DocsProjectPdfContainer.cs @@ -0,0 +1,9 @@ +using Volo.Abp.BlobStoring; + +namespace Volo.Docs.Projects.Pdf; + +[BlobContainerName("docs-document-pdf")] +public class DocsProjectPdfContainer +{ + +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/DocsProjectPdfGeneratorOptions.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/DocsProjectPdfGeneratorOptions.cs new file mode 100644 index 0000000000..ef24e6ffd7 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/DocsProjectPdfGeneratorOptions.cs @@ -0,0 +1,120 @@ +using System; +using Scriban.Syntax; + +namespace Volo.Docs.Projects.Pdf; + +public class DocsProjectPdfGeneratorOptions +{ + public const string StylePlaceholder = "{{style-placeholder}}"; + public const string ContentPlaceholder = "{{content-placeholder}}"; + + /// + /// The HTML layout for the PDF document. + /// + public string HtmlLayout { get; set; } + + /// + /// The HTML style for the PDF document. + /// + public string HtmlStyle { get; set; } + + /// + /// The base URL for the PDF document. + /// Used for resolving relative links and images. + /// + public string BaseUrl { get; set; } + + /// + /// The path to the index page of the documentation. + /// + public string IndexPagePath { get; set; } + + /// + /// PDF file cache expiration time. + /// Default value is 24 hours. + /// + public TimeSpan PdfFileCacheExpiration { get; set; } = TimeSpan.FromHours(24); + + /// + /// The function to calculate the PDF file name. + /// Default is "{project.ShortName}-{version}-{languageCode}.pdf". + /// + public Func CalculatePdfFileName { get; set; } + + /// + /// The function to calculate the PDF file title. + /// + public Func CalculatePdfFileTitle { get; set; } + + public Func HtmlContentNormalizer { get; set; } + + public Func DocumentContentNormalizer { get; set; } + + public DocsProjectPdfGeneratorOptions() + { + HtmlLayout = $@" + + + + + + + {ContentPlaceholder} + + "; + + HtmlStyle = @" + body { margin: 15px; line-height: 1.5; font-family: Arial, sans-serif;} + a { text-decoration: none; word-break: break-all; overflow-wrap: break-word;} + li { word-break: break-all; overflow-wrap: break-word; } + .page { + page-break-after: always; + margin-bottom: 30px; + padding: 15px; + } + img { + max-width: 100%; + max-height: 850px; + object-fit: contain; + display: block; + } + code, pre { + background: #f8fafc; + white-space: pre-wrap; + word-wrap: break-word; + } + pre code { padding: 0; border: none; } + code { + padding: 2px 6px; + border-radius: 4px; + border: 1px solid #e2e8f0; + font-family: Consolas, monospace; + } + pre { + position: relative; + padding: 16px; + border-radius: 8px; + border: 1px solid #e2e8f0; + } + blockquote { + border-left: 4px solid #e2e8f0; + margin: 20px 0; + padding: 10px 20px; + background: #f8fafc; + } + table { width: 100%; border-collapse: collapse; table-layout: fixed; } + table img { width: 100% !important; height: auto; display: block; } + th { font-weight: bold; background-color: #f5f5f5; } + th, td { + border: 1px solid #333; + padding: 6px 10px; + word-break: break-all; + overflow-wrap: break-word; + width: 100%; + }"; + + CalculatePdfFileName = (project, version, languageCode) => $"{project.ShortName}-{version}-{languageCode}.pdf"; + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IHtmlToPdfRenderer.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IHtmlToPdfRenderer.cs new file mode 100644 index 0000000000..c17908af51 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IHtmlToPdfRenderer.cs @@ -0,0 +1,10 @@ +using System.Collections.Generic; +using System.IO; +using System.Threading.Tasks; + +namespace Volo.Docs.Projects.Pdf; + +public interface IHtmlToPdfRenderer +{ + Task RenderAsync(string title, string html, List documents); +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IProjectPdfFileStore.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IProjectPdfFileStore.cs new file mode 100644 index 0000000000..4f11d9cad2 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IProjectPdfFileStore.cs @@ -0,0 +1,13 @@ +using System.IO; +using System.Threading.Tasks; + +namespace Volo.Docs.Projects.Pdf; + +public interface IProjectPdfFileStore +{ + Task SetAsync(Project project, string version, string languageCode, Stream stream); + + Task GetOrNullAsync(Project project, string version, string languageCode); + + Task DeleteAsync(Project project, string version, string languageCode); +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IProjectPdfGenerator.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IProjectPdfGenerator.cs new file mode 100644 index 0000000000..af685659fa --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IProjectPdfGenerator.cs @@ -0,0 +1,9 @@ +using System.Threading.Tasks; +using Volo.Abp.Content; + +namespace Volo.Docs.Projects.Pdf; + +public interface IProjectPdfGenerator +{ + Task GenerateAsync(Project project, string version, string languageCode); +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IText/HtmlIdTagWorkerFactory.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IText/HtmlIdTagWorkerFactory.cs new file mode 100644 index 0000000000..17483a7605 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IText/HtmlIdTagWorkerFactory.cs @@ -0,0 +1,40 @@ +using System.Collections.Generic; +using iText.Html2pdf.Attach; +using iText.Html2pdf.Attach.Impl; +using iText.Kernel.Pdf.Navigation; +using iText.StyledXmlParser.Node; + +namespace Volo.Docs.Projects.Pdf.IText; + +public class HtmlIdTagWorkerFactory : DefaultTagWorkerFactory +{ + private readonly iText.Kernel.Pdf.PdfDocument _pdfDocument; + private readonly Dictionary _pageDestinations = new(); + + public HtmlIdTagWorkerFactory(iText.Kernel.Pdf.PdfDocument pdfDocument) + { + _pdfDocument = pdfDocument; + } + + public override ITagWorker GetCustomTagWorker(IElementNode tag, ProcessorContext context) + { + var tagClass = tag.GetAttribute("class"); + if (tag.Name().Equals("div") && tagClass =="page") + { + var id = tag.GetAttribute("id"); + _pageDestinations[id] = _pdfDocument.GetNumberOfPages() + 1; + } + + return base.GetCustomTagWorker(tag, context); + } + + public void AddNamedDestinations() + { + foreach (var pageDestination in _pageDestinations) + { + var page = _pdfDocument.GetPage(pageDestination.Value); + var destination = PdfExplicitDestination.CreateFit(page); + _pdfDocument.AddNamedDestination(pageDestination.Key, destination.GetPdfObject()); + } + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IText/ITextHtmlToPdfRenderer.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IText/ITextHtmlToPdfRenderer.cs new file mode 100644 index 0000000000..1ee6b679e3 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/IText/ITextHtmlToPdfRenderer.cs @@ -0,0 +1,69 @@ +using System; +using System.Collections.Generic; +using System.IO; +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 Volo.Docs.Utils; +using ITextDocument = iText.Layout.Document; + +namespace Volo.Docs.Projects.Pdf.IText; + +public class ITextHtmlToPdfRenderer : IHtmlToPdfRenderer ,ITransientDependency +{ + protected IOptions Options { get; } + + public ITextHtmlToPdfRenderer(IOptions options) + { + Options = options; + } + + public virtual Task RenderAsync(string title, string html, List documents) + { + var pdfStream = new MemoryStream(); + var pdfWrite = new PdfWriter(pdfStream); + var pdfDocument = new iText.Kernel.Pdf.PdfDocument(pdfWrite); + pdfDocument.GetDocumentInfo().SetTitle(title); + var textDocument = new ITextDocument(pdfDocument); + pdfWrite.SetCloseStream(false); + + var converter = new ConverterProperties(); + var tagWorkerFactory = new HtmlIdTagWorkerFactory(pdfDocument); + converter.SetTagWorkerFactory(tagWorkerFactory); + + HtmlConverter.ConvertToDocument(html, pdfDocument, converter); + + tagWorkerFactory.AddNamedDestinations(); + var pdfOutlines = pdfDocument.GetOutlines(false); + BuildPdfOutlines(pdfOutlines, documents); + + textDocument.Close(); + pdfStream.Position = 0; + return Task.FromResult(pdfStream); + } + + private void BuildPdfOutlines(PdfOutline parentOutline, List pdfDocumentNodes) + { + foreach (var pdfDocumentNode in pdfDocumentNodes) + { + if (pdfDocumentNode.IgnoreOnOutline) + { + continue; + } + + var outline = parentOutline.AddOutline(pdfDocumentNode.Title); + if (!pdfDocumentNode.Id.IsNullOrWhiteSpace()) + { + outline.AddAction(UrlHelper.IsExternalLink(pdfDocumentNode.Id) ? PdfAction.CreateURI(pdfDocumentNode.Id) : PdfAction.CreateGoTo(pdfDocumentNode.Id)); + } + + if (pdfDocumentNode.HasChildren) + { + BuildPdfOutlines(outline, pdfDocumentNode.Children); + } + } + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/Markdig/AnchorLinkRenderer.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/Markdig/AnchorLinkRenderer.cs new file mode 100644 index 0000000000..33fd2fd83a --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/Markdig/AnchorLinkRenderer.cs @@ -0,0 +1,62 @@ +using System; +using System.Linq; +using Markdig.Renderers; +using Markdig.Renderers.Html.Inlines; +using Markdig.Syntax.Inlines; +using Volo.Docs.Utils; + +namespace Volo.Docs.Projects.Pdf.Markdig; + +public class AnchorLinkRenderer : LinkInlineRenderer +{ + private readonly PdfDocument _document; + + public AnchorLinkRenderer(PdfDocument document) + { + _document = document; + } + + protected override void Write(HtmlRenderer renderer, LinkInline link) + { + if (UrlHelper.IsExternalLink(link.Url) || link.Url.IsNullOrWhiteSpace() || link.IsImage) + { + base.Write(renderer, link); + return; + } + + var anchor = ResolveRelativeMarkdownPath(_document.Document.Name, link.Url) + .Replace(".md",string.Empty).Replace("/","-").Replace(" ", "-").ToLower(); + + renderer.Write(""); + renderer.Write(link.FirstChild?.ToString() ?? anchor); + renderer.Write(""); + } + + private string ResolveRelativeMarkdownPath(string currentPath, string relativePath) + { + currentPath = currentPath.EnsureStartsWith('/'); + relativePath = relativePath.EnsureStartsWith('/'); + + var currentDir = currentPath.Substring(0, currentPath.LastIndexOf('/')); + + var baseParts = currentDir.Split('/', StringSplitOptions.RemoveEmptyEntries).ToList(); + var relativeParts = relativePath.Split('/', StringSplitOptions.RemoveEmptyEntries); + + foreach (var part in relativeParts) + { + if (part == "..") + { + if (baseParts.Count > 0) + { + baseParts.RemoveAt(baseParts.Count - 1); + } + } + else if (part != ".") + { + baseParts.Add(part); + } + } + + return string.Join("/", baseParts); + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/Markdig/AnchorLinkResolverExtension.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/Markdig/AnchorLinkResolverExtension.cs new file mode 100644 index 0000000000..38405da4d7 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/Markdig/AnchorLinkResolverExtension.cs @@ -0,0 +1,27 @@ +using Markdig; +using Markdig.Renderers; +using Markdig.Renderers.Html.Inlines; + +namespace Volo.Docs.Projects.Pdf.Markdig; + +public class AnchorLinkResolverExtension : IMarkdownExtension +{ + private readonly PdfDocument _document; + + public AnchorLinkResolverExtension(PdfDocument document) + { + _document = document; + } + + public void Setup(MarkdownPipelineBuilder pipeline) + { + } + + public void Setup(MarkdownPipeline pipeline, IMarkdownRenderer renderer) + { + if (renderer is HtmlRenderer htmlRenderer) + { + htmlRenderer.ObjectRenderers.Replace(new AnchorLinkRenderer(_document)); + } + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/Markdig/MarkdigPdfDocumentToHtmlConverter.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/Markdig/MarkdigPdfDocumentToHtmlConverter.cs new file mode 100644 index 0000000000..22c94b5930 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/Markdig/MarkdigPdfDocumentToHtmlConverter.cs @@ -0,0 +1,116 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text.RegularExpressions; +using System.Web; +using Markdig; +using Microsoft.Extensions.Options; +using Volo.Abp.DependencyInjection; +using Volo.Docs.Documents; +using Volo.Docs.HtmlConverting; +using Volo.Docs.Utils; + +namespace Volo.Docs.Projects.Pdf.Markdig; + +public class MarkdigPdfDocumentToHtmlConverter : IDocumentToHtmlConverter, ITransientDependency +{ + public const string Type = "md"; + protected IOptions Options { get; } + + public MarkdigPdfDocumentToHtmlConverter(IOptions options) + { + Options = options; + } + + public virtual string Convert(PdfDocumentToHtmlConverterContext converterContext) + { + var htmlContent = Markdown.ToHtml(NormalizeContent( + converterContext.Content, + converterContext.PdfDocument, + converterContext.DocumentParams), + GetPipeline(converterContext.PdfDocument)); + return NormalizeHtmlContent(htmlContent, converterContext.PdfDocument); + } + + protected virtual MarkdownPipeline GetPipeline(PdfDocument pdfDocument) + { + return new MarkdownPipelineBuilder() + .UseAdvancedExtensions() + .UseBootstrap() + .Use(new AnchorLinkResolverExtension(pdfDocument)) + .Build(); + } + + protected virtual string NormalizeContent(string content, PdfDocument pdfDocument, DocumentParams documentParams) + { + content = Regex.Replace(content, @"`{3,4}json\s*//\[doc-nav\][\s\S]*?`{3,4}", string.Empty, RegexOptions.IgnoreCase); + content = SetContentTitle(content, pdfDocument, documentParams); + if (Options.Value.DocumentContentNormalizer == null) + { + return content; + } + + return Options.Value.DocumentContentNormalizer(content); + } + + protected virtual string NormalizeHtmlContent(string htmlContent, PdfDocument pdfDocument) + { + htmlContent = WrapHtmlWithPageDiv(htmlContent, pdfDocument); + htmlContent = ReplaceRelativeImageUrls(htmlContent, pdfDocument); + if (Options.Value.HtmlContentNormalizer == null) + { + return htmlContent; + } + + return Options.Value.HtmlContentNormalizer(htmlContent); + } + + private string WrapHtmlWithPageDiv(string htmlContent, PdfDocument pdfDocument) + { + return $"
{htmlContent}
"; + } + + private string ReplaceRelativeImageUrls(string htmlContent, PdfDocument pdfDocument) + { + return Regex.Replace(htmlContent, @"(]*)src=""([^""]*)""([^>]*>)", delegate (Match match) + { + if (UrlHelper.IsExternalLink(match.Groups[2].Value)) + { + return match.Value; + } + + var rootUrl = UrlHelper.IsExternalLink(pdfDocument.Document.RawRootUrl) + ? pdfDocument.Document.RawRootUrl.EnsureEndsWith('/') + : Options.Value.BaseUrl.EnsureEndsWith('/') + pdfDocument.Document.RawRootUrl.TrimStart('/').EnsureEndsWith('/'); + var newImageSource = rootUrl + + (pdfDocument.Document.LocalDirectory.IsNullOrEmpty() ? "" : pdfDocument.Document.LocalDirectory.TrimStart('/').EnsureEndsWith('/')) + + match.Groups[2].Value.TrimStart('/'); + + return match.Groups[1] + " src=\"" + HttpUtility.HtmlEncode(newImageSource) + "\" " + match.Groups[3]; + + }, RegexOptions.IgnoreCase | RegexOptions.Singleline | RegexOptions.Multiline); + } + + private static string SetContentTitle(string content, PdfDocument pdfDocument, DocumentParams documentParams) + { + if (pdfDocument.RenderParameters.IsNullOrEmpty()) + { + return content; + } + + var titleLine = content.Split(Environment.NewLine).FirstOrDefault(x => x.TrimStart().StartsWith("#")); + if (titleLine == null) + { + return content; + } + + var paramValues = pdfDocument.RenderParameters.Select(x => + { + var documentParam = documentParams.Parameters.FirstOrDefault(p => p.Name == x.Key); + return $"{documentParam?.Values[x.Value] ?? x.Value}"; + }); + + var newTitle = $"{titleLine.Trim()} ({string.Join(", ", paramValues)})"; + return content.Replace(titleLine, newTitle); + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/PdfDocument.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/PdfDocument.cs new file mode 100644 index 0000000000..a0aca0c710 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/PdfDocument.cs @@ -0,0 +1,17 @@ +using System.Collections.Generic; +using System.Linq; +using Volo.Docs.Documents; +using Volo.Docs.Documents.Rendering; + +namespace Volo.Docs.Projects.Pdf; + +public class PdfDocument +{ + public Document Document { get; set; } + public string Title { get; set; } + public string Id { get; set; } + public List Children { get; set; } = []; + public DocumentRenderParameters RenderParameters { get; set; } + public bool HasChildren => Children.Any(); + public bool IgnoreOnOutline { get; set; } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/PdfDocumentToHtmlConverterContext.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/PdfDocumentToHtmlConverterContext.cs new file mode 100644 index 0000000000..5a99d46634 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/PdfDocumentToHtmlConverterContext.cs @@ -0,0 +1,18 @@ +using Volo.Docs.Documents; + +namespace Volo.Docs.Projects.Pdf; + +public class PdfDocumentToHtmlConverterContext +{ + public string Content { get; set; } + public PdfDocument PdfDocument { get; set; } + + public DocumentParams DocumentParams { get; set; } + + public PdfDocumentToHtmlConverterContext(string content, PdfDocument pdfDocument, DocumentParams documentParams) + { + Content = content; + PdfDocument = pdfDocument; + DocumentParams = documentParams; + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/ProjectPdfGenerator.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/ProjectPdfGenerator.cs new file mode 100644 index 0000000000..de8be78ae1 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Pdf/ProjectPdfGenerator.cs @@ -0,0 +1,469 @@ +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Microsoft.Extensions.Logging; +using Microsoft.Extensions.Logging.Abstractions; +using Microsoft.Extensions.Options; +using Volo.Abp; +using Volo.Abp.Content; +using Volo.Abp.DependencyInjection; +using Volo.Docs.Documents; +using Volo.Docs.Documents.Rendering; +using Volo.Docs.HtmlConverting; +using Volo.Docs.Utils; +using Volo.Extensions; + +namespace Volo.Docs.Projects.Pdf; + +public class ProjectPdfGenerator : IProjectPdfGenerator, ITransientDependency +{ + protected IDocumentSourceFactory DocumentStoreFactory { get; } + protected IDocumentToHtmlConverterFactory DocumentToHtmlConverterFactory { get; } + protected IDocumentRepository DocumentRepository { get; } + protected IDocumentSectionRenderer DocumentSectionRenderer { get; } + protected IOptions Options { get; } + protected IProjectPdfFileStore ProjectPdfFileStore { get; } + protected IHtmlToPdfRenderer HtmlToPdfRenderer { get; } + protected ILogger Logger { get; set; } + protected IDocumentSource DocumentSource { get; set; } + protected DocumentParams DocumentParams { get; set; } + protected Project Project { get; set; } + protected List AllPdfDocuments { get; } = []; + + public ProjectPdfGenerator( + IDocumentSourceFactory documentStoreFactory, + IDocumentRepository documentRepository, + IOptions options, + IDocumentSectionRenderer documentSectionRenderer, + IProjectPdfFileStore projectPdfFileStore, + IHtmlToPdfRenderer htmlToPdfRenderer, + IDocumentToHtmlConverterFactory documentToHtmlConverterFactory) + { + DocumentStoreFactory = documentStoreFactory; + DocumentRepository = documentRepository; + Options = options; + DocumentSectionRenderer = documentSectionRenderer; + ProjectPdfFileStore = projectPdfFileStore; + HtmlToPdfRenderer = htmlToPdfRenderer; + DocumentToHtmlConverterFactory = documentToHtmlConverterFactory; + Logger = NullLogger.Instance; + } + + public virtual async Task GenerateAsync(Project project, string version, string languageCode) + { + var fileName = Options.Value.CalculatePdfFileName(project, version, languageCode); + var fileStream = await ProjectPdfFileStore.GetOrNullAsync(project, version, languageCode); + + if (fileStream != null) + { + return new RemoteStreamContent(fileStream, fileName, "application/pdf"); + } + + Project = project; + DocumentSource = DocumentStoreFactory.Create(project.DocumentStoreType); + DocumentParams = await GetDocumentParamsAsync(project, version, languageCode); + + var navigation = await GetNavigationAsync(project, version, languageCode); + await SetAllPdfDocumentsAsync(navigation.Items, project, version, languageCode); + + var html = await BuildHtmlAsync(); + var title = Options.Value.CalculatePdfFileTitle?.Invoke(project) ?? project.Name; + var pdfStream = await HtmlToPdfRenderer.RenderAsync(title, html, AllPdfDocuments); + + await ProjectPdfFileStore.SetAsync(project, version, languageCode, pdfStream); + + return new RemoteStreamContent(pdfStream, fileName, "application/pdf"); + } + + protected virtual async Task BuildHtmlAsync() + { + var htmlContent = await ConvertDocumentsToHtmlAsync(AllPdfDocuments); + + var htmlBuilder = new StringBuilder(); + htmlBuilder.Append(Options.Value.HtmlLayout); + htmlBuilder.Replace(DocsProjectPdfGeneratorOptions.StylePlaceholder, Options.Value.HtmlStyle); + htmlBuilder.Replace(DocsProjectPdfGeneratorOptions.ContentPlaceholder, htmlContent); + + return htmlBuilder.ToString(); + } + + protected virtual async Task ConvertDocumentsToHtmlAsync(List pdfDocuments) + { + var contentBuilder = new StringBuilder(); + + foreach (var pdfDocument in pdfDocuments) + { + if (pdfDocument.Document != null) + { + var renderedDocument = await RenderDocumentAsync(pdfDocument); + var documentToHtmlConverter = GetDocumentToHtmlConverter(Project, pdfDocument); + var htmlContent = documentToHtmlConverter.Convert(new PdfDocumentToHtmlConverterContext(renderedDocument, pdfDocument, DocumentParams)); + contentBuilder.AppendLine(htmlContent); + } + + if (pdfDocument.HasChildren) + { + contentBuilder.AppendLine(await ConvertDocumentsToHtmlAsync(pdfDocument.Children)); + } + } + + return contentBuilder.ToString(); + } + + protected virtual IDocumentToHtmlConverter GetDocumentToHtmlConverter(Project project, PdfDocument pdfDocument) + { + return DocumentToHtmlConverterFactory.Create(DocsDomainConsts.PdfDocumentToHtmlConverterPrefix +(pdfDocument.Document.Format ?? project.Format)); + } + + protected virtual async Task RenderDocumentAsync(PdfDocument pdfDocument) + { + var parameters = new DocumentRenderParameters(); + if (pdfDocument.RenderParameters != null) + { + foreach (var renderParameter in pdfDocument.RenderParameters) + { + var documentParam = DocumentParams.Parameters.FirstOrDefault(p => p.Name == renderParameter.Key); + parameters.Add(renderParameter.Key, renderParameter.Value); + parameters.Add(renderParameter.Key + "_Value",documentParam?.Values[renderParameter.Value] ?? renderParameter.Value); + } + } + + return await DocumentSectionRenderer.RenderAsync(pdfDocument.Document.Content, parameters); + } + + protected virtual async Task SetAllPdfDocumentsAsync( + List navigations, + Project project, + string version, + string languageCode, + PdfDocument parentPdfDocument = null) + { + var groupedCombinationsDocuments = new Dictionary>(); + + foreach (var navigation in navigations) + { + if (navigation.IgnoreOnDownload) + { + continue; + } + + try + { + var pdfDocument = new PdfDocument + { + Title = navigation.Text, + IgnoreOnOutline = navigation.Path == Options.Value.IndexPagePath, + Id = UrlHelper.IsExternalLink(navigation.Path) ? navigation.Path: null + }; + + if (!navigation.Path.IsNullOrWhiteSpace() && !UrlHelper.IsExternalLink(navigation.Path) && !navigation.HasChildItems) + { + await HandleLeafDocumentAsync( + navigation, + project, + version, + languageCode, + parentPdfDocument, + groupedCombinationsDocuments, + pdfDocument + ); + } + + if (!navigation.IsInSeries) + { + if (parentPdfDocument == null) + { + AllPdfDocuments.AddIfNotContains(pdfDocument); + } + else + { + parentPdfDocument.Children.AddIfNotContains(pdfDocument); + } + } + + if (navigation.HasChildItems) + { + AddParameterCombinationsDocuments(parentPdfDocument, groupedCombinationsDocuments); + await SetAllPdfDocumentsAsync(navigation.Items, project, version, languageCode, pdfDocument); + } + + if (!navigation.IsInSeries || navigation == navigations.Last()) + { + AddParameterCombinationsDocuments(parentPdfDocument, groupedCombinationsDocuments); + } + } + catch (Exception e) + { + Logger.LogWarning(e, $"Cannot get document for the path '{navigation.Path}' in the project {project.Name}."); + } + } + } + + private async Task HandleLeafDocumentAsync( + NavigationNode navigation, + Project project, + string version, + string languageCode, + PdfDocument parentPdfDocument, + Dictionary> groupedCombinationsDocuments, + PdfDocument leafDocument) + { + var document = await GetDocumentAsync(project, navigation.Path, version, languageCode); + var parameters = await DocumentSectionRenderer.GetAvailableParametersAsync(document.Content); + var parameterCombinations = GenerateAllParameterCombinations(parameters.Keys.ToList(), parameters); + var firstCombination = parameterCombinations.FirstOrDefault(); + + leafDocument.Document = document; + leafDocument.RenderParameters = firstCombination; + leafDocument.Id = GetDocumentId(document.Name, document.Format ?? project.Format, firstCombination, true); + leafDocument.Title = GetDocumentTitle(navigation.Text, firstCombination, DocumentParams); + + if (parameterCombinations.Count <= 1) + { + AddParameterCombinationsDocuments(parentPdfDocument, groupedCombinationsDocuments); + return; + } + + for (var i = 0; i < parameterCombinations.Count; i++) + { + var combination = parameterCombinations[i]; + var key = string.Join("-", combination.Select(x => $"{x.Key}_{x.Value}")); + + if (!groupedCombinationsDocuments.ContainsKey(key)) + { + groupedCombinationsDocuments[key] = []; + } + + var combinationDocument = i == 0 ? leafDocument : new PdfDocument + { + Document = document, + Id = GetDocumentId(document.Name, document.Format ?? project.Format, combination, false), + Title = GetDocumentTitle(navigation.Text, combination, DocumentParams), + RenderParameters = combination + }; + + groupedCombinationsDocuments[key].Add(combinationDocument); + } + } + + private void AddParameterCombinationsDocuments(PdfDocument parentPdfDocument, Dictionary> groupedCombinationsDocuments) + { + foreach (var combinations in groupedCombinationsDocuments) + { + if (parentPdfDocument == null) + { + AllPdfDocuments.AddIfNotContains(combinations.Value); + } + else + { + parentPdfDocument.Children.AddIfNotContains(combinations.Value); + } + } + + groupedCombinationsDocuments.Clear(); + } + + private async Task GetNavigationAsync( + Project project, + string version, + string languageCode) + { + var navigationDocument = await GetDocumentAsync(project, project.NavigationDocumentName, version, languageCode); + + if (!DocsJsonSerializerHelper.TryDeserialize(navigationDocument.Content, out var navigation)) + { + throw new UserFriendlyException($"Cannot validate navigation file '{project.NavigationDocumentName}' for the project {project.Name}."); + } + + if (!Options.Value.IndexPagePath.IsNullOrWhiteSpace()) + { + navigation.Items.Insert(0, new NavigationNode + { + Path = Options.Value.IndexPagePath + }); + } + + return navigation; + } + + private async Task GetDocumentParamsAsync( + Project project, + string version, + string languageCode) + { + if (project.ParametersDocumentName.IsNullOrWhiteSpace()) + { + return new DocumentParams(); + } + + try + { + var documentParamsDocument = await GetDocumentAsync(project, project.ParametersDocumentName, version, languageCode); + + if (!DocsJsonSerializerHelper.TryDeserialize(documentParamsDocument.Content, out var documentParams)) + { + throw new UserFriendlyException($"Cannot validate document params file '{project.ParametersDocumentName}' for the project {project.Name}."); + } + + return documentParams; + } + catch (Exception e) + { + Logger.LogError(e, $"Cannot get document params for the project {project.Name}.", e); + return new DocumentParams(); + } + } + + private async Task GetDocumentAsync( + Project project, + string documentName, + string version, + string languageCode) + { + version = string.IsNullOrWhiteSpace(version) ? project.LatestVersionBranchName : version; + + Document document = null; + + Exception firstException = null; + foreach (var name in GetPossibleNames(documentName, project.Format)) + { + try + { + document = await DocumentRepository.FindAsync(project.Id, documentName, version, languageCode); + if (document != null) + { + break; + } + + document = await DocumentSource.GetDocumentAsync(project, name, languageCode, version); + break; + } + catch (Exception ex) + { + firstException ??= ex; + } + } + + if(document == null) + { + throw firstException!; + } + + return document; + } + + private List GenerateAllParameterCombinations(List parameterKeys, Dictionary> parameters) + { + var parameterCombinations = new List(); + + if (parameters.Count <= 0) + { + return parameterCombinations; + } + + GenerateCombinations(0, new DocumentRenderParameters()); + return parameterCombinations; + + void GenerateCombinations(int keyIndex, DocumentRenderParameters currentCombination) + { + if (keyIndex == parameterKeys.Count) + { + parameterCombinations.Add(new DocumentRenderParameters(currentCombination)); + return; + } + + var currentKey = parameterKeys[keyIndex]; + foreach (var value in parameters[currentKey]) + { + currentCombination[currentKey] = value; + GenerateCombinations(keyIndex + 1, currentCombination); + } + } + } + + private static string GetDocumentId(string documentName, string format, DocumentRenderParameters parameters, bool isFirstCombinationDocument) + { + var id = documentName.Replace("." + format, string.Empty).Replace("/","-").Replace(" ", "-").ToLower(); + if (parameters != null && !isFirstCombinationDocument) + { + id = $"{id}{parameters.Select(x => $"{x.Key}_{x.Value}").JoinAsString("-")}"; + } + + return id; + } + + private static string GetDocumentTitle(string title, DocumentRenderParameters parameters, DocumentParams documentParams) + { + if (parameters == null || parameters.Count <= 0) + { + return title; + } + + var paramValues = parameters.Select(x => + { + var documentParam = documentParams.Parameters.FirstOrDefault(p => p.Name == x.Key); + return $"{documentParam?.DisplayName ?? x.Key} : {documentParam?.Values[x.Value] ?? x.Value}"; + }); + + return title.Trim() + $" ({string.Join(", ", paramValues)})"; + } + + private static List GetPossibleNames(string originalDocumentName, string format) + { + var extension = Path.GetExtension(originalDocumentName); + if (extension.IsNullOrWhiteSpace()) + { + extension = "." + format; + } + + if (!extension.Equals("." + format, StringComparison.OrdinalIgnoreCase)) + { + return [originalDocumentName]; + } + + var lowerCaseIndex = "index." + format; + var titleCaseIndex = "Index." + format; + var indexLength = lowerCaseIndex.Length; + + var possibleNames = new List {originalDocumentName}; + if (originalDocumentName.EndsWith("/" + lowerCaseIndex, StringComparison.OrdinalIgnoreCase) || originalDocumentName.Equals(lowerCaseIndex, StringComparison.OrdinalIgnoreCase)) + { + var indexPart = originalDocumentName.Right(indexLength); + + var documentNameWithoutIndex = originalDocumentName.Left(originalDocumentName.Length - lowerCaseIndex.Length); + + if(indexPart != lowerCaseIndex) + { + possibleNames.Add(documentNameWithoutIndex + lowerCaseIndex); + } + + if(indexPart != titleCaseIndex) + { + possibleNames.Add(documentNameWithoutIndex + titleCaseIndex); + } + } + else + { + var documentNameWithoutExtension = RemoveFileExtensionFromPath(originalDocumentName, format).EnsureEndsWith('/'); + possibleNames.Add(documentNameWithoutExtension + lowerCaseIndex); + possibleNames.Add(documentNameWithoutExtension + titleCaseIndex); + } + + return possibleNames; + } + + private static string RemoveFileExtensionFromPath(string path, string format) + { + if (path == null) + { + return null; + } + + return path.EndsWith("." + format) + ? path.Left(path.Length - format.Length - 1) + : path; + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Project.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Project.cs index 48eb93d19e..69fa3a7056 100644 --- a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Project.cs +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/Project.cs @@ -1,4 +1,5 @@ using System; +using System.Collections.Generic; using JetBrains.Annotations; using Volo.Abp; using Volo.Abp.Domain.Entities; @@ -47,9 +48,12 @@ namespace Volo.Docs.Projects public virtual string MainWebsiteUrl { get; set; } public virtual string LatestVersionBranchName { get; set; } + + public virtual List PdfFiles { get; set; } protected Project() { + PdfFiles = new List(); } public Project( @@ -103,5 +107,24 @@ namespace Volo.Docs.Projects { ShortName = ShortName.ToLower(); } + + public virtual ProjectPdfFile FindPdfFile(string fileName) + { + return PdfFiles.Find(x => x.FileName == fileName); + } + + public virtual void AddPdfFile(Guid projectId, string fileName, string version, string languageCode) + { + PdfFiles.Add(new ProjectPdfFile(projectId, fileName, version, languageCode)); + } + + public virtual void RemovePdfFile(string fileName) + { + var pdfFile = FindPdfFile(fileName); + if (pdfFile != null) + { + PdfFiles.Remove(pdfFile); + } + } } } diff --git a/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/ProjectPdfFile.cs b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/ProjectPdfFile.cs new file mode 100644 index 0000000000..135ca3b01e --- /dev/null +++ b/modules/docs/src/Volo.Docs.Domain/Volo/Docs/Projects/ProjectPdfFile.cs @@ -0,0 +1,38 @@ +using System; +using Volo.Abp.Auditing; +using Volo.Abp.Domain.Entities; + +namespace Volo.Docs.Projects; + +public class ProjectPdfFile : Entity, IHasCreationTime, IHasModificationTime +{ + public virtual Guid ProjectId { get; set; } + public virtual string FileName { get; set; } + public virtual string Version { get; set; } + public virtual string LanguageCode { get; set; } + public virtual DateTime CreationTime { get; set; } + public virtual DateTime? LastModificationTime { get; set; } + + protected ProjectPdfFile() + { + + } + + public ProjectPdfFile(Guid projectId, string fileName, string version, string languageCode) + { + ProjectId = projectId; + FileName = fileName; + Version = version; + LanguageCode = languageCode; + } + + public override object[] GetKeys() + { + return [ProjectId, FileName]; + } + + public virtual bool Equals(Guid projectId, string fileName) + { + return ProjectId == projectId && FileName == fileName; + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/DocsDbContext.cs b/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/DocsDbContext.cs index 9ce0c59dc3..56b2204bc5 100644 --- a/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/DocsDbContext.cs +++ b/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/DocsDbContext.cs @@ -16,6 +16,8 @@ namespace Volo.Docs.EntityFrameworkCore public DbSet Documents { get; set; } public DbSet DocumentContributors { get; set; } + + public DbSet ProjectPdfFiles { get; set; } public DocsDbContext(DbContextOptions options) : base(options) diff --git a/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/DocsDbContextModelBuilderExtensions.cs b/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/DocsDbContextModelBuilderExtensions.cs index 745b822f17..86f230164f 100644 --- a/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/DocsDbContextModelBuilderExtensions.cs +++ b/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/DocsDbContextModelBuilderExtensions.cs @@ -31,6 +31,10 @@ namespace Volo.Docs.EntityFrameworkCore b.Property(x => x.NavigationDocumentName).IsRequired().HasMaxLength(ProjectConsts.MaxNavigationDocumentNameLength); b.Property(x => x.ParametersDocumentName).IsRequired().HasMaxLength(ProjectConsts.MaxParametersDocumentNameLength); b.Property(x => x.LatestVersionBranchName).HasMaxLength(ProjectConsts.MaxLatestVersionBranchNameLength); + + b.HasMany(x => x.PdfFiles).WithOne() + .HasForeignKey(x => new { x.ProjectId }) + .IsRequired(); b.ApplyObjectExtensionMappings(); }); @@ -69,6 +73,17 @@ namespace Volo.Docs.EntityFrameworkCore b.ApplyObjectExtensionMappings(); }); + + builder.Entity(b => + { + b.ToTable(AbpDocsDbProperties.DbTablePrefix + "ProjectPdfFiles", AbpDocsDbProperties.DbSchema); + + b.ConfigureByConvention(); + + b.HasKey(x => new { x.ProjectId, x.FileName }); + + b.ApplyObjectExtensionMappings(); + }); builder.TryConfigureObjectExtensions(); } diff --git a/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/DocsEfCoreQueryableExtensions.cs b/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/DocsEfCoreQueryableExtensions.cs index 0bd2e4fff8..89aff2cf3c 100644 --- a/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/DocsEfCoreQueryableExtensions.cs +++ b/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/DocsEfCoreQueryableExtensions.cs @@ -1,6 +1,7 @@ using System.Linq; using Microsoft.EntityFrameworkCore; using Volo.Docs.Documents; +using Volo.Docs.Projects; namespace Volo.Docs.EntityFrameworkCore { @@ -10,5 +11,10 @@ namespace Volo.Docs.EntityFrameworkCore { return !include ? queryable : queryable.Include(x => x.Contributors); } + + public static IQueryable IncludeDetails(this IQueryable queryable, bool include = true) + { + return !include ? queryable : queryable.Include(x => x.PdfFiles); + } } } \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/IDocsDbContext.cs b/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/IDocsDbContext.cs index e85f9b4aa5..69ab6f7b1d 100644 --- a/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/IDocsDbContext.cs +++ b/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/EntityFrameworkCore/IDocsDbContext.cs @@ -16,5 +16,7 @@ namespace Volo.Docs.EntityFrameworkCore DbSet Documents { get; } DbSet DocumentContributors { get; } + + DbSet ProjectPdfFiles { get; set; } } } diff --git a/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/Projects/EfCoreProjectRepository.cs b/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/Projects/EfCoreProjectRepository.cs index cbdf4cec06..e7db47335c 100644 --- a/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/Projects/EfCoreProjectRepository.cs +++ b/modules/docs/src/Volo.Docs.EntityFrameworkCore/Volo/Docs/Projects/EfCoreProjectRepository.cs @@ -19,9 +19,14 @@ namespace Volo.Docs.Projects { } - public virtual async Task> GetListAsync(string sorting, int maxResultCount, int skipCount, CancellationToken cancellationToken = default) + public virtual async Task> GetListAsync( + string sorting, + int maxResultCount, + int skipCount, + bool includeDetails = false, + CancellationToken cancellationToken = default) { - var projects = await (await GetDbSetAsync()).OrderBy(sorting.IsNullOrEmpty() ? "Id desc" : sorting) + var projects = await (await GetDbSetAsync()).IncludeDetails(includeDetails).OrderBy(sorting.IsNullOrEmpty() ? "Id desc" : sorting) .PageBy(skipCount, maxResultCount) .ToListAsync(GetCancellationToken(cancellationToken)); @@ -64,5 +69,10 @@ namespace Volo.Docs.Projects { return shortName.ToLower(); } + + public async override Task> WithDetailsAsync() + { + return (await GetQueryableAsync()).IncludeDetails(); + } } } diff --git a/modules/docs/src/Volo.Docs.HttpApi.Client/ClientProxies/docs-generate-proxy.json b/modules/docs/src/Volo.Docs.HttpApi.Client/ClientProxies/docs-generate-proxy.json index 13e9ebffb2..717e94c04f 100644 --- a/modules/docs/src/Volo.Docs.HttpApi.Client/ClientProxies/docs-generate-proxy.json +++ b/modules/docs/src/Volo.Docs.HttpApi.Client/ClientProxies/docs-generate-proxy.json @@ -4,206 +4,95 @@ "rootPath": "docs", "remoteServiceName": "AbpDocs", "controllers": { - "Volo.Docs.Projects.DocsProjectController": { - "controllerName": "DocsProject", - "controllerGroupName": "Project", + "Volo.Docs.Areas.Documents.DocumentNavigationController": { + "controllerName": "DocumentNavigation", + "controllerGroupName": "DocumentNavigation", "isRemoteService": true, "isIntegrationService": false, "apiVersion": null, - "type": "Volo.Docs.Projects.DocsProjectController", - "interfaces": [ - { - "type": "Volo.Docs.Projects.IProjectAppService", - "name": "IProjectAppService", - "methods": [ - { - "name": "GetListAsync", - "parametersOnMethod": [], - "returnValue": { - "type": "Volo.Abp.Application.Dtos.ListResultDto", - "typeSimple": "Volo.Abp.Application.Dtos.ListResultDto" - } - }, - { - "name": "GetAsync", - "parametersOnMethod": [ - { - "name": "shortName", - "typeAsString": "System.String, System.Private.CoreLib", - "type": "System.String", - "typeSimple": "string", - "isOptional": false, - "defaultValue": null - } - ], - "returnValue": { - "type": "Volo.Docs.Projects.ProjectDto", - "typeSimple": "Volo.Docs.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", - "typeSimple": "Volo.Abp.Application.Dtos.ListResultDto" - } - }, - { - "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" - } - } - ] - } - ], + "type": "Volo.Docs.Areas.Documents.DocumentNavigationController", + "interfaces": [], "actions": { - "GetListAsync": { - "uniqueName": "GetListAsync", - "name": "GetListAsync", - "httpMethod": "GET", - "url": "api/docs/projects", - "supportedVersions": [], - "parametersOnMethod": [], - "parameters": [], - "returnValue": { - "type": "Volo.Abp.Application.Dtos.ListResultDto", - "typeSimple": "Volo.Abp.Application.Dtos.ListResultDto" - }, - "allowAnonymous": null, - "implementFrom": "Volo.Docs.Projects.IProjectAppService" - }, - "GetAsyncByShortName": { - "uniqueName": "GetAsyncByShortName", - "name": "GetAsync", + "GetNavigationAsyncByInput": { + "uniqueName": "GetNavigationAsyncByInput", + "name": "GetNavigationAsync", "httpMethod": "GET", - "url": "api/docs/projects/{shortName}", + "url": "docs/document-navigation", "supportedVersions": [], "parametersOnMethod": [ { - "name": "shortName", - "typeAsString": "System.String, System.Private.CoreLib", - "type": "System.String", - "typeSimple": "string", + "name": "input", + "typeAsString": "Volo.Docs.Areas.Models.DocumentNavigation.GetNavigationNodeWithLinkModel, Volo.Docs.Web", + "type": "Volo.Docs.Areas.Models.DocumentNavigation.GetNavigationNodeWithLinkModel", + "typeSimple": "Volo.Docs.Areas.Models.DocumentNavigation.GetNavigationNodeWithLinkModel", "isOptional": false, "defaultValue": null } ], "parameters": [ { - "nameOnMethod": "shortName", - "name": "shortName", + "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": [], - "bindingSourceId": "Path", - "descriptorName": "" - } - ], - "returnValue": { - "type": "Volo.Docs.Projects.ProjectDto", - "typeSimple": "Volo.Docs.Projects.ProjectDto" - }, - "allowAnonymous": null, - "implementFrom": "Volo.Docs.Projects.IProjectAppService" - }, - "GetDefaultLanguageCodeAsyncByShortNameAndVersion": { - "uniqueName": "GetDefaultLanguageCodeAsyncByShortNameAndVersion", - "name": "GetDefaultLanguageCodeAsync", - "httpMethod": "GET", - "url": "api/docs/projects/{shortName}/defaultLanguage", - "supportedVersions": [], - "parametersOnMethod": [ + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, { - "name": "shortName", - "typeAsString": "System.String, System.Private.CoreLib", + "nameOnMethod": "input", + "name": "LanguageCode", + "jsonName": null, "type": "System.String", "typeSimple": "string", "isOptional": false, - "defaultValue": null + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" }, { - "name": "version", - "typeAsString": "System.String, System.Private.CoreLib", + "nameOnMethod": "input", + "name": "ProjectName", + "jsonName": null, "type": "System.String", "typeSimple": "string", "isOptional": false, - "defaultValue": null - } - ], - "parameters": [ + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, { - "nameOnMethod": "shortName", - "name": "shortName", + "nameOnMethod": "input", + "name": "ProjectFormat", "jsonName": null, "type": "System.String", "typeSimple": "string", "isOptional": false, "defaultValue": null, - "constraintTypes": [], - "bindingSourceId": "Path", - "descriptorName": "" + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" }, { - "nameOnMethod": "version", - "name": "version", + "nameOnMethod": "input", + "name": "RouteVersion", "jsonName": null, "type": "System.String", "typeSimple": "string", @@ -211,109 +100,99 @@ "defaultValue": null, "constraintTypes": null, "bindingSourceId": "ModelBinding", - "descriptorName": "" + "descriptorName": "input" } ], "returnValue": { - "type": "System.String", - "typeSimple": "string" + "type": "Volo.Docs.Documents.NavigationNode", + "typeSimple": "Volo.Docs.Documents.NavigationNode" }, "allowAnonymous": null, - "implementFrom": "Volo.Docs.Projects.IProjectAppService" - }, - "GetVersionsAsyncByShortName": { - "uniqueName": "GetVersionsAsyncByShortName", - "name": "GetVersionsAsync", + "implementFrom": "Volo.Docs.Areas.Documents.DocumentNavigationController" + } + } + }, + "Volo.Docs.Areas.Documents.DocumentResourceController": { + "controllerName": "DocumentResource", + "controllerGroupName": "DocumentResource", + "isRemoteService": true, + "isIntegrationService": false, + "apiVersion": null, + "type": "Volo.Docs.Areas.Documents.DocumentResourceController", + "interfaces": [], + "actions": { + "GetResourceByInput": { + "uniqueName": "GetResourceByInput", + "name": "GetResource", "httpMethod": "GET", - "url": "api/docs/projects/{shortName}/versions", + "url": "document-resources", "supportedVersions": [], "parametersOnMethod": [ { - "name": "shortName", - "typeAsString": "System.String, System.Private.CoreLib", - "type": "System.String", - "typeSimple": "string", + "name": "input", + "typeAsString": "Volo.Docs.Documents.GetDocumentResourceInput, Volo.Docs.Application.Contracts", + "type": "Volo.Docs.Documents.GetDocumentResourceInput", + "typeSimple": "Volo.Docs.Documents.GetDocumentResourceInput", "isOptional": false, "defaultValue": null } ], "parameters": [ { - "nameOnMethod": "shortName", - "name": "shortName", + "nameOnMethod": "input", + "name": "ProjectId", "jsonName": null, - "type": "System.String", + "type": "System.Guid", "typeSimple": "string", "isOptional": false, "defaultValue": null, - "constraintTypes": [], - "bindingSourceId": "Path", - "descriptorName": "" - } - ], - "returnValue": { - "type": "Volo.Abp.Application.Dtos.ListResultDto", - "typeSimple": "Volo.Abp.Application.Dtos.ListResultDto" - }, - "allowAnonymous": null, - "implementFrom": "Volo.Docs.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 + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" }, { - "name": "version", - "typeAsString": "System.String, System.Private.CoreLib", + "nameOnMethod": "input", + "name": "Name", + "jsonName": null, "type": "System.String", "typeSimple": "string", "isOptional": false, - "defaultValue": null - } - ], - "parameters": [ + "defaultValue": null, + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" + }, { - "nameOnMethod": "shortName", - "name": "shortName", + "nameOnMethod": "input", + "name": "Version", "jsonName": null, "type": "System.String", "typeSimple": "string", "isOptional": false, "defaultValue": null, - "constraintTypes": [], - "bindingSourceId": "Path", - "descriptorName": "" + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" }, { - "nameOnMethod": "version", - "name": "version", + "nameOnMethod": "input", + "name": "LanguageCode", "jsonName": null, "type": "System.String", "typeSimple": "string", "isOptional": false, "defaultValue": null, - "constraintTypes": [], - "bindingSourceId": "Path", - "descriptorName": "" + "constraintTypes": null, + "bindingSourceId": "ModelBinding", + "descriptorName": "input" } ], "returnValue": { - "type": "Volo.Docs.Documents.LanguageConfig", - "typeSimple": "Volo.Docs.Documents.LanguageConfig" + "type": "Microsoft.AspNetCore.Mvc.FileResult", + "typeSimple": "Microsoft.AspNetCore.Mvc.FileResult" }, "allowAnonymous": null, - "implementFrom": "Volo.Docs.Projects.IProjectAppService" + "implementFrom": "Volo.Docs.Areas.Documents.DocumentResourceController" } } }, diff --git a/modules/docs/src/Volo.Docs.MongoDB/Volo/Docs/Projects/MongoProjectRepository.cs b/modules/docs/src/Volo.Docs.MongoDB/Volo/Docs/Projects/MongoProjectRepository.cs index af54bd6bc5..95b2ed0244 100644 --- a/modules/docs/src/Volo.Docs.MongoDB/Volo/Docs/Projects/MongoProjectRepository.cs +++ b/modules/docs/src/Volo.Docs.MongoDB/Volo/Docs/Projects/MongoProjectRepository.cs @@ -20,7 +20,12 @@ namespace Volo.Docs.Projects { } - public virtual async Task> GetListAsync(string sorting, int maxResultCount, int skipCount, CancellationToken cancellationToken = default) + public virtual async Task> GetListAsync( + string sorting, + int maxResultCount, + int skipCount, + bool includeDetails = false, + CancellationToken cancellationToken = default) { var projects = await (await GetQueryableAsync(cancellationToken)).OrderBy(sorting.IsNullOrEmpty() ? "Id desc" : sorting).PageBy(skipCount, maxResultCount) .ToListAsync(GetCancellationToken(cancellationToken)); diff --git a/modules/docs/src/Volo.Docs.Web/DocsWebAutoMapperProfile.cs b/modules/docs/src/Volo.Docs.Web/DocsWebAutoMapperProfile.cs index a4c4c7647e..e0a383e691 100644 --- a/modules/docs/src/Volo.Docs.Web/DocsWebAutoMapperProfile.cs +++ b/modules/docs/src/Volo.Docs.Web/DocsWebAutoMapperProfile.cs @@ -1,6 +1,4 @@ using AutoMapper; -using Volo.Abp.AutoMapper; -using Volo.Docs.Documents; namespace Volo.Docs { @@ -8,7 +6,6 @@ namespace Volo.Docs { public DocsWebAutoMapperProfile() { - } } } diff --git a/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentPartialTemplateWithValuesDto.cs b/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentPartialTemplateWithValuesDto.cs deleted file mode 100644 index d3ea14921c..0000000000 --- a/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentPartialTemplateWithValuesDto.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System.Collections.Generic; - -namespace Volo.Docs.HtmlConverting -{ - public class DocumentPartialTemplateWithValuesDto - { - public string Path { get; set; } - - public Dictionary Parameters { get; set; } - } -} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentRenderParameters.cs b/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentRenderParameters.cs deleted file mode 100644 index 7d9f26832f..0000000000 --- a/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentRenderParameters.cs +++ /dev/null @@ -1,8 +0,0 @@ -using System.Collections.Generic; - -namespace Volo.Docs.HtmlConverting -{ - public class DocumentRenderParameters : Dictionary - { - } -} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentToHtmlConverterContext.cs b/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentToHtmlConverterContext.cs new file mode 100644 index 0000000000..53a5c4d631 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentToHtmlConverterContext.cs @@ -0,0 +1,26 @@ +using Volo.Docs.Common.Projects; +using Volo.Docs.Documents; + +namespace Volo.Docs.HtmlConverting; + +public class DocumentToHtmlConverterContext +{ + public ProjectDto Project { get; set; } + public DocumentWithDetailsDto Document { get; set; } + public string Version { get; set; } + public string LanguageCode { get; set; } + public string ProjectShortName { get; set; } + + public DocumentToHtmlConverterContext(ProjectDto project, + DocumentWithDetailsDto document, + string version, + string languageCode, + string projectShortName = null) + { + Project = project; + Document = document; + Version = version; + LanguageCode = languageCode; + ProjectShortName = projectShortName; + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentToHtmlConverterOptions.cs b/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentToHtmlConverterOptions.cs deleted file mode 100644 index f332f6f58a..0000000000 --- a/modules/docs/src/Volo.Docs.Web/HtmlConverting/DocumentToHtmlConverterOptions.cs +++ /dev/null @@ -1,15 +0,0 @@ -using System; -using System.Collections.Generic; - -namespace Volo.Docs.HtmlConverting -{ - public class DocumentToHtmlConverterOptions - { - public Dictionary Converters { get; set; } - - public DocumentToHtmlConverterOptions() - { - Converters = new Dictionary(); - } - } -} diff --git a/modules/docs/src/Volo.Docs.Web/HtmlConverting/IDocumentSectionRenderer.cs b/modules/docs/src/Volo.Docs.Web/HtmlConverting/IDocumentSectionRenderer.cs deleted file mode 100644 index 73560a7273..0000000000 --- a/modules/docs/src/Volo.Docs.Web/HtmlConverting/IDocumentSectionRenderer.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System.Collections.Generic; -using System.Threading.Tasks; -using Volo.Abp.DependencyInjection; - -namespace Volo.Docs.HtmlConverting -{ - public interface IDocumentSectionRenderer: ITransientDependency - { - Task RenderAsync(string doucment, DocumentRenderParameters parameters = null, List partialTemplates = null); - - Task>> GetAvailableParametersAsync(string document); - - Task> GetPartialTemplatesInDocumentAsync(string documentContent); - - Task GetDocumentNavigationsAsync(string documentContent); - } -} diff --git a/modules/docs/src/Volo.Docs.Web/HtmlConverting/IDocumentToHtmlConverter.cs b/modules/docs/src/Volo.Docs.Web/HtmlConverting/IDocumentToHtmlConverter.cs deleted file mode 100644 index efe145cac2..0000000000 --- a/modules/docs/src/Volo.Docs.Web/HtmlConverting/IDocumentToHtmlConverter.cs +++ /dev/null @@ -1,10 +0,0 @@ -using Volo.Docs.Documents; -using Volo.Docs.Projects; - -namespace Volo.Docs.HtmlConverting -{ - public interface IDocumentToHtmlConverter - { - string Convert(ProjectDto project, DocumentWithDetailsDto document, string version, string languageCode, string projectShortName = null); - } -} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Web/HtmlConverting/IDocumentToHtmlConverterFactory.cs b/modules/docs/src/Volo.Docs.Web/HtmlConverting/IDocumentToHtmlConverterFactory.cs deleted file mode 100644 index 9cdca43a8f..0000000000 --- a/modules/docs/src/Volo.Docs.Web/HtmlConverting/IDocumentToHtmlConverterFactory.cs +++ /dev/null @@ -1,7 +0,0 @@ -namespace Volo.Docs.HtmlConverting -{ - public interface IDocumentToHtmlConverterFactory - { - IDocumentToHtmlConverter Create(string format); - } -} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Web/HtmlConverting/IWebDocumentSectionRenderer.cs b/modules/docs/src/Volo.Docs.Web/HtmlConverting/IWebDocumentSectionRenderer.cs new file mode 100644 index 0000000000..b485c7b132 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Web/HtmlConverting/IWebDocumentSectionRenderer.cs @@ -0,0 +1,14 @@ +using System.Collections.Generic; +using System.Threading.Tasks; +using Volo.Abp.DependencyInjection; +using Volo.Docs.Documents.Rendering; + +namespace Volo.Docs.HtmlConverting +{ + public interface IWebDocumentSectionRenderer: IDocumentSectionRenderer + { + Task> GetPartialTemplatesInDocumentAsync(string documentContent); + + Task GetDocumentNavigationsAsync(string documentContent); + } +} diff --git a/modules/docs/src/Volo.Docs.Web/HtmlConverting/ScribanDocumentSectionRenderer.cs b/modules/docs/src/Volo.Docs.Web/HtmlConverting/ScribanDocumentSectionRenderer.cs deleted file mode 100644 index e8d0149cf8..0000000000 --- a/modules/docs/src/Volo.Docs.Web/HtmlConverting/ScribanDocumentSectionRenderer.cs +++ /dev/null @@ -1,316 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using System.Threading.Tasks; -using Scriban; -using Microsoft.Extensions.Logging; -using Microsoft.Extensions.Logging.Abstractions; -using Volo.Abp; -using Volo.Extensions; - -namespace Volo.Docs.HtmlConverting -{ - public class ScribanDocumentSectionRenderer : IDocumentSectionRenderer - { - private readonly static List DocsJsonSections = new List - { - new DocsJsonSection("````json", "````"), - new DocsJsonSection("```json", "```") - }; - private const string DocsParam = "//[doc-params]"; - private const string DocsTemplates = "//[doc-template]"; - private const string DocsNav = "//[doc-nav]"; - - public ILogger Logger { get; set; } - - public ScribanDocumentSectionRenderer() - { - Logger = NullLogger.Instance; - } - - public async Task RenderAsync(string document, DocumentRenderParameters parameters = null, List partialTemplates = null) - { - if (partialTemplates != null && partialTemplates.Any()) - { - document = SetPartialTemplates(document, partialTemplates); - } - - var scribanTemplate = Template.Parse(document); - - if (parameters == null) - { - return await scribanTemplate.RenderAsync(); - } - - var result = await scribanTemplate.RenderAsync(parameters); - - return RemoveOptionsJson(result, DocsParam, DocsNav); - } - - public Task>> GetAvailableParametersAsync(string document) - { - return GetSectionAsync>>(document, DocsParam); - } - - public Task GetDocumentNavigationsAsync(string documentContent) - { - return GetSectionAsync(documentContent, DocsNav); - } - - protected virtual async Task GetSectionAsync(string document, string sectionName) where T : new() - { - try - { - if (!HasJsonSection(document) || !document.Contains(sectionName)) - { - return new T(); - } - - var (jsonBeginningIndex, jsonEndingIndex, insideJsonSection, _) = GetJsonBeginEndIndexesAndPureJson(document, sectionName); - - if (jsonBeginningIndex < 0 || jsonEndingIndex <= 0 || string.IsNullOrWhiteSpace(insideJsonSection)) - { - return new T(); - } - - var pureJson = insideJsonSection.Replace(sectionName, "").Trim(); - - if (!DocsJsonSerializerHelper.TryDeserialize(pureJson, out var section)) - { - throw new UserFriendlyException($"ERROR-20200327: Cannot validate JSON content for `{sectionName}`!"); - } - - return await Task.FromResult(section); - } - catch (Exception) - { - Logger.LogWarning("Unable to parse parameters of document."); - return new T(); - } - } - - private static string RemoveOptionsJson(string document, params string[] sectionNames) - { - - foreach (var sectionName in sectionNames) - { - var orgDocument = document; - - try - { - if (!HasJsonSection(document) || !document.Contains(sectionName)) - { - continue; - } - - var (jsonBeginningIndex, jsonEndingIndex, insideJsonSection, jsonSection) = GetJsonBeginEndIndexesAndPureJson(document, sectionName); - - if (jsonBeginningIndex < 0 || jsonEndingIndex <= 0 || string.IsNullOrWhiteSpace(insideJsonSection)) - { - continue; - } - - document = document.Remove( - jsonBeginningIndex - jsonSection.Opener.Length, - (jsonEndingIndex + jsonSection.Closer.Length) - (jsonBeginningIndex - jsonSection.Opener.Length) - ); - } - catch (Exception) - { - document = orgDocument; - } - } - - return document; - } - - private static bool HasJsonSection(string document) - { - return DocsJsonSections.Any(section => document.Contains(section.Opener) && document.Contains(section.Closer)); - } - - private static (int, int, string, DocsJsonSection) GetJsonBeginEndIndexesAndPureJson(string document, string sectionName) - { - foreach (var section in DocsJsonSections) - { - var (jsonBeginningIndex, jsonEndingIndex, insideJsonSection) = section.GetJsonBeginEndIndexesAndPureJson(document, sectionName); - - if (jsonBeginningIndex >= 0 && jsonEndingIndex > 0 && !string.IsNullOrWhiteSpace(insideJsonSection)) - { - return (jsonBeginningIndex, jsonEndingIndex, insideJsonSection, section); - } - } - - return (-1, -1, "", null); - } - - public async Task> GetPartialTemplatesInDocumentAsync(string documentContent) - { - var templates = new List(); - - foreach (var section in DocsJsonSections) - { - templates.AddRange(await section.GetPartialTemplatesInDocumentAsync(documentContent)); - } - - return templates; - } - - private static string SetPartialTemplates(string document, IReadOnlyCollection templates) - { - foreach (var section in DocsJsonSections) - { - document = section.SetPartialTemplates(document, templates); - } - - return document; - } - - private class DocsJsonSection - { - public string Opener { get; } - public string Closer { get; } - - public DocsJsonSection(string opener, string closer) - { - Opener = opener; - Closer = closer; - } - - public (int, int, string) GetJsonBeginEndIndexesAndPureJson(string document, string sectionName) - { - var searchedIndex = 0; - - while (searchedIndex < document.Length) - { - var jsonBeginningIndex = document.Substring(searchedIndex).IndexOf(Opener, StringComparison.Ordinal); - - if (jsonBeginningIndex < 0) - { - return (-1, -1, ""); - } - - jsonBeginningIndex += Opener.Length + searchedIndex; - - var jsonEndingIndex = document.Substring(jsonBeginningIndex).IndexOf(Closer, StringComparison.Ordinal); - if (jsonEndingIndex < 0) - { - return (-1, -1, ""); - } - - jsonEndingIndex += jsonBeginningIndex; - var insideJsonSection = document[jsonBeginningIndex..jsonEndingIndex]; - - if (insideJsonSection.IndexOf(sectionName, StringComparison.Ordinal) < 0) - { - searchedIndex = jsonEndingIndex + Closer.Length; - continue; - } - - return (jsonBeginningIndex, jsonEndingIndex, insideJsonSection); - } - - return (-1, -1, ""); - } - - public async Task> GetPartialTemplatesInDocumentAsync( - string documentContent) - { - var templates = new List(); - - while (documentContent.Contains(Opener)) - { - var afterJsonOpener = documentContent.Substring( - documentContent.IndexOf(Opener, StringComparison.Ordinal) + Opener.Length - ); - - var betweenJsonOpenerAndCloser = afterJsonOpener.Substring(0, - afterJsonOpener.IndexOf(Closer, StringComparison.Ordinal) - ); - - documentContent = afterJsonOpener.Substring( - afterJsonOpener.IndexOf(Closer, StringComparison.Ordinal) + Closer.Length - ); - - if (!betweenJsonOpenerAndCloser.Contains(DocsTemplates)) - { - continue; - } - - var json = betweenJsonOpenerAndCloser.Substring( - betweenJsonOpenerAndCloser.IndexOf(DocsTemplates, StringComparison.Ordinal) + - DocsTemplates.Length); - - if (!DocsJsonSerializerHelper.TryDeserialize(json, - out var template)) - { - throw new UserFriendlyException( - $"ERROR-20200327: Cannot validate JSON content for `AvailableParameters`!"); - } - - templates.Add(template); - } - - return await Task.FromResult(templates); - } - - public string SetPartialTemplates(string document, - IReadOnlyCollection templates) - { - var newDocument = new StringBuilder(); - - while (document.Contains(Opener)) - { - var beforeJson = document.Substring(0, - document.IndexOf(Opener, StringComparison.Ordinal) + Opener.Length - ); - - var afterJsonOpener = document.Substring( - document.IndexOf(Opener, StringComparison.Ordinal) + Opener.Length - ); - - var betweenJsonOpenerAndCloser = afterJsonOpener.Substring(0, - afterJsonOpener.IndexOf(Closer, StringComparison.Ordinal) - ); - - if (!betweenJsonOpenerAndCloser.Contains(DocsTemplates)) - { - document = afterJsonOpener.Substring( - afterJsonOpener.IndexOf(Closer, StringComparison.Ordinal) + Closer.Length - ); - - newDocument.Append(beforeJson + betweenJsonOpenerAndCloser + Closer); - continue; - } - - var json = betweenJsonOpenerAndCloser.Substring( - betweenJsonOpenerAndCloser.IndexOf(DocsTemplates, StringComparison.Ordinal) + - DocsTemplates.Length - ); - - if (DocsJsonSerializerHelper.TryDeserialize(json, - out var documentPartialTemplateWithValuesDto)) - { - var template = - templates.FirstOrDefault(t => t.Path == documentPartialTemplateWithValuesDto.Path); - - var beforeTemplate = document.Substring(0, - document.IndexOf(Opener, StringComparison.Ordinal) - ); - - newDocument.Append(beforeTemplate + template?.Content + Closer); - - document = afterJsonOpener.Substring( - afterJsonOpener.IndexOf(Closer, StringComparison.Ordinal) + Closer.Length - ); - } - } - - newDocument.Append(document); - - return newDocument.ToString(); - } - } - } -} diff --git a/modules/docs/src/Volo.Docs.Web/HtmlConverting/ScribanWebDocumentSectionRenderer.cs b/modules/docs/src/Volo.Docs.Web/HtmlConverting/ScribanWebDocumentSectionRenderer.cs new file mode 100644 index 0000000000..e4a26b2df6 --- /dev/null +++ b/modules/docs/src/Volo.Docs.Web/HtmlConverting/ScribanWebDocumentSectionRenderer.cs @@ -0,0 +1,38 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using Scriban; +using Microsoft.Extensions.Logging; +using Microsoft.Extensions.Logging.Abstractions; +using Volo.Abp; +using Volo.Abp.ObjectMapping; +using Volo.Docs.Documents.Rendering; +using Volo.Extensions; + +namespace Volo.Docs.HtmlConverting +{ + public class ScribanWebDocumentSectionRenderer : ScribanDocumentSectionRenderer, IWebDocumentSectionRenderer + { + private IObjectMapper ObjectMapper { get; set; } + + public Task GetDocumentNavigationsAsync(string documentContent) + { + return GetSectionAsync(documentContent, DocsNav); + } + + public async Task> GetPartialTemplatesInDocumentAsync( + string documentContent) + { + var templates = new List(); + + foreach (var section in DocsJsonSections) + { + templates.AddRange(await section.GetPartialTemplatesInDocumentAsync(documentContent)); + } + + return templates; + } + } +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Web/Markdown/MarkdownDocumentToHtmlConverter.cs b/modules/docs/src/Volo.Docs.Web/Markdown/MarkdownDocumentToHtmlConverter.cs index 55a9eacb37..54df0c4440 100644 --- a/modules/docs/src/Volo.Docs.Web/Markdown/MarkdownDocumentToHtmlConverter.cs +++ b/modules/docs/src/Volo.Docs.Web/Markdown/MarkdownDocumentToHtmlConverter.cs @@ -1,20 +1,16 @@ using System; -using System.Collections.Generic; using System.IO; -using System.Net; using System.Text.RegularExpressions; -using Microsoft.AspNetCore.Routing; using Microsoft.Extensions.Options; using Volo.Abp.DependencyInjection; +using Volo.Docs.Common.Projects; using Volo.Docs.Documents; using Volo.Docs.HtmlConverting; -using Volo.Docs.Pages.Documents.Project; -using Volo.Docs.Projects; using Volo.Docs.Utils; namespace Volo.Docs.Markdown { - public class MarkdownDocumentToHtmlConverter : IDocumentToHtmlConverter, ITransientDependency + public class MarkdownDocumentToHtmlConverter : IDocumentToHtmlConverter, ITransientDependency { public const string Type = "md"; @@ -34,20 +30,19 @@ namespace Volo.Docs.Markdown private const string MarkdownLinkRegExp = @"\[(.*?)\]\(((.*?)(\?(.*?))*?)\)"; private const string AnchorLinkRegExp = @"]+href=\""(.*?)\""[^>]*>(.*)?"; - public virtual string Convert(ProjectDto project, DocumentWithDetailsDto document, string version, - string languageCode, string projectShortName = null) + public virtual string Convert(DocumentToHtmlConverterContext context) { - if (document.Content.IsNullOrEmpty()) + if (context.Document.Content.IsNullOrEmpty()) { - return document.Content; + return context.Document.Content; } var content = NormalizeLinks( - document.Content, - _uiOptions.SingleProjectMode.Enable ? projectShortName : projectShortName ?? project.ShortName, - version, - document.LocalDirectory, - !_uiOptions.MultiLanguageMode ? languageCode : languageCode ?? document.LanguageCode + context.Document.Content, + _uiOptions.SingleProjectMode.Enable ? context.ProjectShortName : context.ProjectShortName ?? context.Project.ShortName, + context.Version, + context.Document.LocalDirectory, + !_uiOptions.MultiLanguageMode ? context.LanguageCode : context.LanguageCode ?? context.Document.LanguageCode ); var html = _markdownConverter.ConvertToHtml(content); diff --git a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Index.cshtml.cs b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Index.cshtml.cs index 59f66f7b82..baa440dccd 100644 --- a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Index.cshtml.cs +++ b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Index.cshtml.cs @@ -4,7 +4,7 @@ using System.Threading.Tasks; using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.RazorPages; using Microsoft.Extensions.Options; -using Volo.Docs.Projects; +using Volo.Docs.Common.Projects; namespace Volo.Docs.Pages.Documents { diff --git a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/Index.cshtml b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/Index.cshtml index fb1f232cb3..366f8d2a82 100644 --- a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/Index.cshtml +++ b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/Index.cshtml @@ -71,6 +71,7 @@ + @@ -290,6 +291,14 @@ id="sidebar-scroll" class="nav nav-list"> + @if (Model.HasDownloadPdfPermission) + { + + } } diff --git a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/Index.cshtml.cs b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/Index.cshtml.cs index 2bb7c82c21..471747fac1 100644 --- a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/Index.cshtml.cs +++ b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/Index.cshtml.cs @@ -10,15 +10,17 @@ using System.Web; using Microsoft.AspNetCore.Http.Extensions; using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.Rendering; -using Microsoft.Extensions.Localization; using Microsoft.Extensions.Logging; using Microsoft.Extensions.Options; -using Volo.Abp.Application.Dtos; using Volo.Abp.AspNetCore.Mvc.UI.RazorPages; +using Volo.Abp.Authorization.Permissions; using Volo.Abp.Data; using Volo.Abp.Domain.Entities; using Volo.Abp.EventBus.Local; +using Volo.Docs.Common; +using Volo.Docs.Common.Projects; using Volo.Docs.Documents; +using Volo.Docs.Documents.Rendering; using Volo.Docs.HtmlConverting; using Volo.Docs.Models; using Volo.Docs.Projects; @@ -89,6 +91,8 @@ namespace Volo.Docs.Pages.Documents.Project public bool FullSearchEnabled { get; set; } public bool IsLatestVersion { get; private set; } + + public bool HasDownloadPdfPermission { get; set; } public DocumentNavigationsDto DocumentNavigationsDto { get; private set; } @@ -96,8 +100,9 @@ namespace Volo.Docs.Pages.Documents.Project private readonly IDocumentAppService _documentAppService; private readonly IDocumentToHtmlConverterFactory _documentToHtmlConverterFactory; private readonly IProjectAppService _projectAppService; - private readonly IDocumentSectionRenderer _documentSectionRenderer; + private readonly IWebDocumentSectionRenderer _webDocumentSectionRenderer; private readonly DocsUiOptions _uiOptions; + private readonly IPermissionChecker _permissionChecker; protected IDocsLinkGenerator DocsLinkGenerator => LazyServiceProvider.LazyGetRequiredService(); @@ -108,17 +113,18 @@ namespace Volo.Docs.Pages.Documents.Project IDocumentToHtmlConverterFactory documentToHtmlConverterFactory, IProjectAppService projectAppService, IOptions options, - IDocumentSectionRenderer documentSectionRenderer) + IWebDocumentSectionRenderer webDocumentSectionRenderer, + IPermissionChecker permissionChecker) { ObjectMapperContext = typeof(DocsWebModule); _documentAppService = documentAppService; _documentToHtmlConverterFactory = documentToHtmlConverterFactory; _projectAppService = projectAppService; - _documentSectionRenderer = documentSectionRenderer; + _webDocumentSectionRenderer = webDocumentSectionRenderer; + _permissionChecker = permissionChecker; _uiOptions = options.Value; - - + LocalizationResourceType = typeof(DocsResource); } @@ -136,7 +142,7 @@ namespace Volo.Docs.Pages.Documents.Project { return RedirectPermanent(redirectUrl); } - + return await SetPageAsync(); } @@ -146,7 +152,7 @@ namespace Volo.Docs.Pages.Documents.Project ShowProjectsCombobox = _uiOptions.ShowProjectsCombobox && !_uiOptions.SingleProjectMode.Enable; ShowProjectsComboboxLabel = ShowProjectsCombobox && _uiOptions.ShowProjectsComboboxLabel; FullSearchEnabled = await _documentAppService.FullSearchEnabledAsync(); - + HasDownloadPdfPermission = await _permissionChecker.IsGrantedAsync(DocsCommonPermissions.Projects.PdfGeneration); try { await SetProjectAsync(); @@ -561,11 +567,11 @@ namespace Volo.Docs.Pages.Documents.Project var partialTemplates = await GetDocumentPartialTemplatesAsync(); - DocumentNavigationsDto = await _documentSectionRenderer.GetDocumentNavigationsAsync(Document.Content); + DocumentNavigationsDto = await _webDocumentSectionRenderer.GetDocumentNavigationsAsync(Document.Content); try { - Document.Content = await _documentSectionRenderer.RenderAsync(Document.Content, UserPreferences, partialTemplates); + Document.Content = await _webDocumentSectionRenderer.RenderAsync(Document.Content, UserPreferences, partialTemplates); } catch (Exception e) { @@ -577,8 +583,8 @@ namespace Volo.Docs.Pages.Documents.Project DocumentNavigationsDto = new DocumentNavigationsDto(); } - var converter = _documentToHtmlConverterFactory.Create(Document.Format ?? Project.Format); - var content = converter.Convert(Project, Document, GetSpecificVersionOrLatest(), LanguageCode, ProjectName); + var converter = _documentToHtmlConverterFactory.Create(Document.Format ?? Project.Format); + var content = converter.Convert(new DocumentToHtmlConverterContext(Project, Document, GetSpecificVersionOrLatest(), LanguageCode, ProjectName)); content = HtmlNormalizer.ReplaceImageSources( content, @@ -619,7 +625,7 @@ namespace Volo.Docs.Pages.Documents.Project private async Task> GetDocumentPartialTemplatesAsync() { - var partialTemplatesInDocument = await _documentSectionRenderer.GetPartialTemplatesInDocumentAsync(Document.Content); + var partialTemplatesInDocument = await _webDocumentSectionRenderer.GetPartialTemplatesInDocumentAsync(Document.Content); if (!partialTemplatesInDocument?.Any(t => t.Parameters != null) ?? true) { @@ -772,7 +778,7 @@ namespace Volo.Docs.Pages.Documents.Project return; } - var availableParameters = await _documentSectionRenderer.GetAvailableParametersAsync(Document.Content); + var availableParameters = await _webDocumentSectionRenderer.GetAvailableParametersAsync(Document.Content); DocumentPreferences = new DocumentParametersDto { @@ -813,7 +819,7 @@ namespace Volo.Docs.Pages.Documents.Project { if (!DocumentPreferences?.Parameters?.Any() ?? true) { - return; + return; } AlternativeOptionLinkQueries = CollectAlternativeOptionLinksRecursively(); diff --git a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/index.css b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/index.css index e8d0a035a0..dc720fba6d 100644 --- a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/index.css +++ b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/index.css @@ -45,4 +45,18 @@ body { outline: none; } +.docs-sidebar-footer { + border-block-start: 1px solid #aaa; + border-block-end: 1px solid #aaa; +} + +.download-pdf-btn { + text-align: left; + width: 100%; + color: #aaa; + background-color: #0000; + border-color:#0000; + font-size: 14px; +} + /*# sourceMappingURL=Index.css.map */ diff --git a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/index.scss b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/index.scss index 426dec284c..9589b1fb73 100644 --- a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/index.scss +++ b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/index.scss @@ -6,9 +6,9 @@ } } -.input-group{ - .input-group-text{ - background-color: transparent!important; +.input-group { + .input-group-text { + background-color: transparent !important; } } @@ -16,10 +16,12 @@ .next-link, .prev-link { .desc { color: #0D6EFD; - .fa{ + + .fa { font-size: 12px; } } + .title { font-weight: 600; font-size: 18px; @@ -27,3 +29,46 @@ } } } + +body { + top: 0px !important; +} + +.skiptranslate { + iframe { + display: none !important; + } +} + +.google_translate_text { + color: #aaa; + font-family: var(--bs-body-font-family); + font-size: 10pt; + margin-left: 2px; + font-weight: 500; +} + +.goog-te-gadget { + white-space: break-spaces !important; +} + +.goog-te-combo { + &:focus-visible { + border: 0px; + outline: none; + } +} + +.docs-sidebar-footer { + border-block-start: 1px solid #aaa; + border-block-end: 1px solid #aaa; +} + +.download-pdf-btn { + text-align: left; + width: 100%; + color: #aaa; + background-color: transparent; + border-color: transparent; + font-size: 14px; +} \ No newline at end of file diff --git a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Search.cshtml.cs b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Search.cshtml.cs index 7be35394ae..ad60019b57 100644 --- a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Search.cshtml.cs +++ b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Search.cshtml.cs @@ -3,18 +3,15 @@ using System.Collections.Generic; using System.Linq; using System.Text.Encodings.Web; using System.Threading.Tasks; -using System.Web; using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.RazorPages; using Microsoft.Extensions.Options; using Volo.Abp.AspNetCore.Mvc.UI.Bootstrap.TagHelpers.Pagination; using Volo.Abp.Data; +using Volo.Docs.Common.Projects; using Volo.Docs.Documents; using Volo.Docs.GitHub.Documents.Version; -using Volo.Docs.HtmlConverting; -using Volo.Docs.Models; using Volo.Docs.Projects; -using Volo.Docs.Utils; namespace Volo.Docs.Pages.Documents { diff --git a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Shared/Styles/vs.css b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Shared/Styles/vs.css index 32017cd466..36ca24e100 100644 --- a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Shared/Styles/vs.css +++ b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Shared/Styles/vs.css @@ -219,7 +219,7 @@ body.scrolledMore .alert-criteria p.alert-p { } .docs-page .docs-sidebar .docs-tree-list > ul { display: block; - height: calc(100vh - 310px); + height: calc(100vh - 350px); overflow-y: auto; margin-right: -4px !important; margin-top: 20px !important; diff --git a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Shared/Styles/vs.scss b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Shared/Styles/vs.scss index 6c2c4c7627..deba3d39c3 100644 --- a/modules/docs/src/Volo.Docs.Web/Pages/Documents/Shared/Styles/vs.scss +++ b/modules/docs/src/Volo.Docs.Web/Pages/Documents/Shared/Styles/vs.scss @@ -268,7 +268,7 @@ body { > ul { display: block; - height: calc(100vh - 310px); + height: calc(100vh - 350px); overflow-y: auto; margin-right: -4px !important; margin-top: 20px !important; diff --git a/modules/docs/src/Volo.Docs.Web/Volo.Docs.Web.csproj b/modules/docs/src/Volo.Docs.Web/Volo.Docs.Web.csproj index 1d6e0e1ace..2c36600107 100644 --- a/modules/docs/src/Volo.Docs.Web/Volo.Docs.Web.csproj +++ b/modules/docs/src/Volo.Docs.Web/Volo.Docs.Web.csproj @@ -23,7 +23,7 @@ - +
diff --git a/modules/docs/src/Volo.Docs.Web/wwwroot/client-proxies/docs-common-proxy.js b/modules/docs/src/Volo.Docs.Web/wwwroot/client-proxies/docs-common-proxy.js new file mode 100644 index 0000000000..014e357cba --- /dev/null +++ b/modules/docs/src/Volo.Docs.Web/wwwroot/client-proxies/docs-common-proxy.js @@ -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)); + }; + + })(); + +})(); + + diff --git a/modules/docs/src/Volo.Docs.Web/wwwroot/client-proxies/docs-proxy.js b/modules/docs/src/Volo.Docs.Web/wwwroot/client-proxies/docs-proxy.js index 3195d15cd6..32bcf101cb 100644 --- a/modules/docs/src/Volo.Docs.Web/wwwroot/client-proxies/docs-proxy.js +++ b/modules/docs/src/Volo.Docs.Web/wwwroot/client-proxies/docs-proxy.js @@ -5,43 +5,30 @@ (function(){ - // controller volo.docs.projects.docsProject + // controller volo.docs.areas.documents.documentNavigation (function(){ - abp.utils.createNamespace(window, 'volo.docs.projects.docsProject'); + abp.utils.createNamespace(window, 'volo.docs.areas.documents.documentNavigation'); - volo.docs.projects.docsProject.getList = function(ajaxParams) { + volo.docs.areas.documents.documentNavigation.getNavigation = function(input, ajaxParams) { return abp.ajax($.extend(true, { - url: abp.appPath + 'api/docs/projects', + url: abp.appPath + 'docs/document-navigation' + abp.utils.buildQueryString([{ name: 'projectId', value: input.projectId }, { name: 'version', value: input.version }, { name: 'languageCode', value: input.languageCode }, { name: 'projectName', value: input.projectName }, { name: 'projectFormat', value: input.projectFormat }, { name: 'routeVersion', value: input.routeVersion }]) + '', 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)); - }; + // controller volo.docs.areas.documents.documentResource - volo.docs.projects.docsProject.getVersions = function(shortName, ajaxParams) { - return abp.ajax($.extend(true, { - url: abp.appPath + 'api/docs/projects/' + shortName + '/versions', - type: 'GET' - }, ajaxParams)); - }; + (function(){ + + abp.utils.createNamespace(window, 'volo.docs.areas.documents.documentResource'); - volo.docs.projects.docsProject.getLanguageList = function(shortName, version, ajaxParams) { + volo.docs.areas.documents.documentResource.getResource = function(input, ajaxParams) { return abp.ajax($.extend(true, { - url: abp.appPath + 'api/docs/projects/' + shortName + '/' + version + '/languageList', + url: abp.appPath + 'document-resources' + abp.utils.buildQueryString([{ name: 'projectId', value: input.projectId }, { name: 'name', value: input.name }, { name: 'version', value: input.version }, { name: 'languageCode', value: input.languageCode }]) + '', type: 'GET' }, ajaxParams)); }; diff --git a/modules/docs/test/Volo.Docs.Application.Tests/Volo/Docs/ApplicationService_Tests.cs b/modules/docs/test/Volo.Docs.Application.Tests/Volo/Docs/ApplicationService_Tests.cs index 8f92c414c1..662db4c6aa 100644 --- a/modules/docs/test/Volo.Docs.Application.Tests/Volo/Docs/ApplicationService_Tests.cs +++ b/modules/docs/test/Volo.Docs.Application.Tests/Volo/Docs/ApplicationService_Tests.cs @@ -1,6 +1,6 @@ using System.Threading.Tasks; using Shouldly; -using Volo.Docs.Projects; +using Volo.Docs.Common.Projects; using Xunit; namespace Volo.Docs