Browse Source

Merge branch 'dev' into AppUrlProvider

pull/18492/head
maliming 3 years ago
parent
commit
73080b8890
No known key found for this signature in database GPG Key ID: A646B9CB645ECEA4
  1. 18
      Directory.Packages.props
  2. 10
      README.md
  3. 6
      abp_io/AbpIoLocalization/AbpIoLocalization/Admin/Localization/Resources/en.json
  4. 228
      abp_io/AbpIoLocalization/AbpIoLocalization/Admin/Localization/Resources/ru.json
  5. 7
      abp_io/AbpIoLocalization/AbpIoLocalization/Base/Localization/Resources/en.json
  6. 228
      abp_io/AbpIoLocalization/AbpIoLocalization/Base/Localization/Resources/ru.json
  7. 8
      abp_io/AbpIoLocalization/AbpIoLocalization/Blog/Localization/Resources/ru.json
  8. 5
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/ar.json
  9. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/cs.json
  10. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/de.json
  11. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/en-GB.json
  12. 20
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/en.json
  13. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/es.json
  14. 5
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/fi.json
  15. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/fr.json
  16. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/hi.json
  17. 5
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/hu.json
  18. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/is.json
  19. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/it.json
  20. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/nl.json
  21. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/pl-PL.json
  22. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/pt-BR.json
  23. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/ro-RO.json
  24. 1142
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/ru.json
  25. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/sk.json
  26. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/sl.json
  27. 5
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/tr.json
  28. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/vi.json
  29. 5
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/zh-Hans.json
  30. 3
      abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/zh-Hant.json
  31. 2
      abp_io/AbpIoLocalization/AbpIoLocalization/Community/Localization/Resources/en.json
  32. 127
      abp_io/AbpIoLocalization/AbpIoLocalization/Community/Localization/Resources/ru.json
  33. 9
      abp_io/AbpIoLocalization/AbpIoLocalization/Docs/Localization/Resources/ru.json
  34. 4
      abp_io/AbpIoLocalization/AbpIoLocalization/Www/Localization/Resources/en.json
  35. 164
      abp_io/AbpIoLocalization/AbpIoLocalization/Www/Localization/Resources/ru.json
  36. 35
      abp_io/README.md
  37. 2
      common.props
  38. 223
      docs/en/Blog-Posts/2023-11-15 v8_0_Preview/POST.md
  39. BIN
      docs/en/Blog-Posts/2023-11-15 v8_0_Preview/account-module-register.png
  40. BIN
      docs/en/Blog-Posts/2023-11-15 v8_0_Preview/community-talk-2023-8.png
  41. BIN
      docs/en/Blog-Posts/2023-11-15 v8_0_Preview/cover-image.png
  42. BIN
      docs/en/Blog-Posts/2023-11-15 v8_0_Preview/identity-users.gif
  43. BIN
      docs/en/Blog-Posts/2023-11-15 v8_0_Preview/password-complexity-indicators.png
  44. BIN
      docs/en/Blog-Posts/2023-11-15 v8_0_Preview/suite-master-child-datagrid.png
  45. BIN
      docs/en/Blog-Posts/2023-11-15 v8_0_Preview/users-page.png
  46. 2
      docs/en/Community-Articles/2023-10-28-EF-Core-8-Primitive-Collections/POST.md
  47. 1
      docs/en/Community-Articles/2023-11-06-Blazor-Fullstack-Web-Ui/Post.md
  48. 0
      docs/en/Community-Articles/2023-11-17-AOT-Compilation/Post.md
  49. 15
      docs/en/Dependency-Injection.md
  50. 10
      docs/en/Distributed-Event-Bus-RabbitMQ-Integration.md
  51. 12
      docs/en/Migration-Guides/Abp-8_0.md
  52. 108
      docs/en/Migration-Guides/OpenIddict4-to-5.md
  53. BIN
      docs/en/Migration-Guides/images/openiddict-pro-application-modal.png
  54. BIN
      docs/en/Migration-Guides/images/openiddict-pro-application-timelife-modal.png
  55. 2
      docs/en/Repositories.md
  56. 67
      docs/en/UI/Angular/Sorting-Navigation-Elements.md
  57. BIN
      docs/en/images/book-mastering-abp-framework.png
  58. 10
      docs/zh-Hans/Distributed-Event-Bus-RabbitMQ-Integration.md
  59. 9
      framework/src/Volo.Abp.AspNetCore.Components.Server/Volo/Abp/AspNetCore/Components/Server/AbpAspNetCoreComponentsServerModule.cs
  60. 20
      framework/src/Volo.Abp.AspNetCore.Components.Server/Volo/Abp/AspNetCore/Components/Server/Extensibility/BlazorServerLookupApiRequestService.cs
  61. 8
      framework/src/Volo.Abp.AspNetCore.Components.WebAssembly/Volo/Abp/AspNetCore/Components/WebAssembly/Extensibility/WebAssemblyLookupApiRequestService.cs
  62. 4
      framework/src/Volo.Abp.AspNetCore.Mvc.UI.Bootstrap/TagHelpers/Form/AbpInputTagHelperService.cs
  63. 11
      framework/src/Volo.Abp.AspNetCore.Mvc.UI.Bootstrap/TagHelpers/Form/AbpSelectTagHelperService.cs
  64. 12
      framework/src/Volo.Abp.AspNetCore.Mvc.UI.Theme.Shared/wwwroot/libs/abp/aspnetcore-mvc-ui-theme-shared/datatables/datatables-extensions.js
  65. 1
      framework/src/Volo.Abp.AspNetCore.Mvc/Volo/Abp/AspNetCore/Mvc/AspNetCoreApiDescriptionModelProvider.cs
  66. 8
      framework/src/Volo.Abp.AspNetCore.SignalR/Volo/Abp/AspNetCore/SignalR/AbpAspNetCoreSignalRModule.cs
  67. 44
      framework/src/Volo.Abp.Autofac/Volo/Abp/Autofac/AutoFacInjectPropertiesService.cs
  68. 2
      framework/src/Volo.Abp.BlobStoring/Volo/Abp/BlobStoring/BlobContainer.cs
  69. 16
      framework/src/Volo.Abp.Core/Volo/Abp/DependencyInjection/IInjectPropertiesService.cs
  70. 17
      framework/src/Volo.Abp.Core/Volo/Abp/DependencyInjection/NullInjectPropertiesService.cs
  71. 9
      framework/src/Volo.Abp.EventBus.RabbitMQ/Volo/Abp/EventBus/RabbitMq/AbpRabbitMqEventBusOptions.cs
  72. 6
      framework/src/Volo.Abp.EventBus.RabbitMQ/Volo/Abp/EventBus/RabbitMq/RabbitMqDistributedEventBus.cs
  73. 2
      framework/src/Volo.Abp.ExceptionHandling/Volo/Abp/ExceptionHandling/Localization/en-GB.json
  74. 2
      framework/src/Volo.Abp.ExceptionHandling/Volo/Abp/ExceptionHandling/Localization/en.json
  75. 2
      framework/src/Volo.Abp.Http.Client/Volo/Abp/Http/Client/DynamicProxying/ApiDescriptionFinder.cs
  76. 7
      framework/src/Volo.Abp.Http/Volo/Abp/Http/Modeling/ApplicationApiDescriptionModel.cs
  77. 2
      framework/src/Volo.Abp.Http/Volo/Abp/Http/Modeling/ModuleApiDescriptionModel.cs
  78. 5
      framework/src/Volo.Abp.RabbitMQ/Volo/Abp/RabbitMQ/ExchangeDeclareConfiguration.cs
  79. 5
      framework/src/Volo.Abp.RabbitMQ/Volo/Abp/RabbitMQ/QueueDeclareConfiguration.cs
  80. 2
      framework/test/Volo.Abp.AspNetCore.SignalR.Tests/Volo.Abp.AspNetCore.SignalR.Tests.csproj
  81. 24
      framework/test/Volo.Abp.AspNetCore.SignalR.Tests/Volo/Abp/AspNetCore/SignalR/AbpAspNetCoreSignalRTestModule.cs
  82. 70
      framework/test/Volo.Abp.AspNetCore.SignalR.Tests/Volo/Abp/AspNetCore/SignalR/AbpSignalROptions_Tests.cs
  83. 10
      framework/test/Volo.Abp.AspNetCore.SignalR.Tests/Volo/Abp/AspNetCore/SignalR/Program.cs
  84. 37
      framework/test/Volo.Abp.AspNetCore.SignalR.Tests/Volo/Abp/AspNetCore/SignalR/SampleHubs/RegularHubBase.cs
  85. 67
      framework/test/Volo.Abp.Autofac.Tests/Volo/Abp/Autofac/AutoFacInjectingPropertiesService_Tests.cs
  86. 2
      framework/test/Volo.Abp.BlobStoring.Tests/Volo/Abp/BlobStoring/BlobContainer_Tests.cs
  87. 2
      latest-versions.json
  88. 62
      modules/audit-logging/src/Volo.Abp.AuditLogging.Domain.Shared/Volo/Abp/AuditLogging/Localization/en.json
  89. 4
      modules/audit-logging/src/Volo.Abp.AuditLogging.Domain.Shared/Volo/Abp/AuditLogging/Localization/tr.json
  90. 74
      modules/cms-kit/src/Volo.CmsKit.Domain.Shared/Volo/CmsKit/Localization/Resources/en.json
  91. 18
      modules/cms-kit/src/Volo.CmsKit.Public.Web/Security/Captcha/CaptchaOptions.cs
  92. 12
      modules/cms-kit/src/Volo.CmsKit.Public.Web/Security/Captcha/RandomTextGenerator.cs
  93. 134
      modules/cms-kit/src/Volo.CmsKit.Public.Web/Security/Captcha/SimpleMathsCaptchaGenerator.cs
  94. 3
      modules/cms-kit/src/Volo.CmsKit.Public.Web/Volo.CmsKit.Public.Web.csproj
  95. 2
      modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/Index.cshtml
  96. 6
      modules/feature-management/src/Volo.Abp.FeatureManagement.Domain.Shared/Volo/Abp/FeatureManagement/Localization/Domain/en.json
  97. 13
      modules/openiddict/app/OpenIddict.Demo.API/Program.cs
  98. 35
      modules/openiddict/app/OpenIddict.Demo.Client.BlazorWASM/Pages/Index.razor
  99. 1
      modules/openiddict/app/OpenIddict.Demo.Client.BlazorWASM/Program.cs
  100. 19
      modules/openiddict/app/OpenIddict.Demo.Client.Mvc/Pages/Index.cshtml

18
Directory.Packages.props

@ -15,10 +15,10 @@
<PackageVersion Include="AWSSDK.SecurityToken" Version="3.7.300.2" /> <PackageVersion Include="AWSSDK.SecurityToken" Version="3.7.300.2" />
<PackageVersion Include="Azure.Messaging.ServiceBus" Version="7.17.0" /> <PackageVersion Include="Azure.Messaging.ServiceBus" Version="7.17.0" />
<PackageVersion Include="Azure.Storage.Blobs" Version="12.19.1" /> <PackageVersion Include="Azure.Storage.Blobs" Version="12.19.1" />
<PackageVersion Include="Blazorise" Version="1.4.0" /> <PackageVersion Include="Blazorise" Version="1.3.2" />
<PackageVersion Include="Blazorise.Components" Version="1.4.0" /> <PackageVersion Include="Blazorise.Components" Version="1.3.2" />
<PackageVersion Include="Blazorise.DataGrid" Version="1.4.0" /> <PackageVersion Include="Blazorise.DataGrid" Version="1.3.2" />
<PackageVersion Include="Blazorise.Snackbar" Version="1.4.0" /> <PackageVersion Include="Blazorise.Snackbar" Version="1.3.2" />
<PackageVersion Include="Castle.Core" Version="5.1.1" /> <PackageVersion Include="Castle.Core" Version="5.1.1" />
<PackageVersion Include="Castle.Core.AsyncInterceptor" Version="2.1.0" /> <PackageVersion Include="Castle.Core.AsyncInterceptor" Version="2.1.0" />
<PackageVersion Include="CommonMark.NET" Version="0.15.1" /> <PackageVersion Include="CommonMark.NET" Version="0.15.1" />
@ -113,11 +113,11 @@
<PackageVersion Include="NUglify" Version="1.21.0" /> <PackageVersion Include="NUglify" Version="1.21.0" />
<PackageVersion Include="Nullable" Version="1.3.1" /> <PackageVersion Include="Nullable" Version="1.3.1" />
<PackageVersion Include="Octokit" Version="9.0.0" /> <PackageVersion Include="Octokit" Version="9.0.0" />
<PackageVersion Include="OpenIddict.Abstractions" Version="4.10.0" /> <PackageVersion Include="OpenIddict.Abstractions" Version="5.0.0-rc1.23614.58" />
<PackageVersion Include="OpenIddict.Core" Version="4.10.0" /> <PackageVersion Include="OpenIddict.Core" Version="5.0.0-rc1.23614.58" />
<PackageVersion Include="OpenIddict.Server.AspNetCore" Version="4.10.0" /> <PackageVersion Include="OpenIddict.Server.AspNetCore" Version="5.0.0-rc1.23614.58" />
<PackageVersion Include="OpenIddict.Validation.AspNetCore" Version="4.10.0" /> <PackageVersion Include="OpenIddict.Validation.AspNetCore" Version="5.0.0-rc1.23614.58" />
<PackageVersion Include="OpenIddict.Validation.ServerIntegration" Version="4.10.0" /> <PackageVersion Include="OpenIddict.Validation.ServerIntegration" Version="5.0.0-rc1.23614.58" />
<PackageVersion Include="Oracle.EntityFrameworkCore" Version="8.21.121" /> <PackageVersion Include="Oracle.EntityFrameworkCore" Version="8.21.121" />
<PackageVersion Include="Polly" Version="8.2.0" /> <PackageVersion Include="Polly" Version="8.2.0" />
<PackageVersion Include="Polly.Extensions.Http" Version="3.0.0" /> <PackageVersion Include="Polly.Extensions.Http" Version="3.0.0" />

10
README.md

@ -42,6 +42,16 @@ Create a new solution:
<img width="500" src="docs/en/images/db-options.png"> <img width="500" src="docs/en/images/db-options.png">
## The Book: Mastering ABP Framework
Written by the creator of ABP Framework, this book will help you to gain a complete understanding of the ABP Framework and modern web application development techniques.
* [Buy on Amazon](https://www.amazon.com/gp/product/B097Z2DM8Q)
* [Buy on Packt Publishing](https://www.packtpub.com/product/mastering-abp-framework/9781801079242)
* [More details about the book](https://abp.io/books/mastering-abp-framework)
![book-mastering-abp-framework](docs/en/images/book-mastering-abp-framework.png)
## What ABP Provides? ## What ABP Provides?
ABP provides a **full stack developer experience**. ABP provides a **full stack developer experience**.

6
abp_io/AbpIoLocalization/AbpIoLocalization/Admin/Localization/Resources/en.json

@ -492,7 +492,7 @@
"QuotationTemplate.SubTotal:": "Sub Total :", "QuotationTemplate.SubTotal:": "Sub Total :",
"QuotationTemplate.Tax/VAT:": "Tax / Vat (%{0}) :", "QuotationTemplate.Tax/VAT:": "Tax / Vat (%{0}) :",
"QuotationTemplate.TotalDiscount:": "Total Discount :", "QuotationTemplate.TotalDiscount:": "Total Discount :",
"QuotationTemplate.TOTALDUE:": "TOTAL DUE :", "QuotationTemplate.TOTALDUE:": "TOTAL DUE :",
"QuotationTemplate.BankAccount": "Our bank account information can be found at {0}", "QuotationTemplate.BankAccount": "Our bank account information can be found at {0}",
"Permission:Raffles": "Raffle", "Permission:Raffles": "Raffle",
"Permission:Draw": "Draw", "Permission:Draw": "Draw",
@ -560,6 +560,8 @@
"AddSession": "Add Session", "AddSession": "Add Session",
"AddSponsor": "Add Sponsor", "AddSponsor": "Add Sponsor",
"SponsorLogo": "Sponsor Logo", "SponsorLogo": "Sponsor Logo",
"RegistrationUrl": "Registration Url" "RegistrationUrl": "Registration Url",
"AllowAbpStudioBetaAccess": "Allow ABP Studio Beta Access",
"TotalQuestionCanNotBeNullMessage": "Total Question can not be null"
} }
} }

228
abp_io/AbpIoLocalization/AbpIoLocalization/Admin/Localization/Resources/ru.json

@ -220,6 +220,7 @@
"SuccessfullyReIndexAllPosts": "Все сообщения успешно переиндексированы.", "SuccessfullyReIndexAllPosts": "Все сообщения успешно переиндексированы.",
"Permission:FullSearch": "Полнотекстовый поиск", "Permission:FullSearch": "Полнотекстовый поиск",
"Menu:CliAnalytics": "Cli Analytics", "Menu:CliAnalytics": "Cli Analytics",
"Menu:Reports": "Отчеты",
"TemplateName": "Имя Шаблона", "TemplateName": "Имя Шаблона",
"TemplateVersion": "Версия шаблона", "TemplateVersion": "Версия шаблона",
"DatabaseProvider": "Поставщик базы данных", "DatabaseProvider": "Поставщик базы данных",
@ -233,6 +234,8 @@
"CliAnalytics": "Cli Analytics", "CliAnalytics": "Cli Analytics",
"Permission:CliAnalyticses": "Cli Analyticses", "Permission:CliAnalyticses": "Cli Analyticses",
"Permission:CliAnalytics": "Cli Analytics", "Permission:CliAnalytics": "Cli Analytics",
"Reports": "Отчеты",
"Permission:Reports": "Отчеты",
"Search": "Поиск", "Search": "Поиск",
"ClearFilter": "Очистить фильтр", "ClearFilter": "Очистить фильтр",
"LicensePrivateKey": "Лицензионный закрытый ключ", "LicensePrivateKey": "Лицензионный закрытый ключ",
@ -348,6 +351,229 @@
"Volo.AbpIo.Commercial:030008": "Дата покупки может быть установлена только при статусе «Куплено»!", "Volo.AbpIo.Commercial:030008": "Дата покупки может быть установлена только при статусе «Куплено»!",
"Volo.AbpIo.Commercial:030009": "Пользователь не найден!", "Volo.AbpIo.Commercial:030009": "Пользователь не найден!",
"Volo.AbpIo.Commercial:030010": "Чтобы приобрести пробную лицензию, сначала вам необходимо активировать пробную лицензию!", "Volo.AbpIo.Commercial:030010": "Чтобы приобрести пробную лицензию, сначала вам необходимо активировать пробную лицензию!",
"Volo.AbpIo.Commercial:030011": "Приобретенную пробную лицензию удалить нельзя!" "Volo.AbpIo.Commercial:030011": "Приобретенную пробную лицензию удалить нельзя!",
"Permission:SendWelcomeEmail": "Отправить приветственное письмо",
"SendWelcomeEmail": "Отправить приветственное письмо",
"SendWelcomeEmailWarningMessage": "Вы уверены, что хотите отправить приветственное письмо членам организации?",
"SendWelcomeEmailSuccessMessage": "Приветственное письмо успешно отправлено!",
"Activate": "Активировать",
"ActivateTrialLicenseWarningMessage": " Когда вы активируете пробную лицензию, пользователю будет отправлено приветственное письмо. ",
"ActivateTrialLicenseSuccessMessage": "Активация прошла успешно, членам организации отправлено приветственное письмо.",
"PaymentRequestId": "Идентификатор запроса платежа",
"AdditionalDeveloperCount": "Дополнительное количество разработчиков",
"LicensePrice": "Цена лицензии",
"PurchaseDate": "Дата покупки",
"IsAbpBookDownloaded": "Книга «Освоение ABP» загружена?",
"IsMasteringAbpBookDownloadEnabled": "Загрузка книги ABP включена",
"Permission:Accounting:CustomPaymentLinkGenerator": "Пользовательская ссылка для оплаты",
"CustomPaymentLink": "Пользовательская ссылка для оплаты",
"Menu:CustomPaymentLink": "Пользовательская ссылка для оплаты",
"Amount": "Количество",
"GenerateCustomPaymentLink": "Создать персонализированную платежную ссылку",
"GeneratedPaymentLink": "Сгенерированная платежная ссылка",
"CopyText": "Копировать текст",
"Permission:CommunityEvents": "События",
"Menu:Events": "События",
"Events": "События",
"EventType": "Тип события",
"Number": "Число",
"RegistrationURL": "URL-адрес регистрации",
"URL": "URL-адрес",
"EventDeletionConfirmationMessage": "Вы уверены, что хотите удалить это мероприятие?",
"Enum:EventType:0": "Обсуждения сообщества",
"CreateAnEvent": "Создать событие",
"Permission:CommunitySpeakers": "Динамики",
"CreateASpeaker": "Создать динамик",
"Speakers": "Динамики",
"Image": "Изображение",
"GithubURL": "URL-адрес Гитхаба",
"SpeakerDeletionConfirmationMessage": "Вы уверены, что хотите удалить этого динамика?",
"Menu:Speakers": "Динамики",
"ChooseSpeakerImage": "Выберите изображение динамика...",
"SpeakerImage": "Изображение докладчика",
"AddSpeaker": "Добавить динамик",
"ShowPurchaseItemsOfOrganizations": "Покупка предметов",
"Enum:OrganizationPurchaseState:0": "Не доставлен",
"Enum:OrganizationPurchaseState:1": "Доставленный",
"PurchaseItems": "Покупка предметов",
"SuccessfullyUpdated": "Успешно обновлено",
"SuccessfullyAdded": "Успешно добавлено",
"PurchaseState": "Статус покупки",
"ShowBetweenDayCount": "Шоу между днями",
"PurchaseOrder": "Заказ на покупку",
"ShowCreateInvoiceOfOrganization": "Создать счет",
"ShowCreateQuotationOfOrganization": "Создать предложение",
"BookDiscounts": "Скидки на книги",
"Permission:BookDiscount": "Забронировать скидку",
"Menu:BookDiscounts": "Скидки на книги",
"BookType": "Тип книги",
"PurchasePlatform": "Платформа покупки",
"StartTime": "Время начала",
"EndTime": "Время окончания",
"CreateABookDiscount": "Создать скидку на книгу",
"BookDiscountDeletionConfirmationMessage": "Вы уверены, что хотите удалить эту скидку на книгу?",
"CustomPaymentFlexSwitchDescription": "С лицензией",
"AllowFeatureUpgradeOnLicenseExpire": "Разрешить обновление функций по истечении срока действия лицензии",
"Deleted{0}": "[Удален {0}]",
"Tags": "Теги",
"SetTagsInfo": "Теги должны быть разделены запятыми. ",
"RejectTrialLicenseWarningMessage": "Вы уверены, что хотите отклонить этот запрос на пробную лицензию?",
"ExportToExcel": "Экспорт в Excel",
"OverallTotalPrice": "Общая общая цена",
"OverallDiscountPrice": "Общая цена со скидкой",
"OverallDiscountText": "Общий текст скидки",
"SelectReport": "- Выберите отчет -",
"NoDataAvailable": "Данные недоступны",
"StatisticsOfCachedContents": "Статистика кэшированного содержимого пакета NuGet для nuget.abp.io",
"Compact": "Компактный",
"EditSettings": "Изменить настройки",
"CurrentEstimatedSize": "Текущий расчетный размер",
"CurrentEntryCount": "Текущее количество входов",
"TotalHits": "Всего просмотров",
"TotalMisses": "Всего промахов",
"NoResponseFrom": "Нет ответа от",
"ContentCacheSlidingExpirationByDay": "Скользящий срок действия кэша контента по дням",
"MaxDaysForCaching": "Максимальное количество дней для кэширования",
"Enabled": "Включено",
"Menu:NugetPackagesContentCache": "NuGet-кэш",
"NugetPackagesContentCache": "Кэш контента NuGet",
"SlidingExpritionByDayInfo": "Получает или задает время, в течение которого запись кэша может быть неактивной (например, недоступной), прежде чем она будет удалена. ",
"MaxDaysForCachingInfo": "Получает или задает абсолютное время истечения срока действия относительно текущего момента.",
"CurrentEstimatedSizeInfo": "Указывает приблизительную сумму размера содержимого всех пакетов NuGet, находящихся в настоящее время в кеше памяти.",
"CurrentEntryCountInfo": "Указывает количество экземпляров, находящихся в настоящее время в кэше памяти.",
"TotalHitsInfo": "Указывает общее количество промахов кэша. ",
"TotalMissesInfo": "Указывает общее количество попаданий в кэш. ",
"Permission:VersionHistory": "История версий",
"Caches": "Тайники",
"VersionHistories": "История версий",
"Version": "Версия",
"PublishDate": "Дата публикации",
"IsStableVersion": "Стабильная версия",
"IsActive": "Активный",
"NewVersion": "Новая версия",
"VersionHistoryDeletionConfirmationMessage": "Вы уверены, что хотите удалить эту версию?",
"CreateAbpConsultantLogoInfo": "Максимальный размер файла: <b>1 МБ</b> <br/> Поддерживаемые типы файлов: <b>JPG, JPEG, PNG, SVG, WebP</b>",
"UrlCode": "URL-код",
"Clear": "Прозрачный",
"Permission:AbpConsultant": "Консультант АБП",
"Menu:AbpConsultants": "Консультанты АБП",
"CreateAbpConsultant": "Создать консультанта по ABP",
"UrlCodeIsNotAvailable": "URL-код используется другим консультантом ABP.",
"AbpConsultants": "Консультанты АБП",
"AbpConsultant": "Консультант АБП",
"AbpConsultantEdit": "Изменить консультанта ABP",
"AbpConsultantCreate": "Создать консультанта по ABP",
"WhoWeAreItem": "Кто мы",
"FieldIsRequired": "{0} требуется.",
"FieldIsNotValid": " {0} недействителен.",
"InterestedLicenseType": "Заинтересованный тип лицензии",
"MoveWaitList": "Переместить в список ожидания",
"CommunityLinkTitle": "Открыть на сайте сообщества",
"CommunityLink": "Ссылка на сообщество",
"ReloadFromSource": "Перезагрузить из источника",
"ReloadFromSourceConfirmationMessage": "Это сообщение будет обновлено с \"{0}\". ",
"UnitPrice": "Цена за единицу товара",
"OverallDiscountAmount": "Общая сумма скидки",
"DiscountAmount": "Сумма скидки",
"FullChangeHistory": "Полная история изменений",
"Permission:RefreshReleaseLogs": "Обновить журналы выпусков",
"ReleaseLogs": "Журналы релизов",
"AuthorUserName": "Имя пользователя автора",
"Type": "Тип",
"TotalDiscount": "Общая скидка",
"SubTotal": "Промежуточный итог",
"TotalDue": "Общая сумма задолженности",
"QuotationNo": "Номер предложения",
"ValidTill": "Годен до",
"QuotationNote": "Ценовое примечание",
"QuotationTemplate.Address:": "Адрес:",
"QuotationTemplate.VATNo:": "НДС №:",
"QuotationTemplate.Phone:": "Телефон:",
"QuotationTemplate.E-mail:": "Электронная почта:",
"QuotationTemplate.Quotation": "Цитата",
"QuotationTemplate.To": "К",
"QuotationTemplate.Details": "Подробности",
"QuotationTemplate.QuotationNo:": "Цитата",
"QuotationTemplate.IssueDate:": "Дата выпуска:",
"QuotationTemplate.ValidTill:": "Годен до:",
"QuotationTemplate.ValidDays": "{0} дней",
"QuotationTemplate.Description": "Описание",
"QuotationTemplate.UnitPrice": "Цена за единицу товара",
"QuotationTemplate.Qty": "Кол-во",
"QuotationTemplate.Discount": "Скидка",
"QuotationTemplate.Total": "Общий",
"QuotationTemplate.Notes": "Примечания",
"QuotationTemplate.SubTotal:": "Промежуточный итог :",
"QuotationTemplate.Tax/VAT:": "Налог/НДС (%{0}):",
"QuotationTemplate.TotalDiscount:": "Общая скидка :",
"QuotationTemplate.TOTALDUE:": "ВСЕГО К ЗАПЛАТЕ:",
"QuotationTemplate.BankAccount": "Информацию о нашем банковском счете можно найти по адресу {0}.",
"Permission:Raffles": "Розыгрыш",
"Permission:Draw": "Рисовать",
"Menu:Raffles": "Розыгрыши",
"RaffleIsNotDrawable": "Розыгрыш не проводится",
"WinnerCountMustBeGreaterThanZero": "Число победителей должно быть больше нуля.",
"FullDescription": "Полное описание",
"VisibilityStartDate": "Дата начала видимости",
"VisibilityEndDate": "Дата окончания видимости",
"RaffleDate": "Дата розыгрыша",
"SubscriptionCode": "Код подписки",
"GroupCode": "Код группы",
"MaxWinnerCount": "Максимальное количество победителей",
"ReDraw": "Перерисовать",
"EditRaffle": "Редактировать лотерею",
"Raffles": "Розыгрыши",
"CreateARaffle": "Создать лотерею",
"Draw": "Рисовать",
"Enum:RaffleStatus:0": "Активный",
"Enum:RaffleStatus:1": "Следующий",
"Enum:RaffleStatus:2": "Прошлое",
"DrawDone": "Розыгрыш завершен",
"HomePageShowType": "Тип показа домашней страницы",
"None": "Никто",
"Card": "Карта",
"Horizontal": "Горизонтальный",
"Winners": "Победители",
"StartDateMustBeLessThanEndDate": "Дата начала должна быть меньше даты окончания.",
"VisibilityStartDateMustBeLessThanVisibilityEndDate": "Дата начала видимости должна быть меньше даты окончания видимости.",
"StartDateMustBeGreaterThanVisibilityStartDate": "Дата начала должна быть позже даты начала видимости.",
"EndDateMustBeLessThanVisibilityEndDate": "Дата окончания должна быть меньше даты окончания видимости.",
"DrawnDone": "Нарисовано Готово",
"AddColor": "Добавить цвет",
"Colors": "Цвета",
"RemoveColor": "Удалить цвет",
"MaxColorCountWarning": "Вы можете добавить до {0} цветов.",
"MinColorCountWarning": "Вы должны добавить не менее {0} цветов.",
"RaffleDeletionConfirmationMessage": "Вы уверены, что хотите удалить этот розыгрыш?",
"CreateRaffle": "Создать лотерею",
"RemoveImage": "Удалить изображение",
"SuccessfullySaved": "Успешно сохранено",
"Menu:CommunityTalks": "Обсуждения сообщества",
"Menu:Conferences": "Конференции",
"Menu:OtherLiveEvents": "Другие живые события",
"Menu:SponsoredConferences": "Спонсируемые конференции",
"Logo": "Логотип",
"Slug": "Слизень",
"CompanyUrl": "URL компании",
"TalkTitle": "Название доклада",
"AbstractTopic": "Абстрактная тема",
"Bio": "Био",
"LinkedIn": "LinkedIn",
"Github": "GitHub",
"Twitch": "Twitch",
"Youtube": "YouTube",
"Twitter": "Twitter",
"PersonalWebsite": "Персональный сайт",
"VideoId": "Идентификатор видео",
"Order": "Заказ",
"Image1x1": "Изображение 1х1",
"Image16x9": "Изображение 16x9",
"Banner": "Баннер",
"Speaker": "Оратор",
"SessionDate": "Дата сессии",
"AddSession": "Добавить сеанс",
"AddSponsor": "Добавить спонсора",
"SponsorLogo": "Логотип спонсора",
"RegistrationUrl": "URL-адрес регистрации"
} }
} }

7
abp_io/AbpIoLocalization/AbpIoLocalization/Base/Localization/Resources/en.json

@ -230,6 +230,11 @@
"CommunityProfile": "Community Profile", "CommunityProfile": "Community Profile",
"BlogProfile": "Blog Profile", "BlogProfile": "Blog Profile",
"Tickets": "Tickets", "Tickets": "Tickets",
"Videos": "Videos" "Raffles": "Raffles",
"Status": "Status",
"Resources": "Resources",
"Video Courses": "Video Courses",
"Packages": "Packages",
"Trainings": "Trainings"
} }
} }

228
abp_io/AbpIoLocalization/AbpIoLocalization/Base/Localization/Resources/ru.json

@ -3,22 +3,39 @@
"texts": { "texts": {
"Volo.AbpIo.Domain:010004": "Достигнуто максимальное количество участников!", "Volo.AbpIo.Domain:010004": "Достигнуто максимальное количество участников!",
"Volo.AbpIo.Domain:010005": "Достигнуто максимальное количество владельцев!", "Volo.AbpIo.Domain:010005": "Достигнуто максимальное количество владельцев!",
"Volo.AbpIo.Domain:010006": "Этот пользователь уже является владельцем в этой организации!", "Volo.AbpIo.Domain:010006": "Этот пользователь уже является владельцем этой организации!",
"Volo.AbpIo.Domain:010007": "Этот пользователь уже является разработчиком в этой организации!", "Volo.AbpIo.Domain:010007": "Этот пользователь уже является разработчиком в этой организации!",
"Volo.AbpIo.Domain:010008": "Разрешенное количество разработчиков не может быть меньше текущего количества разработчиков!", "Volo.AbpIo.Domain:010008": "Разрешенное количество разработчиков не может быть меньше текущего количества разработчиков!",
"Volo.AbpIo.Domain:010009": "Допустимое количество разработчиков не может быть меньше 0!", "Volo.AbpIo.Domain:010009": "Разрешенное количество разработчиков не может быть меньше 0!",
"Volo.AbpIo.Domain:010010": "Превышено максимальное количество MAC-адресов!", "Volo.AbpIo.Domain:010010": "Превышено максимальное количество Mac-адресов!",
"Volo.AbpIo.Domain:010011": "Персональная лицензия не может иметь более 1 разработчика!", "Volo.AbpIo.Domain:010011": "Персональная лицензия не может иметь более 1 разработчика!",
"Volo.AbpIo.Domain:010012": "Лицензия не может быть продлена через месяц после истечения срока действия лицензии!", "Volo.AbpIo.Domain:010012": "Лицензия не может быть продлена через месяц после истечения срока действия лицензии!",
"Volo.AbpIo.Domain:020001": "Не удалось удалить этот пакет NPM, поскольку пакеты Nuget \"{NugetPackages}\" зависят от этого пакета.", "Volo.AbpIo.Domain:020001": "Не удалось удалить этот пакет NPM, поскольку пакеты Nuget \"{NugetPackages}\" зависят от этого пакета.",
"Volo.AbpIo.Domain:020002": "Не удалось удалить этот пакет NPM, потому что модули \"{Modules}\" используют этот пакет.", "Volo.AbpIo.Domain:020002": "Не удалось удалить этот пакет NPM, поскольку этот пакет используют модули «{Modules}».",
"Volo.AbpIo.Domain:020003": "Не удалось удалить этот пакет NPM, поскольку модули \"{Modules}\" используют этот пакет, а пакеты Nuget \"{NugetPackages}\" зависят от этого пакета.", "Volo.AbpIo.Domain:020003": "Не удалось удалить этот пакет NPM, поскольку модули «{Modules}» используют этот пакет, а пакеты Nuget «{NugetPackages}» зависят от этого пакета.",
"Volo.AbpIo.Domain:020004": "Не удалось удалить этот пакет Nuget, потому что модули \"{Modules}\" используют этот пакет.", "Volo.AbpIo.Domain:020004": "Не удалось удалить этот пакет Nuget, поскольку этот пакет используют модули «{Modules}».",
"Volo.AbpIo.Domain:030000": "Вы уже завершили пробный период.",
"Volo.AbpIo.Domain:030001": "Это название организации уже существует.",
"Volo.AbpIo.Domain:030002": "После активации вы не сможете переключить пробную лицензию в статус «запрошено»!",
"Volo.AbpIo.Domain:030003": "Нет такого статуса!",
"Volo.AbpIo.Domain:030004": "Статус не удалось изменить из-за непредвиденной ошибки!",
"Volo.AbpIo.Domain:030005": "Даты начала и окончания могут быть обновлены, когда пробная лицензия находится в статусе «активировано»!",
"Volo.AbpIo.Domain:030006": "Дата окончания должна быть больше даты начала!",
"Volo.AbpIo.Domain:030007": "Эта пробная лицензия уже активирована!",
"Volo.AbpIo.Domain:030008": "Дату покупки можно установить только при статусе -куплено-!",
"Volo.AbpIo.Domain:030009": "Пользователь не найден!",
"Volo.AbpIo.Domain:030010": "Чтобы приобрести пробную лицензию, вам сначала необходимо активировать пробную лицензию!",
"Volo.AbpIo.Domain:030011": "Вы не можете удалить пробную лицензию после ее приобретения!",
"Volo.AbpIo.Domain:030012": "Пользователь имеет право иметь только 1 бесплатный пробный период. ",
"Volo.AbpIo.Domain:030013": "Пользователь с активной лицензией не может запустить пробную лицензию.",
"Volo.AbpIo.Domain:040000": "Телеметрия уже существует!.",
"Volo.AbpIo.Domain:070000": "Название организации может содержать только латинские буквы, цифры, точки и дефисы!",
"Volo.AbpIo.Domain:070001": "Название компании может содержать только латинские буквы, цифры, точки, пробелы и дефисы!",
"WantToLearn?": "Хотеть учиться?", "WantToLearn?": "Хотеть учиться?",
"ReadyToGetStarted?": "Готовы начать?", "ReadyToGetStarted?": "Готовы начать?",
"JoinOurCommunity": "Присоединяйтесь к нашему сообществу", "JoinOurCommunity": "Присоединяйтесь к нашему сообществу",
"GetStartedUpper": "НАЧАТЬ", "GetStartedUpper": "НАЧАТЬ",
"ForkMeOnGitHub": "Разветвите меня на GitHub", "ForkMeOnGitHub": "Раскошелитесь на GitHub",
"Features": "Функции", "Features": "Функции",
"GetStarted": "Начать", "GetStarted": "Начать",
"Documents": "Документы", "Documents": "Документы",
@ -26,19 +43,198 @@
"ContributionGuide": "Руководство по вкладу", "ContributionGuide": "Руководство по вкладу",
"Blog": "Блог", "Blog": "Блог",
"Commercial": "Коммерческий", "Commercial": "Коммерческий",
"MyAccount": "Мой аккаунт", "MyAccount": "Мой счет",
"Permission:License": "Лицензия", "Permission:License": "Лицензия",
"Permission:UserInfo": "Информация о пользователе", "Permission:UserInfo": "Информация о пользователе",
"SeeDocuments": "См. Документы", "SeeDocuments": "См. документы",
"Samples": "Образцы", "Samples": "Образцы",
"Framework": "Фреймворк", "Framework": "Рамки",
"Support": "Служба поддержки", "Support": "Поддерживать",
"FreeDDDBook": "Бесплатная электронная книга DDD", "FreeDDDBook": "Бесплатная электронная книга DDD",
"New": "Новый", "New": "Новый",
"Volo.AbpIo.Domain:020005": "Год продления лицензии не может быть меньше {MinExtendLicenseYear} лет и больше {MaxExtendLicenseYear} лет.", "Volo.AbpIo.Domain:020005": "Год продления лицензии не может быть меньше {MinExtendLicenseYear} лет и больше {MaxExtendLicenseYear} лет. ",
"TrialLicensePeriodHasExpired": "Срок действия вашей пробной лицензии истек {0} дней назад.", "TrialLicensePeriodHasExpired": "Срок действия пробной лицензии истек {0} дн. назад.",
"TrialLicensePeriodWillExpire": "Срок действия вашей пробной лицензии истечет через {0} дн.", "TrialLicensePeriodWillExpire": "Срок действия пробной лицензии истечет через {0} дн.",
"TrialLicensePeriodExpireToday": "Срок действия вашей пробной лицензии истекает сегодня.", "TrialLicensePeriodExpireToday": "Срок действия пробной лицензии истекает сегодня.",
"PurchaseNow": "Купить сейчас!" "PurchaseNow": "Купить сейчас!",
"LatestReleaseLogs": "Журналы последних выпусков",
"RoadMap": "Дорожная карта",
"FAQ": "Часто задаваемые вопросы",
"SourceCode": "Исходный код",
"SeeAllPosts": "Посмотреть все публикации",
"Contribute": "Способствовать",
"LiveDemo": "Живая демонстрация",
"GetLicense": "Получить лицензию",
"OpenSource": "Открытый источник",
"WebApplication": "Веб приложение",
"MeetTheABP": "Знакомьтесь: ABP",
"CompleteWebDevelopment": "Полная веб-разработка",
"Platform": "Платформа",
"ABPDescription": "Платформа с открытым исходным кодом для разработки веб-приложений для ASP.NET Core. ",
"StrongInfrastructure": "Сильная инфраструктура",
"CompleteArchitecture": "Полная архитектура",
"DeveloperFocused": "Ориентирован на разработчиков",
"ShareYourExperiences": "Поделитесь своим опытом использования ABP Framework",
"LatestPosts": "Последние посты",
"LatestVideos": "Последние видео",
"Views": "Взгляды",
"LearnLatestNewsAboutABPFramework": "Получайте информацию о событиях в ABP, таких как новые выпуски, бесплатные источники, публикации и многое другое.",
"DeveloperTools": "Инструменты разработчика",
"StartupTemplates": "Шаблоны запуска",
"ApplicationModules": "Прикладные модули",
"UI": "пользовательский интерфейс",
"Themes": "Темы",
"Premium": "Премиум",
"PrivacyPolicy": "политика конфиденциальности",
"TermsAndConditions": "Условия",
"WouldLikeToReceiveMarketingMaterials": "Я хотел бы получать маркетинговые материалы, такие как предложения по продуктам",
"JoinOurMarketingNewsletter": "Подпишитесь на нашу маркетинговую рассылку",
"CommunityPrivacyPolicyConfirmation": "Я согласен с Условиями <a class=\"text-white fw-6 text-decoration-underline opacity-50\" href=\"https://commercial.abp.io/Privacy\">политика конфиденциальности</a>.",
"WouldLikeToReceiveNotification": "Я хотел бы получать последние новости с сайтов abp.io.",
"CommercialNewsletterConfirmationMessage": "я согласен <a class=\"text-white fw-6 text-decoration-underline opacity-50\" href=\"https://commercial.abp.io/TermsConditions\">Условия</a> и <a class=\"text-white fw-6 text-decoration-underline opacity-50\" href=\"https://commercial.abp.io/Privacy\">политика конфиденциальности</a>.",
"FreeDDDEBook": "Бесплатная электронная книга DDD",
"AdditionalServices": "Дополнительные услуги",
"Learn": "Учиться",
"AccountOverview": "Обзор учетной записи",
"MyOrganizations": "Мои организации",
"MySupportQuestions": "Мои вопросы о поддержке",
"MyProfile": "Мой профайл",
"Logout": "Выйти",
"Home": "Дом",
"Posts": "Сообщения",
"Videos": "Видео",
"JoinTheABPCommunity": "Присоединяйтесь к сообществу ABP",
"SubmitYourPost": "Отправьте свое сообщение",
"Modules": "Модули",
"Tools": "Инструменты",
"Pricing": "Цены",
"ChangeLogs": "Журналы изменений",
"SubscribeToNewsletter": "Подписаться на рассылку",
"SubscribeToNewsletterDescription": "Получайте информацию о событиях в ABP, таких как новые выпуски, бесплатные источники, публикации и многое другое.",
"EmailAddress": "Адрес электронной почты",
"Subscribe": "Подписаться",
"WelcomeToABP": "Добро пожаловать в ABP",
"EULA": "Лицензионное соглашение",
"ABPCommercialIntroductionMessage": "Готовые модули приложений, расширенные шаблоны запуска, инструменты быстрой разработки приложений, профессиональные темы пользовательского интерфейса и премиум-поддержка.",
"MasteringAbpFrameworkEBook": "Освоение структуры ABP",
"MasteringTheABPFrameworkExplanation": "Эта книга, написанная создателем ABP Framework, поможет вам получить полное представление об этой платформе и современных методах разработки веб-приложений.",
"Speakers": "Динамики",
"PreviousEvents": "Предыдущие события",
"WatchTheEvent": "Посмотреть событие",
"RegisterNow": "Зарегистрироваться",
"ThereIsNoEvent": "Нет никакого события.",
"Events": "События",
"Volo.AbpIo.Domain:080000": "Уже есть купленный товар с названием \"{Name}\"",
"MasteringAbpFrameworkBook": "Книга: Освоение ABP Framework",
"ABPIO-CommonPreferenceDefinition": "Получайте последние новости о платформе ABP, такие как новые публикации, события и многое другое.",
"BuiltOn": "Построен на",
"AbpFramework": "Структура ABP",
"Volo.AbpIo.Domain:080001": "Время начала не может быть больше времени окончания.",
"Enum:BookType:0": "Освоение структуры ABP",
"Enum:PurchasePlatform:0": "Амазонка",
"Enum:PurchasePlatform:1": "Пакет",
"Copied": "Скопировано!",
"CouldNotCopy": "Не удалось скопировать!",
"CopyNotSupportByYourBrowser": "Эта функция не работает в используемом вами браузере.",
"City": "Город",
"ZipCode": "Почтовый индекс",
"Address": "Адрес",
"Homepage": "Домашняя страница",
"Year": "Год",
"Year_Plural": "Годы",
"Copyright": "Авторское право © <a href=\"{0}\" target=\"_blank\">{1}</a>",
"DomainDrivenDesign": "Проектирование, ориентированное на предметную область",
"CrossCuttingConcerns": "Межсекторальные проблемы",
"AbpCommunity": "Сообщество ABP",
"Footer_GithubStarCount": "{0} Звезды на GitHub",
"Footer_NugetDownloadCount": "{0} Загрузки на NuGet",
"AbpDescription": "ABP — это платформа приложений с открытым исходным кодом, ориентированная на разработку веб-приложений на базе AspNet Core. ",
"Layout_AbpFramework_MetaTitle": "Структура ABP | ",
"CommunityTalks_CountdownDays": "Дни",
"CommunityTalks_CountdownHours": "Часы",
"CommunityTalks_CountdownMinutes": "Мин",
"CommunityTalks_CountdownSeconds": "сек.",
"SeePreviousEvents": "См. предыдущие события",
"CookieConsent_Accept": "Принимать",
"CookieConsent_Explanation_1": "Мы используем файлы cookie, чтобы вам было удобнее пользоваться нашим сайтом.",
"CookieConsent_Explanation_2": "Если вы продолжаете просматривать, вы соглашаетесь с нашими <a href=\"@Url.Page(\"/Privacy\")\">Политика конфиденциальности и политика использования файлов cookie.</a>.",
"Error_Page_400_Title": "Возникла проблема с обслуживанием запрошенной страницы.",
"Error_Page_400_Description_1": "Обычно это означает, что при обработке вашего запроса произошла непредвиденная ошибка.",
"Error_Page_400_Description_2": "Если проблема не устранена, свяжитесь с нами по адресу <a href=\"mailto:info@abp.io\">info@abp.io</a> и мы поможем вам продолжить путь.",
"GoToHomepage": "Вернуться на домашнюю страницу",
"Error_Page_404_Title": "Страница не найдена!",
"Error_Page_404_Description_1": "Это не та веб-страница, которую вы ищете.",
"Error_Page_500_Title": "Похоже, что-то пошло не так!",
"Error_Page_500_Description_1": "Мы отслеживаем эти ошибки автоматически, но если проблема не устранена, не стесняйтесь <br /> связаться с нами. ",
"Error_Page_500_Description_2": "Свяжитесь с нами по адресу <a href=\"mailto:info@abp.io\" target=\"_blank\">info@abp.io</a>.",
"Books": "Книги",
"ABPDiscordServer": "Дискорд-сервер ABP",
"ABPCommunityTalks": "Обсуждения сообщества ABP",
"ABPCommunityPosts": "Сообщения сообщества ABP",
"BuyAndGetMonths": "КУПИТЬ 12 МЕСЯЦЕВ, <span>ПОЛУЧИТЕ 14 МЕСЯЦЕВ!</span>",
"GetYourDeal": "Получите свою сделку",
"BuyOrRenewLicense": "Купите или продлите лицензию сейчас и получите 2 дополнительных месяца!",
"BuyOrRenewLicenseToGetExtra2Months": "Купите или продлите лицензию сейчас и получите 2 дополнительных месяца! ",
"HurryUp": "ТОРОПИТЬСЯ!",
"LastDay": "Последний день: {0}",
"BuyNewLicenseBetweenDatesToGetBenefit": "Купите новую лицензию в период с {0} по {1} и получите дополнительные 2 месяца выгоды!",
"CheckAllCommunityTalks": "Проверить все публикации сообщества",
"ReadMore": "Читать далее",
"ContinueReading": "Продолжить чтение",
"Post": "Почта",
"ExploreTheContentsCreatedByTheCoreABPTeamAndTheABPCommunity": "Изучите контент, созданный основной командой ABP и сообществом ABP.",
"WelcomeFallCampaign": "Приветствуем осеннюю кампанию!",
"GiveAwayForNewPurchases": "За новые покупки будет разыграно обучение в классе разработки приложений!",
"BlackFriday": "<strong>ЧЕРНЫЙ</strong> <span>ПЯТНИЦА</span>",
"ValidForExistingCustomers": "Также актуально для <br> Существующие клиенты!",
"CampaignBetweenDates": "От {0} <br>В {1}",
"SaveUpTo": "<span>СОХРАНЯТЬ</span> ВПЛОТЬ ДО<strong>{0}тыс. долларов США</strong>",
"ImplementingDDD": "Реализация предметно-ориентированного проектирования",
"ExploreTheEBook": "Изучите электронную книгу",
"ExploreTheBook": "Изучите книгу",
"ConsultantType": "Тип консультации",
"Expert": "Эксперт ABP",
"Partner": "Партнер ABP",
"Industry": "Промышленность",
"Location": "Расположение",
"Contact": "Контакт",
"Partner_Year": "Год партнерства",
"Info": "Информация",
"SpokenLanguages": "Разговорные языки",
"SocialMedia": "Социальные медиа",
"Activity": "Активность",
"Type": "Тип",
"Contribution": "Вклад",
"WhoWeAre": "Кто мы",
"Icons": "Иконки",
"Url": "URL",
"Icon": "Икона",
"RecentActivities": "Последние действия",
"SpringCampaign": "Добро пожаловать <br>Весенняя распродажа!",
"SpringCampaign2": "<span>Ограниченное <br> Временное предложение!</span>",
"AboutUs": "О нас",
"HowItWorks": "Как это работает?",
"ReleaseNotes": "Примечания к выпуску",
"DetailedChangeNotes": "Подробные примечания к изменениям",
"SeeTrainings": "Посмотреть тренинги",
"NoContent": "Без содержания",
"More": "Более",
"WhyABPIOPlatform": "Почему платформа ABP.IO?",
"AbpStudio": "АBP Студия",
"ExtraMonths": "{0}<span>ДОПОЛНИТЕЛЬНЫЕ МЕСЯЦЫ</span>",
"RSS": "RSS",
"RSSFeed": "Новостная лента",
"Articles": "Статьи",
"Organizations": "Организации",
"ManageAccount": "Управлять счетом",
"CommunityProfile": "Профиль сообщества",
"BlogProfile": "Профиль блога",
"Tickets": "Билеты",
"Raffles": "Розыгрыши",
"Status": "Положение дел",
"Resources": "Ресурсы",
"Video Courses": "Видео курсы",
"Packages": "Пакеты",
"Trainings": "Тренинги"
} }
} }

8
abp_io/AbpIoLocalization/AbpIoLocalization/Blog/Localization/Resources/ru.json

@ -0,0 +1,8 @@
{
"culture": "ru",
"texts": {
"AbpTitle": "Читайте все блог-посты",
"AbpDescription": "ABP - это открытый фреймворк приложений, ориентированный на разработку веб-приложений на базе AspNet Core. Не повторяйте себя, сосредоточьтесь на своем бизнес-коде.",
"AbpDefinition": "Блог ABP по разработке .NET, кроссплатформенные шаблоны приложений ASP.NET, новости, связанные с ABP и многое другое..."
}
}

5
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/ar.json

@ -577,7 +577,7 @@
"Purchase_TrainingPrice": "سعر التدريب", "Purchase_TrainingPrice": "سعر التدريب",
"Purchase_OnboardingTraining": "تدريب مباشر على ABP وتطوير تطبيقات الويب", "Purchase_OnboardingTraining": "تدريب مباشر على ABP وتطوير تطبيقات الويب",
"TotalDeveloperPrice": "إجمالي سعر المطور", "TotalDeveloperPrice": "إجمالي سعر المطور",
"Purchase_PricePerDeveloper": "<span>{0} {1}</span> لكل مطور", "Purchase_PricePerDeveloper": "<span>{0}</span> لكل مطور",
"Purchase_IncludedDeveloperInfo": "{0} {1} يتضمن.", "Purchase_IncludedDeveloperInfo": "{0} {1} يتضمن.",
"Purchase_LicenseExtraDeveloperPurchaseMessage": "رخصة <span class=\"fw-6\">{0} </span> تحتوي على {1} مطور/ين. يمكنك إضافة مطورين إضافيين الآن أو لاحقًا.", "Purchase_LicenseExtraDeveloperPurchaseMessage": "رخصة <span class=\"fw-6\">{0} </span> تحتوي على {1} مطور/ين. يمكنك إضافة مطورين إضافيين الآن أو لاحقًا.",
"StartupTemplates_Page_Title": "عارضات بدء التشغيل", "StartupTemplates_Page_Title": "عارضات بدء التشغيل",
@ -791,6 +791,7 @@
"PrivacyPolicyPageTitle": "سياسة الخصوصية - سياسة ملفات تعريف الارتباط", "PrivacyPolicyPageTitle": "سياسة الخصوصية - سياسة ملفات تعريف الارتباط",
"TermsConditionsPageTitle": "الأحكام والشروط", "TermsConditionsPageTitle": "الأحكام والشروط",
"TrainingsPageTitle": "حزم تدريب ABP", "TrainingsPageTitle": "حزم تدريب ABP",
"ModulesPageTitle": "وحدات تطبيق ABP سابقة البناء" "ModulesPageTitle": "وحدات تطبيق ABP سابقة البناء",
"MultipleOrganizationInfo": "شاهد جميع مؤسساتك"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/cs.json

@ -405,6 +405,7 @@
"WhatHappensWhenLicenseEndsExplanation6": "Již nelze získat <a href=\"{0}\">prémiovou podporu</a>.", "WhatHappensWhenLicenseEndsExplanation6": "Již nelze získat <a href=\"{0}\">prémiovou podporu</a>.",
"WhatHappensWhenLicenseEndsExplanation7": "Pokud chcete i nadále využívat tyto výhody, můžete svou licenci prodloužit (obnovit). Pokud prodloužíte licenci do <strong>{3} dní</strong> po vypršení platnosti licence, budou uplatněny následující slevy: Týmová licence {0}; Obchodní licence {1}; Enterprise Licence {2}.", "WhatHappensWhenLicenseEndsExplanation7": "Pokud chcete i nadále využívat tyto výhody, můžete svou licenci prodloužit (obnovit). Pokud prodloužíte licenci do <strong>{3} dní</strong> po vypršení platnosti licence, budou uplatněny následující slevy: Týmová licence {0}; Obchodní licence {1}; Enterprise Licence {2}.",
"BlazoriseLicense": "Musíme si koupit licenci Blazorise?", "BlazoriseLicense": "Musíme si koupit licenci Blazorise?",
"BlazoriseLicenseExplanation": "Máme dohodu mezi společnostmi Volosoft a Megabit, na základě této dohody je licence Blazorise přibalena k produktům ABP Commercial, proto si naši zákazníci nemusí kupovat další licenci Blazorise." "BlazoriseLicenseExplanation": "Máme dohodu mezi společnostmi Volosoft a Megabit, na základě této dohody je licence Blazorise přibalena k produktům ABP Commercial, proto si naši zákazníci nemusí kupovat další licenci Blazorise.",
"MultipleOrganizationInfo": "Podívejte se na všechny vaše organizace"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/de.json

@ -386,6 +386,7 @@
"ContinueWithNewOrganization": "Weiter mit einer neuen Organisation", "ContinueWithNewOrganization": "Weiter mit einer neuen Organisation",
"RenewLicenseEarly": "Erhalte ich das ganze Jahr, wenn ich meine Lizenz vorzeitig erneuere?", "RenewLicenseEarly": "Erhalte ich das ganze Jahr, wenn ich meine Lizenz vorzeitig erneuere?",
"RenewLicenseEarylExplanation": "Wenn Sie Ihre Lizenz vor dem Ablaufdatum Ihrer Lizenz erneuern, wird Ihr Lizenzablaufdatum um 1 Jahr verlängert. Wenn Ihre Lizenz beispielsweise am {0}-06-06 abläuft und Sie sie am {0}-01-01 erneuern, ist das neue Ablaufdatum der Lizenz der {1}-06-06.", "RenewLicenseEarylExplanation": "Wenn Sie Ihre Lizenz vor dem Ablaufdatum Ihrer Lizenz erneuern, wird Ihr Lizenzablaufdatum um 1 Jahr verlängert. Wenn Ihre Lizenz beispielsweise am {0}-06-06 abläuft und Sie sie am {0}-01-01 erneuern, ist das neue Ablaufdatum der Lizenz der {1}-06-06.",
"BlackFridayDiscount": "Black Friday Rabatt" "BlackFridayDiscount": "Black Friday Rabatt",
"MultipleOrganizationInfo": "Alle Ihre Organisationen anzeigen"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/en-GB.json

@ -110,6 +110,7 @@
"RenewLicenseEarly": "If I renew my license early, will I get the full year?", "RenewLicenseEarly": "If I renew my license early, will I get the full year?",
"RenewLicenseEarylExplanation": "When you renew your license before your license expiry date, 1 year will be added to your license expiry date. For example, if your license expires on {0}-06-06 and you renew it on {0}-01-01, your new license expiry date will be {1}-06-06.", "RenewLicenseEarylExplanation": "When you renew your license before your license expiry date, 1 year will be added to your license expiry date. For example, if your license expires on {0}-06-06 and you renew it on {0}-01-01, your new license expiry date will be {1}-06-06.",
"LicenseTypeNotCorrect": "The license type is not correct!", "LicenseTypeNotCorrect": "The license type is not correct!",
"BlackFridayDiscount": "Black Friday Discount" "BlackFridayDiscount": "Black Friday Discount",
"MultipleOrganizationInfo": "See All Your Organizations"
} }
} }

20
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/en.json

@ -49,7 +49,7 @@
"IndexPageHeroSection": "<span class=\"first-line\">A complete</span><span class=\"second-line\"> web development platform</span><span class=\"third-line\">built-on <img src=\"{0}\" width=\"110\" class=\"ml-1\" /> framework</span>", "IndexPageHeroSection": "<span class=\"first-line\">A complete</span><span class=\"second-line\"> web development platform</span><span class=\"third-line\">built-on <img src=\"{0}\" width=\"110\" class=\"ml-1\" /> framework</span>",
"AbpCommercialShortDescription": "ABP Commercial provides pre-built application modules, rapid application development tooling, professional UI themes, premium support and more.", "AbpCommercialShortDescription": "ABP Commercial provides pre-built application modules, rapid application development tooling, professional UI themes, premium support and more.",
"LiveDemo": "Live Demo", "LiveDemo": "Live Demo",
"LiveDemoLead": "<a href=\"{0}\">{1}</a> using your ABP account, <a href=\"{2}\">{3}</a> to abp.io.<br/>Or fill the form below to create a live demo now", "LiveDemoLead": "<a href=\"{0}\">{1}</a> using your ABP account, <a href=\"{2}\">{3}</a> to abp.io <br/> or fill the form below to create a live demo now",
"ThereIsAlreadyAnAccountWithTheGivenEmailAddress": "There is already an account with the given email address: <b>{0}</b><br/> You can login with your account to proceed.", "ThereIsAlreadyAnAccountWithTheGivenEmailAddress": "There is already an account with the given email address: <b>{0}</b><br/> You can login with your account to proceed.",
"GetLicence": "Get a License", "GetLicence": "Get a License",
"Application": "Application", "Application": "Application",
@ -603,7 +603,7 @@
"Purchase_TrainingPrice": "Training Price", "Purchase_TrainingPrice": "Training Price",
"Purchase_OnboardingTraining": "Onboarding & Web Application Development Live Training", "Purchase_OnboardingTraining": "Onboarding & Web Application Development Live Training",
"TotalDeveloperPrice": "Total Developer Price", "TotalDeveloperPrice": "Total Developer Price",
"Purchase_PricePerDeveloper": "<span>{0} {1}</span> per developer", "Purchase_PricePerDeveloper": "<span>{0}</span> per developer",
"Purchase_IncludedDeveloperInfo": "{0} {1} included.", "Purchase_IncludedDeveloperInfo": "{0} {1} included.",
"Purchase_LicenseExtraDeveloperPurchaseMessage": "The <span class=\"fw-bold\">{0} License</span> includes {1} developers. You can add additional developers.", "Purchase_LicenseExtraDeveloperPurchaseMessage": "The <span class=\"fw-bold\">{0} License</span> includes {1} developers. You can add additional developers.",
"StartupTemplates_Page_Title": "ABP Startup Templates", "StartupTemplates_Page_Title": "ABP Startup Templates",
@ -986,8 +986,8 @@
"Summary": "Summary", "Summary": "Summary",
"TrainingPack": "Training pack", "TrainingPack": "Training pack",
"TrainingPackDiscount": "Training pack discount", "TrainingPackDiscount": "Training pack discount",
"Purchase_OnboardingTraining_Description": "This live training package is valid for a class of 8 students and this discount is only valid when purchased with the new license. <a href=\"{0}\" class=\"text-white\">Learn more <i class=\"fa fa-external-link ms-1\"></i></a>", "Purchase_OnboardingTraining_Description": "This live training is valid for a class of 8 students and this discount is only valid when purchased with the new license. <a href=\"{0}\" class=\"text-white\">Learn more <i class=\"fa fa-external-link ms-1\"></i></a>",
"Purchase_Save": "{0}% <span class=\"save ms-1\">Save {1} {2}</span>", "Purchase_Save": "{0}% <span class=\"save ms-1\">Save {1}</span>",
"RemoveBasket": "Remove from basket", "RemoveBasket": "Remove from basket",
"WhyABPIOPlatform?": "Why <span class=\"gradient-commercial\">ABP.IO Platform</span>?", "WhyABPIOPlatform?": "Why <span class=\"gradient-commercial\">ABP.IO Platform</span>?",
"DocumentAim": "This document aims to answer the big question:", "DocumentAim": "This document aims to answer the big question:",
@ -998,10 +998,10 @@
"CreatingAnEmptySolution": "Creating an Empty Solution", "CreatingAnEmptySolution": "Creating an Empty Solution",
"THEPROBLEM": "THE PROBLEM", "THEPROBLEM": "THE PROBLEM",
"CreatingAnEmptySolution_THEPROBLEM_Description": "Even creating an almost-empty solution is challenging;", "CreatingAnEmptySolution_THEPROBLEM_Description": "Even creating an almost-empty solution is challenging;",
"CreatingAnEmptySolution_THEPROBLEM_Description2": "How do you organize your codebase across projects?", "CreatingAnEmptySolution_THEPROBLEM_Description2": "How do you organize your code-base across projects?",
"CreatingAnEmptySolution_THEPROBLEM_Description3": "What are the layers and how do they interact?", "CreatingAnEmptySolution_THEPROBLEM_Description3": "What are the layers and how do they interact?",
"CreatingAnEmptySolution_THEPROBLEM_Description4": "How do you integrate to 3rd-party library and systems?", "CreatingAnEmptySolution_THEPROBLEM_Description4": "How do you integrate to 3rd-party libraries?",
"CreatingAnEmptySolution_THEPROBLEM_Description5": "How to set up the automated tests?", "CreatingAnEmptySolution_THEPROBLEM_Description5": "How to set up automated tests?",
"ABPSOLUTION": "ABP SOLUTION", "ABPSOLUTION": "ABP SOLUTION",
"CreatingAnEmptySolution_ABPSOLUTION_Description": "ABP provides a well-architected, layered and production-ready <a href=\"https://docs.abp.io/en/abp/latest/Startup-Templates/Application\" target=\"_blank\">startup solution</a> based on the <a href=\"https://docs.abp.io/en/abp/latest/Domain-Driven-Design\" target=\"_blank\">Domain Driven Design</a> principles. The solution also includes a pre-configured unit and integration <a href=\"https://docs.abp.io/en/abp/latest/Testing\" target=\"_blank\">test</a> projects for each layer.", "CreatingAnEmptySolution_ABPSOLUTION_Description": "ABP provides a well-architected, layered and production-ready <a href=\"https://docs.abp.io/en/abp/latest/Startup-Templates/Application\" target=\"_blank\">startup solution</a> based on the <a href=\"https://docs.abp.io/en/abp/latest/Domain-Driven-Design\" target=\"_blank\">Domain Driven Design</a> principles. The solution also includes a pre-configured unit and integration <a href=\"https://docs.abp.io/en/abp/latest/Testing\" target=\"_blank\">test</a> projects for each layer.",
"CommonLibraries": "Common Libraries", "CommonLibraries": "Common Libraries",
@ -1085,6 +1085,10 @@
"MultipleYearDiscount": "Multiple Year Discount", "MultipleYearDiscount": "Multiple Year Discount",
"CampaignDiscountText": "Black Friday Discount", "CampaignDiscountText": "Black Friday Discount",
"CampaignDiscountName": "Black Friday", "CampaignDiscountName": "Black Friday",
"CampaignName:BlackFriday": "Black Friday" "CampaignName:BlackFriday": "Black Friday",
"MultipleOrganizationInfo": "See All Your Organizations",
"AbpStudioBetaAccessInfoTitle": "ABP Studio Beta Access",
"AbpStudioBetaAccessInfoText": "We're thrilled to share with you the <span class=\"text-highlight-white\">beta</span> version of <span class=\"text-highlight-white\">ABP Studio</span>! This release marks a significant milestone in our development journey, and we're eager to gather your feedback to make the application even better.",
"YouAreNotAuthorizedToDownloadStudio": "You are not authorized to download ABP Studio."
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/es.json

@ -386,6 +386,7 @@
"ContinueWithNewOrganization": "Continuar con una nueva organización", "ContinueWithNewOrganization": "Continuar con una nueva organización",
"RenewLicenseEarly": "Si renuevo mi licencia antes, ¿obtendré el año completo?", "RenewLicenseEarly": "Si renuevo mi licencia antes, ¿obtendré el año completo?",
"RenewLicenseEarylExplanation": "Cuando renueve su licencia antes de la fecha de vencimiento de su licencia, se agregará 1 año a la fecha de vencimiento de su licencia. Por ejemplo, si su licencia vence el {0} -06-06 y la renueva el {0} -01-01, la fecha de vencimiento de su nueva licencia será {1} -06-06.", "RenewLicenseEarylExplanation": "Cuando renueve su licencia antes de la fecha de vencimiento de su licencia, se agregará 1 año a la fecha de vencimiento de su licencia. Por ejemplo, si su licencia vence el {0} -06-06 y la renueva el {0} -01-01, la fecha de vencimiento de su nueva licencia será {1} -06-06.",
"BlackFridayDiscount": "Descuento de viernes negro" "BlackFridayDiscount": "Descuento de viernes negro",
"MultipleOrganizationInfo": "Vea todas sus organizaciones"
} }
} }

5
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/fi.json

@ -600,7 +600,7 @@
"Purchase_TrainingPrice": "Koulutuksen hinta", "Purchase_TrainingPrice": "Koulutuksen hinta",
"Purchase_OnboardingTraining": "ABP:n perehdytys ja verkkosovelluskehitys live-koulutus", "Purchase_OnboardingTraining": "ABP:n perehdytys ja verkkosovelluskehitys live-koulutus",
"TotalDeveloperPrice": "Kehittäjän kokonaishinta", "TotalDeveloperPrice": "Kehittäjän kokonaishinta",
"Purchase_PricePerDeveloper": "<span>{0} {1}</span> kehittäjää kohden", "Purchase_PricePerDeveloper": "<span>{0}</span> kehittäjää kohden",
"Purchase_IncludedDeveloperInfo": "{0} {1} mukana.", "Purchase_IncludedDeveloperInfo": "{0} {1} mukana.",
"Purchase_LicenseExtraDeveloperPurchaseMessage": "<span class=\"fw-6\">{0} lisenssi</span> sisältää {1} kehittäjää. Voit lisätä uusia kehittäjiä nyt tai myöhemmin.", "Purchase_LicenseExtraDeveloperPurchaseMessage": "<span class=\"fw-6\">{0} lisenssi</span> sisältää {1} kehittäjää. Voit lisätä uusia kehittäjiä nyt tai myöhemmin.",
"StartupTemplates_Page_Title": "Käynnistysmallit", "StartupTemplates_Page_Title": "Käynnistysmallit",
@ -827,6 +827,7 @@
"ExpirationDate": "Viimeinen käyttöpäivä", "ExpirationDate": "Viimeinen käyttöpäivä",
"SpringCampaignDiscount": "Kevään kampanja-alennus", "SpringCampaignDiscount": "Kevään kampanja-alennus",
"WhyUseAbpIoPlatform": "Miksi minun pitäisi käyttää ABP.IO-alustaa sen sijaan, että luon uuden ratkaisun tyhjästä?", "WhyUseAbpIoPlatform": "Miksi minun pitäisi käyttää ABP.IO-alustaa sen sijaan, että luon uuden ratkaisun tyhjästä?",
"WhyUseAbpIoPlatformFaqExplanation": "Katso <a href=\"https://docs.abp.io/en/commercial/latest/why-abp-io-platform \"> kyseisestä asiakirjasta </a> yksityiskohtainen selitys siitä, miksi ABP.IO Platformin käyttäminen on huomattavasti edullisempaa kuin kaiken tekeminen itse." "WhyUseAbpIoPlatformFaqExplanation": "Katso <a href=\"https://docs.abp.io/en/commercial/latest/why-abp-io-platform \"> kyseisestä asiakirjasta </a> yksityiskohtainen selitys siitä, miksi ABP.IO Platformin käyttäminen on huomattavasti edullisempaa kuin kaiken tekeminen itse.",
"MultipleOrganizationInfo": "Katso kaikki organisaatiosi"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/fr.json

@ -405,6 +405,7 @@
"WhatHappensWhenLicenseEndsExplanation6": "Vous ne pouvez plus bénéficier du <a href=\"{0}\">support premium</a>.", "WhatHappensWhenLicenseEndsExplanation6": "Vous ne pouvez plus bénéficier du <a href=\"{0}\">support premium</a>.",
"WhatHappensWhenLicenseEndsExplanation7": "Vous pouvez prolonger (renouveler) votre licence si vous souhaitez continuer à bénéficier de ces avantages. Si vous prolongez votre licence dans <strong>{3} jours</strong> après l'expiration de votre licence, les remises suivantes seront appliquées : Licence d'équipe {0} ; Licence commerciale {1} ; Licence Entreprise {2}.", "WhatHappensWhenLicenseEndsExplanation7": "Vous pouvez prolonger (renouveler) votre licence si vous souhaitez continuer à bénéficier de ces avantages. Si vous prolongez votre licence dans <strong>{3} jours</strong> après l'expiration de votre licence, les remises suivantes seront appliquées : Licence d'équipe {0} ; Licence commerciale {1} ; Licence Entreprise {2}.",
"BlazoriseLicense": "Faut-il acheter une licence Blazorise ?", "BlazoriseLicense": "Faut-il acheter une licence Blazorise ?",
"BlazoriseLicenseExplanation": "Nous avons conclu un accord entre Volosoft et Megabit, dans le cadre duquel la licence Blazorise est intégrée aux produits ABP Commercial, de sorte que nos clients n'ont pas besoin d'acheter une licence Blazorise supplémentaire." "BlazoriseLicenseExplanation": "Nous avons conclu un accord entre Volosoft et Megabit, dans le cadre duquel la licence Blazorise est intégrée aux produits ABP Commercial, de sorte que nos clients n'ont pas besoin d'acheter une licence Blazorise supplémentaire.",
"MultipleOrganizationInfo": "Voir toutes vos organisations"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/hi.json

@ -404,6 +404,7 @@
"WhatHappensWhenLicenseEndsExplanation6": "अब आप <a href=\"{0}\">प्रीमियम समर्थन</a> प्राप्त नहीं कर सकते।", "WhatHappensWhenLicenseEndsExplanation6": "अब आप <a href=\"{0}\">प्रीमियम समर्थन</a> प्राप्त नहीं कर सकते।",
"WhatHappensWhenLicenseEndsExplanation7": "यदि आप इन लाभों को प्राप्त करना जारी रखना चाहते हैं तो आप अपने लाइसेंस का विस्तार (नवीनीकरण) कर सकते हैं। यदि आप अपना लाइसेंस समाप्त होने के बाद <strong>{3} दिन</strong> के भीतर अपना लाइसेंस बढ़ाते हैं, तो निम्नलिखित छूट लागू होंगी: टीम लाइसेंस {0}; व्यवसाय लाइसेंस {1}; उद्यम लाइसेंस {2}।", "WhatHappensWhenLicenseEndsExplanation7": "यदि आप इन लाभों को प्राप्त करना जारी रखना चाहते हैं तो आप अपने लाइसेंस का विस्तार (नवीनीकरण) कर सकते हैं। यदि आप अपना लाइसेंस समाप्त होने के बाद <strong>{3} दिन</strong> के भीतर अपना लाइसेंस बढ़ाते हैं, तो निम्नलिखित छूट लागू होंगी: टीम लाइसेंस {0}; व्यवसाय लाइसेंस {1}; उद्यम लाइसेंस {2}।",
"BlazoriseLicense": "क्या हमें ब्लेज़ोराइज़ लाइसेंस खरीदने की ज़रूरत है?", "BlazoriseLicense": "क्या हमें ब्लेज़ोराइज़ लाइसेंस खरीदने की ज़रूरत है?",
"BlazoriseLicenseExplanation": "हमारे पास Volosoft और Megabit के बीच एक समझौता है, इस समझौते के साथ Blazorise लाइसेंस को ABP वाणिज्यिक उत्पादों के साथ बंडल किया गया है, इसलिए हमारे ग्राहकों को एक अतिरिक्त Blazorise लाइसेंस खरीदने की आवश्यकता नहीं है।" "BlazoriseLicenseExplanation": "हमारे पास Volosoft और Megabit के बीच एक समझौता है, इस समझौते के साथ Blazorise लाइसेंस को ABP वाणिज्यिक उत्पादों के साथ बंडल किया गया है, इसलिए हमारे ग्राहकों को एक अतिरिक्त Blazorise लाइसेंस खरीदने की आवश्यकता नहीं है।",
"MultipleOrganizationInfo": "अपने सभी संगठन देखें"
} }
} }

5
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/hu.json

@ -601,7 +601,7 @@
"Purchase_TrainingPrice": "Képzési ár", "Purchase_TrainingPrice": "Képzési ár",
"Purchase_OnboardingTraining": "ABP Onboarding és webalkalmazás-fejlesztés élő képzés", "Purchase_OnboardingTraining": "ABP Onboarding és webalkalmazás-fejlesztés élő képzés",
"TotalDeveloperPrice": "Teljes fejlesztői ár", "TotalDeveloperPrice": "Teljes fejlesztői ár",
"Purchase_PricePerDeveloper": "<span>{0} {1}</span> fejlesztőnként", "Purchase_PricePerDeveloper": "<span>{0}</span> fejlesztőnként",
"Purchase_IncludedDeveloperInfo": "{0} {1} tartalmazza.", "Purchase_IncludedDeveloperInfo": "{0} {1} tartalmazza.",
"Purchase_LicenseExtraDeveloperPurchaseMessage": "A(z) <span class=\"fw-6\">{0} licensz</span> {1} fejlesztőt tartalmaz. Hozzáadhat további fejlesztőket most vagy később.", "Purchase_LicenseExtraDeveloperPurchaseMessage": "A(z) <span class=\"fw-6\">{0} licensz</span> {1} fejlesztőt tartalmaz. Hozzáadhat további fejlesztőket most vagy később.",
"StartupTemplates_Page_Title": "Az indítási sablonok", "StartupTemplates_Page_Title": "Az indítási sablonok",
@ -753,6 +753,7 @@
"ExtendPaymentInfoSection_DeveloperPrice": "{0}x További Fejlesztő(k)", "ExtendPaymentInfoSection_DeveloperPrice": "{0}x További Fejlesztő(k)",
"ExtendPaymentInfoSection_DiscountRate": "Kedvezmény: {0}%", "ExtendPaymentInfoSection_DiscountRate": "Kedvezmény: {0}%",
"TotalNetPrice": "Total Net Price", "TotalNetPrice": "Total Net Price",
"BlackFridayDiscount": "Black Friday Kedvezmény" "BlackFridayDiscount": "Black Friday Kedvezmény",
"MultipleOrganizationInfo": "Tekintse meg az összes szervezetét"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/is.json

@ -383,6 +383,7 @@
"TryForFree": "Prófaðu ókeypis", "TryForFree": "Prófaðu ókeypis",
"TrialLicenseExpiredInfo": "Prófunartímabil þitt er útrunnið!", "TrialLicenseExpiredInfo": "Prófunartímabil þitt er útrunnið!",
"CommercialNewsletterConfirmationMessage": "Ég samþykki <a href=\"https://commercial.abp.io/TermsConditions\">skilmálana</a> og <a href=\"https://commercial.abp.io/Privacy\">persónuverndarstefnuna </a>.", "CommercialNewsletterConfirmationMessage": "Ég samþykki <a href=\"https://commercial.abp.io/TermsConditions\">skilmálana</a> og <a href=\"https://commercial.abp.io/Privacy\">persónuverndarstefnuna </a>.",
"BlackFridayDiscount": "Black Friday afsláttur" "BlackFridayDiscount": "Black Friday afsláttur",
"MultipleOrganizationInfo": "Sjá öll samtök þín"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/it.json

@ -404,6 +404,7 @@
"WhatHappensWhenLicenseEndsExplanation6": "Non è più possibile ottenere il <a href=\"{0}\">supporto premium</a>.", "WhatHappensWhenLicenseEndsExplanation6": "Non è più possibile ottenere il <a href=\"{0}\">supporto premium</a>.",
"WhatHappensWhenLicenseEndsExplanation7": "Puoi estendere (rinnovare) la tua licenza se desideri continuare a ottenere questi vantaggi. Se estendi la licenza entro <strong>{3} giorni</strong> dalla scadenza della licenza, verranno applicati i seguenti sconti: Licenza Team {0}; Licenza commerciale {1}; Licenza aziendale {2}.", "WhatHappensWhenLicenseEndsExplanation7": "Puoi estendere (rinnovare) la tua licenza se desideri continuare a ottenere questi vantaggi. Se estendi la licenza entro <strong>{3} giorni</strong> dalla scadenza della licenza, verranno applicati i seguenti sconti: Licenza Team {0}; Licenza commerciale {1}; Licenza aziendale {2}.",
"BlazoriseLicense": "Dobbiamo acquistare la licenza di Blazorise?", "BlazoriseLicense": "Dobbiamo acquistare la licenza di Blazorise?",
"BlazoriseLicenseExplanation": "Abbiamo un accordo tra Volosoft e Megabit, con il quale la licenza di Blazorise viene fornita in bundle con i prodotti commerciali ABP, pertanto i nostri clienti non hanno bisogno di acquistare una licenza Blazorise aggiuntiva." "BlazoriseLicenseExplanation": "Abbiamo un accordo tra Volosoft e Megabit, con il quale la licenza di Blazorise viene fornita in bundle con i prodotti commerciali ABP, pertanto i nostri clienti non hanno bisogno di acquistare una licenza Blazorise aggiuntiva.",
"MultipleOrganizationInfo": "Visualizza tutte le tue organizzazioni"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/nl.json

@ -383,6 +383,7 @@
"TryForFree": "Probeer gratis", "TryForFree": "Probeer gratis",
"TrialLicenseExpiredInfo": "Uw proeflicentieperiode is verlopen!", "TrialLicenseExpiredInfo": "Uw proeflicentieperiode is verlopen!",
"CommercialNewsletterConfirmationMessage": "Ik ga akkoord met de <a href=\"https://commercial.abp.io/TermsConditions\">Algemene voorwaarden</a> en het <a href=\"https://commercial.abp.io/Privacy\">Privacybeleid </a>.", "CommercialNewsletterConfirmationMessage": "Ik ga akkoord met de <a href=\"https://commercial.abp.io/TermsConditions\">Algemene voorwaarden</a> en het <a href=\"https://commercial.abp.io/Privacy\">Privacybeleid </a>.",
"BlackFridayDiscount": "Black Friday korting" "BlackFridayDiscount": "Black Friday korting",
"MultipleOrganizationInfo": "Bekijk al uw organisaties"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/pl-PL.json

@ -383,6 +383,7 @@
"TryForFree": "Wypróbuj za darmo", "TryForFree": "Wypróbuj za darmo",
"TrialLicenseExpiredInfo": "Twoja licencja próbna wygasła!", "TrialLicenseExpiredInfo": "Twoja licencja próbna wygasła!",
"CommercialNewsletterConfirmationMessage": "Wyrażam zgodę na <a href=\"https://commercial.abp.io/TermsConditions\">Warunki</a> i <a href=\"https://commercial.abp.io/Privacy\">Politykę prywatności </a>.", "CommercialNewsletterConfirmationMessage": "Wyrażam zgodę na <a href=\"https://commercial.abp.io/TermsConditions\">Warunki</a> i <a href=\"https://commercial.abp.io/Privacy\">Politykę prywatności </a>.",
"BlackFridayDiscount": "Zniżka Black Friday" "BlackFridayDiscount": "Zniżka Black Friday",
"MultipleOrganizationInfo": "Zobacz wszystkie swoje organizacje"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/pt-BR.json

@ -406,6 +406,7 @@
"WhatHappensWhenLicenseEndsExplanation4": "Você não pode instalar novos módulos e temas adicionados à plataforma comercial da ABP após o término de sua licença.", "WhatHappensWhenLicenseEndsExplanation4": "Você não pode instalar novos módulos e temas adicionados à plataforma comercial da ABP após o término de sua licença.",
"WhatHappensWhenLicenseEndsExplanation5": "Você não pode usar o ABP Suite", "WhatHappensWhenLicenseEndsExplanation5": "Você não pode usar o ABP Suite",
"WhatHappensWhenLicenseEndsExplanation6": "Você não pode mais obter o <a href==\"{0}\">apoio de premium</a>.", "WhatHappensWhenLicenseEndsExplanation6": "Você não pode mais obter o <a href==\"{0}\">apoio de premium</a>.",
"WhatHappensWhenLicenseEndsExplanation7": "Você pode estender (renovar) sua licença se quiser continuar obtendo esses benefícios. Se você estender sua licença dentro de <strong>{3} dias</strong> após a expiração de sua licença, os seguintes descontos serão aplicados: Licença de equipe {0}; Licença Comercial {1}; Licença empresarial {2}." "WhatHappensWhenLicenseEndsExplanation7": "Você pode estender (renovar) sua licença se quiser continuar obtendo esses benefícios. Se você estender sua licença dentro de <strong>{3} dias</strong> após a expiração de sua licença, os seguintes descontos serão aplicados: Licença de equipe {0}; Licença Comercial {1}; Licença empresarial {2}.",
"MultipleOrganizationInfo": "Veja todas as suas organizações"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/ro-RO.json

@ -383,6 +383,7 @@
"TryForFree": "Încearcă pe gratis", "TryForFree": "Încearcă pe gratis",
"TrialLicenseExpiredInfo": "Perioada de licență de probă a expirat!", "TrialLicenseExpiredInfo": "Perioada de licență de probă a expirat!",
"CommercialNewsletterConfirmationMessage": "Sunt de acord cu <a href=\"https://commercial.abp.io/TermsConditions\">Termenii și condițiile</a> și cu <a href=\"https://commercial.abp.io/Privacy\">Politica de confidențialitate </a>.", "CommercialNewsletterConfirmationMessage": "Sunt de acord cu <a href=\"https://commercial.abp.io/TermsConditions\">Termenii și condițiile</a> și cu <a href=\"https://commercial.abp.io/Privacy\">Politica de confidențialitate </a>.",
"BlackFridayDiscount": "Black Friday Discount" "BlackFridayDiscount": "Black Friday Discount",
"MultipleOrganizationInfo": "Vedeți toate organizațiile dvs"
} }
} }

1142
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/ru.json

File diff suppressed because it is too large

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/sk.json

@ -402,6 +402,7 @@
"WhatHappensWhenLicenseEndsExplanation6": "Už nemôžete získať <a href=\"{0}\">prémiovú podporu</a>.", "WhatHappensWhenLicenseEndsExplanation6": "Už nemôžete získať <a href=\"{0}\">prémiovú podporu</a>.",
"WhatHappensWhenLicenseEndsExplanation7": "Ak chcete naďalej využívať tieto výhody, môžete si licenciu predĺžiť (obnoviť). Ak predĺžite svoju licenciu do <strong>30 dní</strong> po vypršaní platnosti licencie, budú sa uplatňovať nasledujúce zľavy: Tímová licencia {0}; Obchodná licencia {1}; Podniková licencia {2}", "WhatHappensWhenLicenseEndsExplanation7": "Ak chcete naďalej využívať tieto výhody, môžete si licenciu predĺžiť (obnoviť). Ak predĺžite svoju licenciu do <strong>30 dní</strong> po vypršaní platnosti licencie, budú sa uplatňovať nasledujúce zľavy: Tímová licencia {0}; Obchodná licencia {1}; Podniková licencia {2}",
"BlazoriseLicense": "Musíme si kúpiť licenciu Blazorise?", "BlazoriseLicense": "Musíme si kúpiť licenciu Blazorise?",
"BlazoriseLicenseExplanation": "Máme dohodu medzi spoločnosťami Volosoft a Megabit, na základe ktorej je licencia Blazorise pribalená k produktom ABP Commercial, preto si naši zákazníci nemusia kupovať ďalšiu licenciu Blazorise." "BlazoriseLicenseExplanation": "Máme dohodu medzi spoločnosťami Volosoft a Megabit, na základe ktorej je licencia Blazorise pribalená k produktom ABP Commercial, preto si naši zákazníci nemusia kupovať ďalšiu licenciu Blazorise.",
"MultipleOrganizationInfo": "Pozrite si všetky vaše organizácie"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/sl.json

@ -383,6 +383,7 @@
"TryForFree": "Poskusite brezplačno", "TryForFree": "Poskusite brezplačno",
"TrialLicenseExpiredInfo": "Vaša preizkusna licenca je potekla!", "TrialLicenseExpiredInfo": "Vaša preizkusna licenca je potekla!",
"CommercialNewsletterConfirmationMessage": "Strinjam se s <a href=\"https://commercial.abp.io/TermsConditions\">pogoji in določili</a> in <a href=\"https://commercial.abp.io/Privacy\">pravilnikom o zasebnosti </a>.", "CommercialNewsletterConfirmationMessage": "Strinjam se s <a href=\"https://commercial.abp.io/TermsConditions\">pogoji in določili</a> in <a href=\"https://commercial.abp.io/Privacy\">pravilnikom o zasebnosti </a>.",
"BlackFridayDiscount": "Popust Black Friday" "BlackFridayDiscount": "Popust Black Friday",
"MultipleOrganizationInfo": "Oglejte si vse svoje organizacije"
} }
} }

5
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/tr.json

@ -610,7 +610,7 @@
"Purchase_TrainingPrice": "Eğitim Fiyatı", "Purchase_TrainingPrice": "Eğitim Fiyatı",
"Purchase_OnboardingTraining": "ABP Onboarding & Web Uygulama Geliştirme Canlı Eğitimi", "Purchase_OnboardingTraining": "ABP Onboarding & Web Uygulama Geliştirme Canlı Eğitimi",
"TotalDeveloperPrice": "Toplam Geliştirici Fiyatı", "TotalDeveloperPrice": "Toplam Geliştirici Fiyatı",
"Purchase_PricePerDeveloper": "<span>{0} {1}</span> geliştirici başına", "Purchase_PricePerDeveloper": "<span>{0}</span> geliştirici başına",
"Purchase_IncludedDeveloperInfo": "{0} {1} dahil.", "Purchase_IncludedDeveloperInfo": "{0} {1} dahil.",
"Purchase_LicenseExtraDeveloperPurchaseMessage": "<span class=\"fw-6\">{0} lisansı</span> {1} geliştirici(ler) içerir. Şimdi veya daha sonra ek geliştiriciler ekleyebilirsiniz.", "Purchase_LicenseExtraDeveloperPurchaseMessage": "<span class=\"fw-6\">{0} lisansı</span> {1} geliştirici(ler) içerir. Şimdi veya daha sonra ek geliştiriciler ekleyebilirsiniz.",
"StartupTemplates_Page_Title": "ABP Başlangıç Şablonları", "StartupTemplates_Page_Title": "ABP Başlangıç Şablonları",
@ -841,6 +841,7 @@
"OneCodeBaseMultipleDevices": "Tek Kod Tabanı, Birden Çok Cihaz", "OneCodeBaseMultipleDevices": "Tek Kod Tabanı, Birden Çok Cihaz",
"OneCodeBaseMultipleDevices_Description": "ABP Mobil uygulamaları çapraz platformdur. iOS ve Android cihazlara yüklenmeye ve çalıştırılmaya hazırdırlar ve tek bir kod tabanı kullanarak farklı form faktörlerine uyum sağlarlar. Geliştiricilerin kullanıcı arayüzünü ve ön uç kodunu yalnızca bir kez oluşturması gerekir, desteklemek istediğiniz her cihaz için kodu uyarlamanıza gerek yoktur.", "OneCodeBaseMultipleDevices_Description": "ABP Mobil uygulamaları çapraz platformdur. iOS ve Android cihazlara yüklenmeye ve çalıştırılmaya hazırdırlar ve tek bir kod tabanı kullanarak farklı form faktörlerine uyum sağlarlar. Geliştiricilerin kullanıcı arayüzünü ve ön uç kodunu yalnızca bir kez oluşturması gerekir, desteklemek istediğiniz her cihaz için kodu uyarlamanıza gerek yoktur.",
"ComesWithTheSourceCode": "Kaynak Koduyla Birlikte Geliyor", "ComesWithTheSourceCode": "Kaynak Koduyla Birlikte Geliyor",
"ComesWithTheSourceCode_Description": "Mobil uygulamalar kaynak koduyla birlikte sağlanır. Marka yönergelerini karşılamak için uygulamalarınızın UX/UI'sini kolayca özelleştirin." "ComesWithTheSourceCode_Description": "Mobil uygulamalar kaynak koduyla birlikte sağlanır. Marka yönergelerini karşılamak için uygulamalarınızın UX/UI'sini kolayca özelleştirin.",
"MultipleOrganizationInfo": "Tüm Organizasyonlarınızı Görün"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/vi.json

@ -383,6 +383,7 @@
"TryForFree": "Thử miễn phí", "TryForFree": "Thử miễn phí",
"TrialLicenseExpiredInfo": "Thời gian cấp phép dùng thử của bạn đã hết hạn!", "TrialLicenseExpiredInfo": "Thời gian cấp phép dùng thử của bạn đã hết hạn!",
"CommercialNewsletterConfirmationMessage": "Tôi đồng ý với <a href=\"https://commercial.abp.io/TermsConditions\"> Điều khoản & điều kiện </a> và <a href=\"https://commercial.abp.io/Privacy\"> Chính sách quyền riêng tư </a>.", "CommercialNewsletterConfirmationMessage": "Tôi đồng ý với <a href=\"https://commercial.abp.io/TermsConditions\"> Điều khoản & điều kiện </a> và <a href=\"https://commercial.abp.io/Privacy\"> Chính sách quyền riêng tư </a>.",
"BlackFridayDiscount": "Giảm giá Black Friday" "BlackFridayDiscount": "Giảm giá Black Friday",
"MultipleOrganizationInfo": "Xem tất cả các tổ chức của bạn"
} }
} }

5
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/zh-Hans.json

@ -600,7 +600,7 @@
"Purchase_TrainingPrice": "培训价格", "Purchase_TrainingPrice": "培训价格",
"Purchase_OnboardingTraining": "ABP 熟悉使用和 Web 应用程序开发现场培训", "Purchase_OnboardingTraining": "ABP 熟悉使用和 Web 应用程序开发现场培训",
"TotalDeveloperPrice": "开发商总价", "TotalDeveloperPrice": "开发商总价",
"Purchase_PricePerDeveloper": "<span>{0} {1}</span> 每个开发者", "Purchase_PricePerDeveloper": "<span>{0}</span> 每个开发者",
"Purchase_IncludedDeveloperInfo": "{0} {1} 包括在内。", "Purchase_IncludedDeveloperInfo": "{0} {1} 包括在内。",
"Purchase_LicenseExtraDeveloperPurchaseMessage": "<span class=\"fw-6\">{0} 许可</span> 包含 {1} 个开发者。 您可以现在或以后添加其他开发人员。", "Purchase_LicenseExtraDeveloperPurchaseMessage": "<span class=\"fw-6\">{0} 许可</span> 包含 {1} 个开发者。 您可以现在或以后添加其他开发人员。",
"StartupTemplates_Page_Title": "ABP启动模板", "StartupTemplates_Page_Title": "ABP启动模板",
@ -842,6 +842,7 @@
"BlazoriseSupportExplanation4": "如果您有有效的ABP商业版许可证,您还将拥有Blazorise PRO许可证。您可以在<a href=\"https://blazorise.com/support/user/manage/license\" rel=\"nofollow\">blazorise.com/support/user/manage/license</a>获取您的Blazorise许可密钥。", "BlazoriseSupportExplanation4": "如果您有有效的ABP商业版许可证,您还将拥有Blazorise PRO许可证。您可以在<a href=\"https://blazorise.com/support/user/manage/license\" rel=\"nofollow\">blazorise.com/support/user/manage/license</a>获取您的Blazorise许可密钥。",
"BlazoriseSupportExplanation5": "您可以在support网站上发布您的问题,并为您的应用程序生成一个产品令牌。", "BlazoriseSupportExplanation5": "您可以在support网站上发布您的问题,并为您的应用程序生成一个产品令牌。",
"ExtraQuestionCreditsFaqTitle": "我可以购买额外的问题支持次数吗?", "ExtraQuestionCreditsFaqTitle": "我可以购买额外的问题支持次数吗?",
"ExtraQuestionCreditsFaqExplanation": "是的,您可以购买额外的问题支持次数,请发送电子邮件至<a href=\"mailto:info@abp.io\">info@abp.io</a>,并提供您的组织名称。以下是额外问题支持次数的价格列表: <ul><li>50次问题 $999</li><li>25次问题 $625</li><li>15次问题 $450</li></ul>" "ExtraQuestionCreditsFaqExplanation": "是的,您可以购买额外的问题支持次数,请发送电子邮件至<a href=\"mailto:info@abp.io\">info@abp.io</a>,并提供您的组织名称。以下是额外问题支持次数的价格列表: <ul><li>50次问题 $999</li><li>25次问题 $625</li><li>15次问题 $450</li></ul>",
"MultipleOrganizationInfo": "查看您的所有组织"
} }
} }

3
abp_io/AbpIoLocalization/AbpIoLocalization/Commercial/Localization/Resources/zh-Hant.json

@ -408,6 +408,7 @@
"WhatHappensWhenLicenseEndsExplanation6": "您無法再獲得<a href=\"{0}\">高級支持</a>。", "WhatHappensWhenLicenseEndsExplanation6": "您無法再獲得<a href=\"{0}\">高級支持</a>。",
"WhatHappensWhenLicenseEndsExplanation7": "如果您想繼續獲得這些好處,您可以延長(更新)您的許可證。如果您在許可到期後 <strong>{3} 天</strong> 內延長許可,將應用以下折扣:團隊許可 {0};營業執照{1};企業許可證{2}。", "WhatHappensWhenLicenseEndsExplanation7": "如果您想繼續獲得這些好處,您可以延長(更新)您的許可證。如果您在許可到期後 <strong>{3} 天</strong> 內延長許可,將應用以下折扣:團隊許可 {0};營業執照{1};企業許可證{2}。",
"DoesTheSubscriptionRenewAutomatically": "許可會自動續費嗎?", "DoesTheSubscriptionRenewAutomatically": "許可會自動續費嗎?",
"DoesTheSubscriptionRenewAutomaticallyExplanation": "ABP 商業版沒有自動續費的計費模式。因此,在您的許可期結束時,<strong>您的訂閱將不會自動續訂</strong>。如果您希望繼續享受ABP商業版的服務,請在<a href=\"/my-organizations\">組織管理頁面</a>手動進行續費操作。如果您擁有多個組織,您可以點擊即將到期的組織上的\"管理\"按鈕,然後點擊\"立即續費\"按鈕來續訂您的許可。您還可以查看<a href=\"/faq#what-happens-when-license-ends\">許可到期後會發生什麼?</a>部分了解更多信息。" "DoesTheSubscriptionRenewAutomaticallyExplanation": "ABP 商業版沒有自動續費的計費模式。因此,在您的許可期結束時,<strong>您的訂閱將不會自動續訂</strong>。如果您希望繼續享受ABP商業版的服務,請在<a href=\"/my-organizations\">組織管理頁面</a>手動進行續費操作。如果您擁有多個組織,您可以點擊即將到期的組織上的\"管理\"按鈕,然後點擊\"立即續費\"按鈕來續訂您的許可。您還可以查看<a href=\"/faq#what-happens-when-license-ends\">許可到期後會發生什麼?</a>部分了解更多信息。",
"MultipleOrganizationInfo": "查看您的所有組織"
} }
} }

2
abp_io/AbpIoLocalization/AbpIoLocalization/Community/Localization/Resources/en.json

@ -254,7 +254,7 @@
"Videos({0})": "Videos ({0})", "Videos({0})": "Videos ({0})",
"LatestArticles": "Latest Articles", "LatestArticles": "Latest Articles",
"RaffleHeader": "Hello ABP Community Member!", "RaffleHeader": "Hello ABP Community Member!",
"RafflesInfo": "<br>This is the raffle page dedicated to show our appreciation towards you for being an active Community Member. We do <a target=\"_blank\" class=\"fw-6 \" href=\"https://community.abp.io/events\">ABP Community Talks</a> <a target=\"_blank\" class=\"fw-6\" href=\"https://abp.io/conference/2023\">,ABP .NET Conference</a>, attend or sponsor to the .NET-related events in which we give away some gifts. <br><br>You can follow this page to see the upcoming raffles, attend them, or see previous raffles we draw including the winners. <br><br>Thank you for being an active member! See you in the upcoming raffles.", "RafflesInfo": "<br>This is the raffle page dedicated to show our appreciation towards you for being an active Community Member. We do <a class=\"fw-6 \" href=\"https://community.abp.io/events\">ABP Community Talks</a> <a target=\"_blank\" class=\"fw-6\" href=\"https://abp.io/conference/2023\">,ABP .NET Conference</a>, attend or sponsor to the .NET-related events in which we give away some gifts. <br><br>You can follow this page to see the upcoming raffles, attend them, or see previous raffles we draw including the winners. <br><br>Thank you for being an active member! See you in the upcoming raffles.",
"RafflesInfoTitle": "ABP Community <span class=\"gradient-community\">Raffles</span>" "RafflesInfoTitle": "ABP Community <span class=\"gradient-community\">Raffles</span>"
} }
} }

127
abp_io/AbpIoLocalization/AbpIoLocalization/Community/Localization/Resources/ru.json

@ -13,7 +13,6 @@
"Status": "Положение дел", "Status": "Положение дел",
"ContentSource": "Источник контента", "ContentSource": "Источник контента",
"Details": "Подробности", "Details": "Подробности",
"Url": "URL",
"Title": "Заголовок", "Title": "Заголовок",
"CreationTime": "Время создания", "CreationTime": "Время создания",
"Save": "Сохранить", "Save": "Сохранить",
@ -27,25 +26,26 @@
"ContributeAbpCommunity": "Внесите свой вклад в сообщество ABP", "ContributeAbpCommunity": "Внесите свой вклад в сообщество ABP",
"SubmitYourPost": "Отправьте свой пост", "SubmitYourPost": "Отправьте свой пост",
"ContributionGuide": "Руководство по вкладу", "ContributionGuide": "Руководство по вкладу",
"BugReport": "Сообщение об ошибке",
"SeeAllPosts": "Просмотреть все сообщения",
"WelcomeToABPCommunity!": "Добро пожаловать в сообщество ABP!",
"MyProfile": "Мой профайл", "MyProfile": "Мой профайл",
"MyOrganizations": "Мои организации", "MyOrganizations": "Мои организации",
"BugReport": "Отчет об ошибке",
"SeeAllPosts": "Посмотреть все публикации",
"WelcomeToABP": "Добро пожаловать в АБП",
"EmailNotValid": "Пожалуйста, введите действительный адрес электронной почты.", "EmailNotValid": "Пожалуйста, введите действительный адрес электронной почты.",
"FeatureRequest": "Запрос функции", "FeatureRequest": "Запрос функции",
"CreatePostTitleInfo": "Название сообщения, которое будет отображаться в списке сообщений.", "CreatePostTitleInfo": "Название сообщения, которое будет отображаться в списке сообщений.",
"CreatePostSummaryInfo": "Краткое изложение сообщения, которое будет отображаться в списке сообщений.", "CreatePostSummaryInfo": "Краткое изложение сообщения, которое будет отображаться в списке сообщений.",
"CreatePostCoverInfo": "Для создания эффектной статьи добавьте фото на обложке. Загрузите изображения с соотношением сторон 16: 9 для наилучшего просмотра. Максимальный размер файла: 1 МБ.",
"ThisExtensionIsNotAllowed": "Это расширение не разрешено.", "ThisExtensionIsNotAllowed": "Это расширение не разрешено.",
"TheFileIsTooLarge": "Файл слишком большой.", "TheFileIsTooLarge": "Файл слишком большой.",
"GoToThePost": "Перейти к статье", "GoToThePost": "Перейти к статье",
"Contribute": "Делать вклад", "Contribute": "Делать вклад",
"GoToTheVideo": "Перейти к видео",
"OverallProgress": "Общий прогресс", "OverallProgress": "Общий прогресс",
"Done": "Выполнено", "Done": "Выполнено",
"Open": "Открытым", "Open": "Открытым",
"Closed": "Закрыто", "Closed": "Закрыто",
"LatestQuestionOnThe": "Последний вопрос по", "LatestQuestionOnThe": "Последний вопрос по",
"RecentQuestionFrom": "Недавний вопрос от {0}",
"Stackoverflow": "Переполнение стека", "Stackoverflow": "Переполнение стека",
"Votes": "голосов", "Votes": "голосов",
"Answer": "Отвечать", "Answer": "Отвечать",
@ -91,6 +91,8 @@
"AllPostRequests": "Просмотреть все запросы статей", "AllPostRequests": "Просмотреть все запросы статей",
"SubscribeToTheNewsletter": "Подпишитесь на рассылку новостей", "SubscribeToTheNewsletter": "Подпишитесь на рассылку новостей",
"NewsletterEmailDefinition": "Получайте информацию о событиях в ABP, например о новых выпусках, бесплатных источниках, статьях и многом другом.", "NewsletterEmailDefinition": "Получайте информацию о событиях в ABP, например о новых выпусках, бесплатных источниках, статьях и многом другом.",
"ArticleRequestsDescription": "Хотите увидеть здесь конкретный контент? ",
"LatestContentRequests": "Последние запросы контента",
"NoThanks": "Нет, спасибо", "NoThanks": "Нет, спасибо",
"MaybeLater": "Может быть позже", "MaybeLater": "Может быть позже",
"JoinOurPostNewsletter": "Подпишитесь на нашу новостную рассылку статей", "JoinOurPostNewsletter": "Подпишитесь на нашу новостную рассылку статей",
@ -143,6 +145,119 @@
"Volo.AbpIo.Domain:060001": "Исходный URL (\"{PostUrl}\") не является URL-адресом Github", "Volo.AbpIo.Domain:060001": "Исходный URL (\"{PostUrl}\") не является URL-адресом Github",
"Volo.AbpIo.Domain:060002": "Контент статьи недоступен на ресурсе Github (\"{PostUrl}\").", "Volo.AbpIo.Domain:060002": "Контент статьи недоступен на ресурсе Github (\"{PostUrl}\").",
"Volo.AbpIo.Domain:060003": "Контент статьи не найден!", "Volo.AbpIo.Domain:060003": "Контент статьи не найден!",
"IConsentToMedium": "Я даю согласие на публикацию этого поста на https://medium.com/volosoft." "SeeMore": "Узнать больше",
"JoinTheABPCommunity": "Присоединяйтесь к сообществу АБП",
"ABPCommunityTalks": "Обсуждения сообщества ABP",
"LiveDemo": "Живая демонстрация",
"GetLicense": "Получить лицензию",
"GetStarted": "Начать",
"SourceCode": "Исходный код",
"LeaveComment": "Оставьте комментарий",
"ShowMore": "Показать больше",
"NoPublishedPostsYet": "Опубликованных постов пока нет.",
"Name": "Имя",
"Surname": "Фамилия",
"WebSite": "Веб-сайт",
"FullURL": "Полный URL-адрес",
"JobTitle": "Должность",
"Prev": "Предыдущий",
"Previous": "Предыдущий",
"Next": "Следующий",
"Share": "Делиться",
"SortBy": "Сортировать по",
"NoPublishedEventsYet": "Опубликованных событий пока нет.",
"SubscribeYoutubeChannel": "Подпишитесь на канал Youtube",
"Enum:EventType:0": "Переговоры",
"MemberNotPublishedPostYet": "Этот участник еще не опубликовал ни одного сообщения.",
"TimeAgo": "{0} назад",
"Discord_Page_JoinCommunityMessage": "Присоединяйтесь к сообществу ABP Discord",
"Discord_Page_Announce": "Мы рады анонсировать Discord-сервер сообщества ABP!",
"Discord_Page_Description_1": "Сообщество ABP росло с первого дня. ",
"Discord_Page_Description_2": "Сервер Discord сообщества ABP — это место, где вы можете продемонстрировать свои творения с использованием ABP Framework, поделиться советами, которые вам помогли, узнать последние новости и объявления об ABP Framework, просто пообщаться с членами сообщества для обмена идеями и весело провести время!",
"Discord_Page_Description_3": "Этот сервер Discord сообщества ABP является официальным, и основная команда ABP присутствует на сервере для мониторинга.",
"Discord_Page_JoinToServer": "Присоединяйтесь к Discord-серверу ABP",
"Events_Page_MetaTitle": "Мероприятия сообщества ABP",
"Events_Page_MetaDescription": "Живые выступления, проводимые командой ABP, представляют собой случайные сеансы, наполненные контентом сообщества, демонстрациями и вопросами.",
"Events_Page_Title": "АДП<span class=\"gradient-community\"> Сообщество</span> Переговоры",
"Members_Page_WritingFromUser": "Прочтите статьи от {0} в сообществе ABP.",
"Post_Create_Page_MetaTitle": "Новый пост",
"Post_Create_Page_MetaDescription": "Создайте публикацию, чтобы поделиться своим опытом работы с платформой ABP и внести свой вклад в сообщество ABP.",
"Post_Create_Page_CreateNewPost": "Создать новый пост",
"Post_Index_Page_MetaDescription": "Цель сообщества ABP — создать среду для участия разработчиков, использующих структуру ABP.",
"Layout_Title": "{0} | ",
"Layout_MetaDescription": "Центр ABP Framework, .NET и разработки программного обеспечения. ",
"Index_Page_CommunityIntroduction": "Это центр ABP Framework, .NET и разработки программного обеспечения. ",
"TagsInArticle": "Теги в статье",
"IConsentToMedium": "Я даю согласие на публикацию данного поста на https://medium.com/volosoft.",
"SearchResultsFor": "Результаты поиска для <span class=\"fw-bold\">\"{0}\"</span>",
"SeeMoreVideos": "Посмотреть больше видео",
"DiscordPageTitle": "Discord-сообщество ABP",
"ViewVideo": "Посмотреть видео",
"AbpCommunityTitleContent": "Сообщество ABP — платформа ABP с открытым исходным кодом",
"CommunitySlogan": "Уникальная общественная платформа для <span class=\"d-inline-block d-md-block gradient-community\">Любители АБП</span>",
"RaffleIsNotActive": "Розыгрыш не активен",
"YouAreAlreadyJoinedToThisRaffle": "Вы уже участвуете в этом розыгрыше",
"InvalidSubscriptionCode": "Неверный код подписки",
"Raffle:{0}": "Розыгрыш: {0}",
"Join": "Присоединиться",
"Leave": "Оставлять",
"LoginToJoin": "Войдите, чтобы присоединиться",
"ToEnd:": "В конец:",
"ToStart:": "Начать:",
"days": "дни",
"hrs": "часы",
"min": "мин",
"sec": "сек",
"Winners": "Победители",
"To{0}LuckyWinners": "счастливчикам ({0})",
"ActiveRaffles": "Активный <span class=\"gradient-community\">Розыгрыши</span>",
"UpcomingRaffles": "Предстоящие <span class=\"gradient-community\">Розыгрыши</span>",
"CompletedRaffles": "Завершенный <span class=\"gradient-community\">Розыгрыши</span>",
"NoActiveRaffleTitle": "На данный момент активной лотереи нет.",
"NoActiveRaffleDescription": "На данный момент активной лотереи нет.",
"RaffleSubscriptionCodeInputMessage": "Для этой лотереи требуется регистрационный код. ",
"RaffleSubscriptionCodeInputErrorMessage": "Регистрационный код неверен. ",
"GoodJob!": "Хорошая работа!",
"RaffleJoinSuccessMessage": "Вы успешно зарегистрированы для участия в розыгрыше. ",
"RaffleLoginAndRegisterMessage": "Вам необходимо войти в систему, чтобы принять участие в розыгрыше. ",
"Ok": "Хорошо",
"SeeDetails": "Смотрите подробности",
"WaitingForTheDraw": "Ждем розыгрыша",
"AllAttendees": "Все участники",
"SeeRaffleDetail": "См. подробную информацию о розыгрыше",
"SeeRaffle": "Посмотреть лотерею",
"ParticipationIsComplete!": "Участие завершено!",
"ABPCoreDevelopmentTeam": "Основная группа разработчиков ABP",
"RegisterTheEvent": "Зарегистрировать мероприятие",
"GoToConferencePage": "Перейти на страницу конференции",
"BuyTicket": "Купить билет",
"SeeEvent": "См. событие",
"PreviousEvents": "<span class=\"text-secondary\">Предыдущий</span> События",
"OtherLiveEvents": "Другие живые события",
"SponsoredConferences": "Спонсируемые конференции",
"SponsoredConferencesDescription": "Для нас большая честь поддерживать сообщества .NET и мероприятия для разработчиков программного обеспечения.",
"UpcomingEvents": "<span class=\"text-info\">Предстоящие</span> События",
"UpcomingCommunityTalkEventDescription": "Живые выступления, проводимые командой ABP, представляют собой случайные сеансы, наполненные контентом сообщества, демонстрациями и вопросами.",
"UpcomingConferenceEventDescription": "Конференция ABP .NET — это виртуальное мероприятие, на котором сообщество разработчиков .NET может собраться вместе и послушать доклады о мире .NET, общих практиках разработки программного обеспечения и ABP Framework с открытым исходным кодом.",
"LastOneYear": "Последний 1 год",
"AllTimes": "Все время",
"TopContributors": "Лучшие участники",
"{0}Posts": "{0} сообщений",
"LATESTPOSTS": "ПОСЛЕДНИЕ ЗАПИСИ",
"NoContributorsFound": "Соавторы не найдены!",
"LatestPost": "Последний пост",
"MEMBERSINCE{0}": "УЧАСТНИК С {0}",
"CopyLink": "Копировать ссылку",
"ShareOnTwitter": "Поделиться в Твиттере",
"ShareOnLinkedIn": "Поделиться в LinkedIn",
"MoreFrom{0}": "Еще от {0}",
"SeeAllFrom{0}": "Посмотреть все из {0}",
"MostWatched": "Самые просматриваемые",
"Articles({0})": "Статьи ({0})",
"Videos({0})": "Видео ({0})",
"LatestArticles": "Последние статьи",
"RaffleHeader": "Привет, участник сообщества ABP!",
"RafflesInfo": "<br>Эта страница розыгрыша посвящена тому, чтобы выразить нашу признательность вам за то, что вы являетесь активным членом сообщества. <a target=\"_blank\" class=\"fw-6 \" href=\"https://community.abp.io/events\">Обсуждения сообщества ABP</a> <a target=\"_blank\" class=\"fw-6\" href=\"https://abp.io/conference/2023\">,Конференция ABP .NET</a>, посещать или спонсировать мероприятия, связанные с .NET, на которых мы раздаем подарки. <br><br>Вы можете подписаться на эту страницу, чтобы увидеть предстоящие розыгрыши, посетить их или просмотреть предыдущие розыгрыши, которые мы проводим, включая победителей. <br><br>Спасибо за активное участие! ",
"RafflesInfoTitle": "Сообщество АБП <span class=\"gradient-community\">Розыгрыши</span>"
} }
} }

9
abp_io/AbpIoLocalization/AbpIoLocalization/Docs/Localization/Resources/ru.json

@ -0,0 +1,9 @@
{
"culture": "ru",
"texts": {
"Buy": "Купить",
"SeeBookDetails": "См. сведения о книге",
"MasteringAbpFrameworkEBookDescription": "Эта книга поможет вам получить полное представление о инфраструктуре и современных методах разработки веб-приложений.",
"Feedback": "Обратная связь"
}
}

4
abp_io/AbpIoLocalization/AbpIoLocalization/Www/Localization/Resources/en.json

@ -115,7 +115,7 @@
"DependencyInjection": "Dependency Injection", "DependencyInjection": "Dependency Injection",
"DependencyInjectionByConventions": "Dependency Injection by Conventions", "DependencyInjectionByConventions": "Dependency Injection by Conventions",
"ABPCLIExplanation": "ABP CLI (Command Line Interface) is a command line tool to automate some common operations for ABP based solutions.", "ABPCLIExplanation": "ABP CLI (Command Line Interface) is a command line tool to automate some common operations for ABP based solutions.",
"ModularityExplanation": "ABP provides a complete infrastructure to build your own application modules that may have entities, services, database integration, APIs, UI components and so on..", //TODO: strong "your own application modules",- "ModularityExplanation": "ABP provides a complete infrastructure to build your own application modules that may have entities, services, database integration, APIs, UI components and so on..",
"MultiTenancyExplanation": "ABP framework doesn't only support developing multi-tenant applications, but also makes your code mostly unaware of the multi-tenancy.", "MultiTenancyExplanation": "ABP framework doesn't only support developing multi-tenant applications, but also makes your code mostly unaware of the multi-tenancy.",
"MultiTenancyExplanation2": "Can automatically determine the current tenant, isolate data of different tenants from each other.", "MultiTenancyExplanation2": "Can automatically determine the current tenant, isolate data of different tenants from each other.",
"MultiTenancyExplanation3": "Supports single database, database per tenant and hybrid approaches.", "MultiTenancyExplanation3": "Supports single database, database per tenant and hybrid approaches.",
@ -438,7 +438,7 @@
"CoolestCompaniesUseABPFramework": "Coolest Companies Use <span class=\"fw-bold\">ABP Framework</span>", "CoolestCompaniesUseABPFramework": "Coolest Companies Use <span class=\"fw-bold\">ABP Framework</span>",
"Index_Page_Testimonial_1": "ABP Framework is not just a tool but a catalyst that has accelerated my growth as a developer. It has made it possible for me to build new features faster than ever before, reminiscent of the experiences of other users. The unified coding pattern has streamlined my projects, giving me more time to focus on creating rather than troubleshooting.\nI would say the ABP Framework has been the cornerstone of my early professional journey. It has facilitated my transition from an aspiring developer to a confident professional ready to make a mark in the software world. I am looking forward to the exciting projects that await me, knowing that ABP will be there to guide me. It is more than just a product; it's a partner in success.", "Index_Page_Testimonial_1": "ABP Framework is not just a tool but a catalyst that has accelerated my growth as a developer. It has made it possible for me to build new features faster than ever before, reminiscent of the experiences of other users. The unified coding pattern has streamlined my projects, giving me more time to focus on creating rather than troubleshooting.\nI would say the ABP Framework has been the cornerstone of my early professional journey. It has facilitated my transition from an aspiring developer to a confident professional ready to make a mark in the software world. I am looking forward to the exciting projects that await me, knowing that ABP will be there to guide me. It is more than just a product; it's a partner in success.",
"Index_Page_Testimonial_2": "ABP Framework is not only a framework, it is also a guidance for project development/management, because it provides DDD, GenericRepository, DI, Microservice, Modularity trainings. Even if you are not going to use framework itself, you can develop yourself with docs.abp.io which is well and professionally prepared. (OpenIddict, Redis, Quartz etc.)\nBecause many thing pre-built, it shortens project development time significantly. (Such as login page, exception handling, data filtering-seeding, audit logging, localization, auto api controller etc.)\nAs an example from our app, i have used Local Event Bus for stock control. So, I am able to manage order movements by writing stock handler.\nIt is wonderful not to lose time for CreationTime, CreatorId. They are filled automatically.", "Index_Page_Testimonial_2": "ABP Framework is not only a framework, it is also a guidance for project development/management, because it provides DDD, GenericRepository, DI, Microservice, Modularity trainings. Even if you are not going to use framework itself, you can develop yourself with docs.abp.io which is well and professionally prepared. (OpenIddict, Redis, Quartz etc.)\nBecause many thing pre-built, it shortens project development time significantly. (Such as login page, exception handling, data filtering-seeding, audit logging, localization, auto api controller etc.)\nAs an example from our app, i have used Local Event Bus for stock control. So, I am able to manage order movements by writing stock handler.\nIt is wonderful not to lose time for CreationTime, CreatorId. They are filled automatically.",
"VideosLoginAndRegisterMessage": "You must sign in to watch videos. You can create an account for watch if you haven't.", "VideosLoginAndRegisterMessage": "To be able to watch videos, you must sign in.",
"Filter": "Filter", "Filter": "Filter",
"VideoCourses": "Video Courses" "VideoCourses": "Video Courses"
} }

164
abp_io/AbpIoLocalization/AbpIoLocalization/Www/Localization/Resources/ru.json

@ -214,7 +214,11 @@
"SeeDocs": "См. Документы", "SeeDocs": "См. Документы",
"None": "Никто", "None": "Никто",
"Application": "заявка", "Application": "заявка",
"ApplicationExplanation": "Создает многоуровневое решение на основе практики доменно-ориентированного проектирования. ",
"ApplicationNoLayer": "Нанесение (один слой)",
"ApplicationNoLayerExplanation": "Создает однослойное веб-приложение. ",
"Module": "Модуль", "Module": "Модуль",
"ModuleExplanation": "Создает многократно используемое, полностью многоуровневое решение модуля приложения. ",
"PackageName": "Имя пакета", "PackageName": "Имя пакета",
"LicenseURL": "URL лицензии", "LicenseURL": "URL лицензии",
"License": "Лицензия", "License": "Лицензия",
@ -274,8 +278,166 @@
"FirstEdition": "Первое издание", "FirstEdition": "Первое издание",
"ThankYou": "Спасибо!", "ThankYou": "Спасибо!",
"CheckboxMandatory": "Вам необходимо проверить это, чтобы продолжить!", "CheckboxMandatory": "Вам необходимо проверить это, чтобы продолжить!",
"UserInterface": "Пользовательский интерфейс",
"APIGateway": "API-шлюз",
"Database": "База данных",
"Saas": "Саас",
"OpenSourceWebApp": "Открыть <span class=\"forever\">источник </span> <br/> веб приложение",
"Framework": "Рамки",
"AuditLoggingExplanation": "Автоматически отслеживайте все операции и изменения данных в вашей системе.",
"AbpNewCommandExplanation": "Создает новые решения, используя шаблоны запуска ABP.",
"AbpAddModuleCommandExplanation": "Устанавливает в ваше решение готовые модули приложений.",
"AbpUpdateCommandExplanation": "Автоматически обновляет все пакеты NuGet и NPM, связанные с ABP, в вашем решении.",
"ExploreAllCLICommands": "Изучите все команды CLI",
"ExploreDocumentationAndGuides": "Изучите подробную документацию и руководства.",
"Documentations": "Документация",
"Views": "Взгляды",
"EnterYouEmailToGetNews": "Введите свой адрес электронной почты, чтобы получать последние новости о ABP Framework",
"Tiered": "Многоуровневый",
"SeparateIdentityServer": "Отдельный сервер идентификации",
"SeparateAuthenticationServer": "Отдельный сервер аутентификации",
"ProgressiveWebApplication": "Прогрессивное веб-приложение",
"Preview": "Предварительный просмотр",
"CreateANewSolution": "Создать новое решение",
"ABPFrameworkFeatures": "Структура ABP <span class=\"gradient-framework\">Функции</span>",
"Commercial": "Коммерческий",
"ThirdPartyTools": "Сторонние инструменты",
"Back": "Назад",
"Community": "Сообщество",
"SeeMore": "Узнать больше",
"DetailsOfTheEBook": "Подробности об электронной книге",
"JoinOurMarketingNewsletter": "Подпишитесь на нашу маркетинговую рассылку",
"FrameworkNewsletterConfirmationMessage": "я согласен <a class=\"text-white fw-6 text-decoration-underline opacity-50\" href=\"https://commercial.abp.io/TermsConditions\">Условия</a> и <a class=\"text-white fw-6 text-decoration-underline opacity-50\" href=\"https://commercial.abp.io/Privacy\">политика конфиденциальности</a>.",
"GetYourFreeEBook": "Получите ваш <span class=\"gradient-framework d-block\">Бесплатная электронная книга DDD </span>",
"EverythingYouNeedToKnow": "Все, что Вам нужно знать.",
"PreOrderNow": "Предварительный заказ сейчас",
"UITheming": "Темы пользовательского интерфейса",
"UIThemingExplanation": "Создавайте повторно используемые темы и макеты пользовательского интерфейса или используйте одну из готовых тем пользовательского интерфейса.",
"DataFilteringExplanation2": "Автоматически фильтруйте запросы к базе данных, чтобы легко реализовать такие шаблоны, как обратимое удаление и многопользовательское использование.",
"NeedHelp": "Нужна помощь?",
"GiveYourProjectAName": "Дайте своему проекту имя",
"SelectProjectType": "Выберите тип проекта",
"SelectUIFramework": "Выберите инфраструктуру пользовательского интерфейса",
"SelectDatabaseProvider": "Выберите поставщика базы данных",
"SelectDatabaseManagementSystem": "Выберите систему управления базой данных",
"InstallingTheABPCLI": "Установка интерфейса командной строки ABP",
"CreateYourProjectNow": "Создайте свой проект сейчас",
"OrderOn": "Закажите {0}",
"DownloadFreeDDDBook": "Скачать бесплатную книгу DDD",
"WhatIsABPFramework": "Что такое структура ABP?",
"TenantDatabase": "База данных арендаторов {0}",
"SharedDatabase": "Общая база данных",
"ConnectionResolver": "Резолвер соединений",
"TenantBasedDataFilter": "Фильтр данных на основе арендаторов",
"ApplicationCode": "Код приложения",
"TenantResolution": "Резолюция арендатора",
"TenantUser": "Арендатор {0} Пользователь",
"CardTitle": "Название карты",
"View": "Вид",
"Model": "Модель",
"Email": "Электронная почта",
"Password": "Пароль",
"Address": "Адрес",
"Gender": "Пол",
"Male": "Мужской",
"Female": "Женский",
"Submit": "Представлять на рассмотрение",
"Unspecified": "Неопределенные",
"StaticFileMiddleware": "Промежуточное ПО для статических файлов",
"RazorViewEngine": "Механизм просмотра Razor",
"PhysicalFiles": "Физические файлы (wwwroot)",
"EmbeddedFiles": "Встроенные файлы (DLL)",
"DynamicFiles": "Динамические файлы (память)",
"BuildSolutionsWithAbp": "Создавайте удобные в обслуживании решения .NET, следуя передовым практикам разработки программного обеспечения с использованием ABP.",
"BuyOnAmazon": "Купить на Амазоне",
"BuyOnPackt": "Купить на Packt",
"Discounted": "Со скидкой",
"MasteringAbpFramework_Book_KeyFeatures": "Ключевая особенность",
"MasteringAbpFramework_Book_Key_Features_Description_1": "Создавайте надежные, удобные в обслуживании, модульные и масштабируемые программные решения с помощью ABP Framework.",
"MasteringAbpFramework_Book_Key_Features_Description_2": "Узнайте, как реализовать принципы SOLID и предметно-ориентированное проектирование в ваших веб-приложениях.",
"MasteringAbpFramework_Book_Key_Features_Description_3": "Узнайте, как ABP Framework ускоряет цикл разработки за счет автоматизации повторяющихся задач.",
"MasteringAbpFramework_Book_Description": "Описание книги",
"MasteringAbpFramework_Book_Description_Details_1": "ABP Framework — это полная инфраструктура для создания современных веб-приложений с помощью следующего программного обеспечения.\n ",
"MasteringAbpFramework_Book_Description_Details_2": "Эта книга, написанная создателем ABP Framework, поможет вам получить полное представление о\n ",
"MasteringAbpFramework_Book_Description_Details_3": "К концу этой книги вы сможете создать полноценное веб-решение, которое легко разрабатывать.\n ",
"MasteringAbpFramework_Book_WhatYouWillLearn": "Что вы узнаете",
"MasteringAbpFramework_Book_What_You_Will_Learn_1": "Настройте среду разработки и начните работу с ABP Framework.",
"MasteringAbpFramework_Book_What_You_Will_Learn_2": "Работайте с Entity Framework Core и MongoDB для разработки уровня доступа к данным.",
"MasteringAbpFramework_Book_What_You_Will_Learn_3": "Поймите сквозные проблемы и то, как ABP автоматизирует повторяющиеся задачи.",
"MasteringAbpFramework_Book_What_You_Will_Learn_4": "Освойте реализацию предметно-ориентированного проектирования с помощью ABP Framework.",
"MasteringAbpFramework_Book_What_You_Will_Learn_5": "Создавайте страницы и компоненты пользовательского интерфейса с помощью ASP.NET Core MVC (Razor Pages) и Blazor.",
"MasteringAbpFramework_Book_What_You_Will_Learn_6": "Работайте с мультитенантностью для создания модульных веб-приложений.",
"MasteringAbpFramework_Book_What_You_Will_Learn_7": "Понимайте модульность и создавайте повторно используемые модули приложений.",
"MasteringAbpFramework_Book_What_You_Will_Learn_8": "Написание модульных, интеграционных и UI-тестов с использованием ABP Framework.",
"MasteringAbpFramework_Book_WhoIsThisBookFor": "Для кого эта книга",
"MasteringAbpFramework_Book_WhoIsThisBookFor_Description": "Эта книга предназначена для веб-разработчиков, которые хотят изучить архитектуру программного обеспечения и лучшие практики создания\n ",
"ComputersAndTechnology": "Компьютеры",
"BuildingMicroserviceSolutions": "Создание микросервисных решений",
"MicroserviceBookPracticalGuide": "Эта книга представляет собой справочное руководство по разработке и управлению приложениями на основе микросервисов с использованием ABP Framework. <strong>Пример справочного приложения микросервиса .NET</strong>: eShopOnContainers и обсуждает подходы к проектированию архитектуры и реализации с использованием ABP Framework. ",
"IntroducingTheSolution": "Представляем решение eShopOnAbp",
"RunningTheSolution": "Запуск решения",
"UnderstandingTheAuthenticationSystem": "Понимание системы аутентификации",
"ExploringTheApplications": "Изучение приложений",
"UnderstandingTheAPIGateways": "Понимание шлюзов API",
"DevelopingTheMicroservices": "Разработка микросервисов",
"UnderstandingTheInfrastructure": "Понимание инфраструктуры",
"DiggingInTheUseCases": "Копаем в вариантах использования",
"DeployingTheSolution": "Развертывание решения",
"ThisBookIsInDraftStageAndIsNotCompletedYet": "Эта книга находится на стадии черновика и еще не завершена.",
"Authors": "Авторы",
"MicroserviceEBook": "Электронная книга по микросервисам",
"SelectUITheme": "Выберите тему пользовательского интерфейса", "SelectUITheme": "Выберите тему пользовательского интерфейса",
"LeptonXLiteTheme": "Тема LeptonX Lite",
"BasicTheme": "Основная тема",
"LeptonXLiteThemeInfo": " Современная и стильная тема пользовательского интерфейса Bootstrap. ",
"BasicThemeInfo": "Минималистичная тема пользовательского интерфейса с простыми цветами и стилями Bootstrap. ",
"SeeDocumentation": "Видеть <a href='{0}' target='_blank'>документация</a>.",
"SeeFullScreen": "<a href='{0}' target='_blank'>🖼️ Смотрите скриншот</a>",
"BuildingMicroserviceSolutionsShortDescription": "Эта книга представляет собой справочное руководство по разработке и управлению приложениями на основе микросервисов с использованием ABP Framework.",
"InstallAbpCliMessage": "Установите ABP CLI в терминале командной строки, если вы еще не установили его раньше:",
"Terminal": "Терминал",
"Copy": "Копировать",
"RunTheFollowingCommand": "Запустите следующую команду в терминале командной строки:",
"ChangeSolutionOptionsBelow": "Вы можете изменить варианты решения ниже.",
"MultiLayerApplication": "Многослойный <br>Приложение",
"MultiLayerApplicationExplanation1": "Создает многоуровневое решение на основе практики доменно-ориентированного проектирования.",
"MultiLayerApplicationExplanation2": "Рекомендуется для долгосрочных проектов, которым нужна поддерживаемая и расширяемая база кода.",
"SingleLayerApplication": "Одиночный слой <br>Приложение",
"SingleLayerApplicationExplanation1": "Создает однослойное веб-приложение. ",
"SingleLayerApplicationExplanation2": "Рекомендуется для создания приложения с более простой и понятной архитектурой.",
"ApplicationModule": "Приложение <br>Модуль",
"SeeTheScreenshot": "Смотрите скриншот",
"ApplicationModuleExplanation1": "Создает многократно используемое, полностью многоуровневое решение модуля приложения.",
"ApplicationModuleExplanation2": "Вы можете использовать эту опцию для создания модулей для вашего модульного приложения.",
"Expert_": "Эксперт",
"Partner_": "партнерство",
"WebSite": "Веб-сайт",
"Expert_Year": "Год экспертизы",
"CompanyInfo": "информация о компании",
"Date": "Дата",
"WhoWeAre_Partner": "Кто мы",
"WhoWeAre_Expert": "Обо мне",
"CreateSolutionFolder": "Создать папку решения", "CreateSolutionFolder": "Создать папку решения",
"CreateSolutionFolderOption": "Указывает, будет ли проект находиться в новой папке в выходной папке или непосредственно в выходной папке." "CreateSolutionFolderOption": "Указывает, будет ли проект находиться в новой папке в выходной папке или непосредственно в выходной папке.",
"BooksPageTitle": "Книги АБП",
"PackageDetailPage_NuGetPackageInstallationOptions": "Есть три способа установки <code>{0}</code> Пакет NuGet в ваш проект",
"PackageDetailPage_InstallingWithABPCLI": "1. Установка с помощью ABP CLI",
"PackageDetailPage_InstallingWithABPCLIDescription1": "Если вы не установили <a href=\"https://docs.abp.io/en/abp/latest/CLI\">Интерфейс командной строки ABP</a>сначала установите, выполнив следующую команду в терминале командной строки",
"PackageDetailPage_InstallingWithABPCLIDescription2": "После установки ABP CLI откройте терминал командной строки в папке проекта (<code>.csproj</code> файл), вы хотите его установить, и выполните следующую команду",
"PackageDetailPage_InstallingWithABPCLIDescription3": "Это добавит <code>{0}</code> ссылка на пакет вашего проекта и <code>{1}</code> зависимость от вашего класса модуля.",
"PackageDetailPage_ManualInstallation": "2. Установка с помощью Dotnet CLI",
"PackageDetailPage_ManualInstallationDescription1": "Добавлять <code>{0}</code> Ссылка на пакет NuGet для вашего проекта с использованием вашей IDE или выполнением следующей команды",
"PackageDetailPage_ManualInstallationDescription2": "Затем добавьте <code>{0}</code> зависимость от вашего <a href=\"https://docs.abp.io/en/abp/latest/Module-Development-Basics\">класс модуля</a> как показано в следующем примере",
"PackageDetailPage_SeeDocumentation": "<a href=\"{0}\">См. документацию</a> чтобы узнать, как использовать этот пакет в ваших приложениях.",
"PackageDetailPage_InstallingUsingPMC": "3. Установка с помощью консоли диспетчера пакетов",
"PackageDetailPage_InstallingUsingPMCDescription1": "Открой <strong>Консоль диспетчера пакетов</strong> в Visual Studio (Инструменты -> Диспетчер пакетов Nuget -> Консоль диспетчера пакетов) и выполните следующую команду",
"UIOptions": "Параметры пользовательского интерфейса",
"Testimonials": "Отзывы",
"CoolestCompaniesUseABPFramework": "Самые крутые компании используют <span class=\"fw-bold\">Структура ABP</span>",
"Index_Page_Testimonial_1": "ABP Framework — это не просто инструмент, а катализатор, который ускорил мой рост как разработчика. ",
"Index_Page_Testimonial_2": "ABP Framework — это не только платформа, но и руководство по разработке/управлению проектами, поскольку оно обеспечивает обучение DDD, GenericRepository, DI, Microservice и Modularity. ",
"VideosLoginAndRegisterMessage": "Чтобы иметь возможность смотреть видео, вам необходимо войти в систему.",
"Filter": "Фильтр",
"VideoCourses": "Видео курсы"
} }
} }

35
abp_io/README.md

@ -1,11 +1,32 @@
## Abp.io platform localization ## ABP Platform Websites Localization
This project is all localized resources of the abp.io platform. This is the localization project of [abp.io platform](https://abp.io).
All *.abp.io websites are built on top of ABP Framework, and it uses ABP Framework's localization system.
You can correct a wrong localization text, or you can translate it into your own language.
By doing so, [abp.io](https://abp.io) websites will be translated into a new language and it will help to expand the ABP Community.
If you like, you can contribute to the localization resources in this project.
For example: `AbpIoLocalization\AbpIoLocalization\Www\Localization\Resources\zh-Hans.json`
If the file is missing some translations or the translation is wrong, you can add it.
If the language file is missing (eg `kr.json`), you can also add it.
Please refer to the [Contribution Guide](https://github.com/abpframework/abp/blob/dev/docs/en/Contribution/Index.md) for details. ## How to Translate abp.io Into Your Language:
1. Install [ABP CLI](https://docs.abp.io/en/abp/latest/CLI) command line tool.
2. Run the following command to generate the localization file.
For example, for translating from English to French `fr`:
```bash
abp translate -c fr
```
3. After you fill in the empty localization keys, run the following command to apply it.
```bash
abp translate -a
```
4. Send your PR to the team; after the review process, we wil merge it.
---
## References:
* [ABP CLI Translate Command](https://docs.abp.io/en/abp/latest/Contribution/Index#using-the-abp-translate-command)
* [Contribution Guide](https://github.com/abpframework/abp/blob/dev/docs/en/Contribution/Index.md)

2
common.props

@ -1,7 +1,7 @@
<Project> <Project>
<PropertyGroup> <PropertyGroup>
<LangVersion>latest</LangVersion> <LangVersion>latest</LangVersion>
<Version>8.0.0-rc.3</Version> <Version>8.1.0</Version>
<NoWarn>$(NoWarn);CS1591;CS0436</NoWarn> <NoWarn>$(NoWarn);CS1591;CS0436</NoWarn>
<PackageIconUrl>https://abp.io/assets/abp_nupkg.png</PackageIconUrl> <PackageIconUrl>https://abp.io/assets/abp_nupkg.png</PackageIconUrl>
<PackageProjectUrl>https://abp.io/</PackageProjectUrl> <PackageProjectUrl>https://abp.io/</PackageProjectUrl>

223
docs/en/Blog-Posts/2023-11-15 v8_0_Preview/POST.md

@ -0,0 +1,223 @@
# ABP.IO Platform 8.0 RC Has Been Released
Today, we are happy to release the [ABP Framework](https://abp.io/) and [ABP Commercial](https://commercial.abp.io/) version **8.0 RC** (Release Candidate). This blog post introduces the new features and important changes in this new version.
Try this version and provide feedback for a more stable version of ABP v8.0! Thanks to all of you.
## Get Started with the 8.0 RC
Follow the steps below to try version 8.0.0 RC today:
1) **Upgrade** the ABP CLI to version `8.0.0-rc.1` using a command line terminal:
````bash
dotnet tool update Volo.Abp.Cli -g --version 8.0.0-rc.1
````
**or install** it if you haven't before:
````bash
dotnet tool install Volo.Abp.Cli -g --version 8.0.0-rc.1
````
2) Create a **new application** with the `--preview` option:
````bash
abp new BookStore --preview
````
See the [ABP CLI documentation](https://docs.abp.io/en/abp/latest/CLI) for all the available options.
> You can also use the [Get Started](https://abp.io/get-started) page to generate a CLI command to create a new application.
You can use any IDE that supports .NET 8.x, like [Visual Studio 2022](https://visualstudio.microsoft.com/downloads/).
## Migration Guides
There are a few breaking changes in this version that may affect your application.
Please see the following migration documents, if you are upgrading from v7.x or earlier:
* [ABP Framework 7.x to 8.0 Migration Guide](https://docs.abp.io/en/abp/8.0/Migration-Guides/Abp-8_0)
* [ABP Commercial 7.x to 8.0 Migration Guide](https://docs.abp.io/en/commercial/8.0/migration-guides/v8_0)
## What's New with ABP Framework 8.0?
In this section, I will introduce some major features released in this version.
Here is a brief list of titles explained in the next sections:
* Upgraded to .NET 8.0
* Upgraded to Angular 17
* Dynamic Claims
* CDN Support for Bundling & Minification System
* Read-Only Repositories
* Account Module: Set Username After Social/External Login
* Other News...
### Upgraded to .NET 8.0
We've upgraded the ABP Framework to .NET 8.0, so you need to move your solutions to .NET 8.0 if you want to use ABP 8.0. You can check [Microsoft’s Migrate from ASP.NET Core 7.0 to 8.0 documentation](https://learn.microsoft.com/en-us/aspnet/core/migration/70-80), to see how to update an existing ASP.NET Core 7.0 project to ASP.NET Core 8.0.
### Upgraded to Angular 17
Angular 17 [was released on November 8](https://blog.angular.io/introducing-angular-v17-4d7033312e4b) and ABP Framework & ABP Commercial startup templates were immediately migrated to **Angular 17**!
So, when you create a new solution with the Angular UI, you will take advantage of the new Angular with the new cutting-edge features and enhancements right from the start!
### Dynamic Claims
The **Dynamic Claims** feature is used to dynamically generate claims for the user in each request. It's used to automatically and dynamically override the configured claim values in the client's authentication token/cookie by the latest user claims.
In the prior versions, whenever a user changed their email address or confirmed their own email address, or any other information related to the user (and if it's in the claims), he/she would need to logout and then login to refresh its claims. The new **Dynamic Claims** feature overcomes this problem and allows to **always get the latest user claims**.
This feature is disabled by default and you can enable it easily for your existing MVC applications by following the [Dynamic Claims documentation](https://docs.abp.io/en/abp/8.0/Dynamic-Claims). For the other UI options (Angular & Blazor UIs), you don't need to enable this feature, since they obtain claims ftom a configuration endpoint.
> **Note**: Beginning from the v8.0, all the startup templates are pre-configured and the **Dynamic Claims** feature is enabled by default.
### CDN Support for Bundling & Minification System
In this version, ABP Framework's [Bundling & Minification System](https://docs.abp.io/en/abp/latest/UI/AspNetCore/Bundling-Minification) provides CDN support for MVC / Razor Pages UI. The bundling system automatically recognizes the external/CDN files and places them as link/script tags on the page along with the bundled CSS/JSS files.
> Read the documentation for more info: https://docs.abp.io/en/abp/8.0/UI/AspNetCore/Bundling-Minification
### Read-Only Repositories
ABP Framework provides read-only repository interfaces (`IReadOnlyRepository<>` or `IReadOnlyBasicRepository<>`) to explicitly indicate that your purpose is to query data, but not change it. It uses [EF Core's No-Tracking Feature](https://learn.microsoft.com/en-us/ef/core/querying/tracking#no-tracking-queries) behind the scenes, which means the entities returned from the repository will not be tracked by the EF Core's [change tracker](https://learn.microsoft.com/en-us/ef/core/change-tracking/) and thanks to that you get significant performance gains.
```csharp
public class MyService
{
private readonly IReadOnlyRepository<Book, Guid> _bookRepository;
public async Task MyMethod()
{
var books = await _bookRepository.GetListAsync(); //change tracking not involved
//...
}
}
```
> In addition to the read-only repository interfaces, ABP Framework introduces the `IRepository.DisableTracking()` and `IRepository.EnableTracking()` extension methods to allow developers to disable/enable entity tracking by these methods manually. If you don't want to use the read-only repositories, you can use these methods to enable or disable the change tracker controlled. Read the documentation to learn more: [https://docs.abp.io/en/abp/8.0/Repositories#enabling-disabling-the-change-tracking](https://docs.abp.io/en/abp/8.0/Repositories#enabling-disabling-the-change-tracking)
### Account Module: Set Username After Social/External Login
Prior to this version, when you registered with your social accounts for the first time, your email address was becoming your username and it was shown everywhere in the application. Therefore, you would need to update your username later on and this is not a good user experience.
Thus, in this version, we have enhanced this flow, and now, when you register as an external user for the first time, a username and email address are shown you in a form for you to revise and update if you want, before logging into the application. Thanks to that, after the social registration you would not need to update your username and email address. This is also good at the point of GDPR regulations because your email address will not be shown as a username and will not exposed.
![](account-module-register.png)
### Other News
* LDAP over SSL (LDAPS) setting has been added and recommended to establish a secure connection. See [#17865](https://github.com/abpframework/abp/pull/17865) for more information.
* Object Mapping Enhancements (supports mapping collection of objects for custom object mappers).
* Email Sending Improvements (sending attachments with `IEmailSender.QueueAsync()` method).
## What's New with ABP Commercial 8.0?
We've also worked on ABP Commercial to align the features and changes made in the ABP Framework. The following sections introduce a few new features coming with ABP Commercial 8.0.
### Suite: Generating Master/Detail Relationship
In this version, we have introduced the **Master/Detail Relationship** support in Suite. The Master-Detail (or Master-Child) relationship refers to a hierarchical connection between two entities, where one entity (the master or parent entity) influences or controls the behavior or properties of another element (the child entity) relationship. The relationship between **Order - Order Lines** can be considered as an example of a master-detail relationship.
![](suite-master-child-datagrid.png)
ABP Suite allows you to create a master-detail relationship with a few clicks. It generates the necessary code for the master and detail tables, including the foreign key relationship between the two tables.
To establish a master-detail relationship, you need to apply the following two steps:
1-) Create the master entity,
2-) Create a child entity and associate it with a master entity.
That's it! ABP Suite will be generating the entities, making the related configurations, establishing database relations (including the foreign key relationship), generating the UI for the master entity (with child-grids for child entities), and so on...
It’s already documented and you can read the documentation at [https://docs.abp.io/en/commercial/8.0/abp-suite/creating-master-detail-relationship](https://docs.abp.io/en/commercial/8.0/abp-suite/creating-master-detail-relationship).
#### Known Issues
* After you generate CRUD pages via Suite for the Angular UI, you should start the backend project and run the `abp generate-proxy -t ng` command in the root directory of the Angular application manually. It will be automatically done with the next version, so you will not need to run the command manually in further versions.
### Get Profile Picture From Social/External Logins
A user's profile picture would be blank when they first register for an application using a social account through an external authentication provider like Google or Facebook because it hasn't been configured yet. The user must update their profile photo after logging into the application.
In order to save the user from having to change their profile picture after logging in for the first time, we have improved this behavior in this version and are now attempting to retrieve the user's profile picture from external authentication providers (like Google) and set it as their profile picture. Later on, if desired, he or she might modify the profile image.
### Switch Ocelot to YARP for the API Gateway
Until this version, ABP Commercial was using the [Ocelot](https://github.com/ThreeMammals/Ocelot) for the API Gateway, in the [Microservice Startup Template](https://docs.abp.io/en/commercial/latest/startup-templates/microservice/index). Since the **Ocelot** library is not actively maintained, we have searched for an alternative and decided to switch from Ocelot to [YARP](https://github.com/microsoft/reverse-proxy) for the API Gateway. YARP is maintained by Microsoft and is actively being developed and seems a better alternative than Ocelot and provides the same feature stack and even more.
You can read the [Migrating to YARP](https://docs.abp.io/en/commercial/8.0/migration-guides/migrating-to-yarp) documentation for migrating your existing microservice application's API Gateway from [Ocelot](https://github.com/ThreeMammals/Ocelot) to [YARP](https://github.com/microsoft/reverse-proxy).
> We have made the all related changes in the Microservice Startup Template, and also updated the documentation, which you can read [here](https://docs.abp.io/en/commercial/8.0/startup-templates/microservice/gateways).
### Password Complexity Indicators (MVC & Blazor UIs)
In v7.4, we have introduced the [Password Complexity Indicators for Angular UI](https://docs.abp.io/en/commercial/7.4/ui/angular/password-complexity-indicator-component) and with this version, we have implemented it for the MVC & Blazor UIs as well. You can use this feature to dynamically evaluate and rate the strength of user-generated passwords, providing real-time feedback to users as they create or update their passwords.
![](password-complexity-indicators.png)
### Read-Only View for Users Page
In your application, you may want to grant permission to a specific group or people to read-only view the users of your application to be able to do some actions. For example, you may want to marketing team to see the users to organize campaigns for the customers, or make controls. In this case, you can grant default permissions for these groups, however, they could not see the details of a user, because in the current design, if the edit permission is not granted you can't see the detailed info for a user.
![](identity-users.gif)
In this version, we have added the read-only view action to the user's page. This allows you to only grant the default view permission to the specific users and allow them to view user information as read-only and not allow them to change or modify it.
### Export & Import Users as Excel / CSV
With v8.0, now it's possible to import and export user records in Excel and CSV formats. You can import external users, or import users from Excel or CSV files and also you can export users to Excel or CSV files:
![](users-page.png)
## Community News
### Highlights from .NET 8.0
Our team has closely followed the ASP.NET Core and Entity Framework Core 8.0 releases, read Microsoft's guides and documentation, and adapted the changes to our ABP.IO Platform. We are proud to say that we've shipped the ABP 8.0 RC.1 based on .NET 8.0 just after Microsoft's .NET 8.0 release.
In addition to the ABP's .NET 8.0 upgrade, our team has created 13 great articles to highlight the important features coming with ASP.NET Core 8.0 and Entity Framework Core 8.0.
> You can read [this post](https://volosoft.com/blog/Highlights-for-ASP-NET-Entity-Framework-Core-NET-8-0) to see the list of all articles.
### New ABP Community Articles
In addition to [the 13 articles to highlight .NET 8.0 features written by our team](https://volosoft.com/blog/Highlights-for-ASP-NET-Entity-Framework-Core-NET-8-0), here are some of the recent posts added to the [ABP Community](https://community.abp.io/):
* [Upgrade Your Existing Projects to .NET 8 & ABP 8.0](https://community.abp.io/posts/upgrade-your-existing-projects-to-.net-8-abp-8.0-x0n7hiqr) by [Engincan Veske](https://github.com/EngincanV)
* [How to Upload and Download Files in the ABP Framework using Angular](https://community.abp.io/posts/how-to-upload-and-download-files-in-the-abp-framework-using-angular-que8cdr8) by [Mahmut Gündoğdu](https://github.com/mahmut-gundogdu)
* New **ABP Framework Essentials** Videos by [Hamza Albreem](https://github.com/braim23):
* [ABP Essentials - Interception](https://community.abp.io/videos/abp-essentials-interception-ath78xhw)
* [ABP Essentials - Virtual File System](https://community.abp.io/videos/abp-essentials-virtual-file-system-hpgr2j72)
* [ABP Framework Essentials - Localization](https://community.abp.io/videos/abp-framework-essentials-localization-7taieh68)
* [ABP Framework Essentials - Dependency Injection](https://community.abp.io/videos/abp-framework-essentials-dependency-injection-q241mfrf)
* See the playlist for other videos of this series: https://www.youtube.com/playlist?list=PLsNclT2aHJcNupH2wz83y7htugpLoUZ_B
Thanks to the ABP Community for all the content they have published. You can also [post your ABP related (text or video) content](https://community.abp.io/articles/submit) to the ABP Community.
### We were in the .NET Conf 2023
Microsoft has released .NET 8.0 and celebrated it with a 3-day international online conference. The core team members of ABP Framework, [Alper Ebiçoğlu](https://twitter.com/alperebicoglu) and [Enis Necipoğlu](https://twitter.com/EnisNecipoglu) gave speeches at the .NET Conf 2023.
[Alper Ebiçoğlu](https://twitter.com/alperebicoglu)'s topic was "Building Multi-Tenant ASP.NET Core Applications and ABP Framework" and in this talk, he talked about what's SaaS development, what are its pros and challenges and multi-tenant development with the open-source ABP Framework:
<iframe width="560" height="315" src="https://www.youtube.com/embed/3uWeyEbV4c4?si=XuU8-QJs2w5j6Inp" title="YouTube video player" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" allowfullscreen></iframe>
On the other hand, [Enis Necipoğlu](https://twitter.com/EnisNecipoglu)'s topic was "Reactive programming with .NET MAUI" and he talked about applying reactive programming in .NET MAUI with MVVM and ReactiveUI:
<iframe width="560" height="315" src="https://www.youtube.com/embed/i0EFuRF2u-w?si=wPTSDxtbfkzMF5CN" title="YouTube video player" frameborder="0" allow="accelerometer; autoplay; clipboard-write; encrypted-media; gyroscope; picture-in-picture; web-share" allowfullscreen></iframe>
### ABP Community Talks 2023.8: What’s coming with .NET 8.0 & ABP v8.0
![](community-talk-2023-8.png)
In this episode of ABP Community Talks, 2023.8; [Steve Sanderson](https://twitter.com/stevensanderson) will be our guest speaker and we'll talk about .NET 8.0 and ABP 8.0 with the ABP Core Team. We will dive into the features that came with .NET 8.0, how they are implemented in ABP 8.0, and the highlights in the .NET Conf 2023 with [Halil İbrahim Kalkan](https://github.com/hikalkan), [Alper Ebicoglu](https://github.com/ebicoglu), [Engincan Veske](https://github.com/EngincanV), [Berkan Sasmaz](https://github.com/berkansasmaz) and [Bige Besikci Yaman](https://github.com/bigebesikci).
## Conclusion
This version comes with some new features and a lot of enhancements to the existing features. You can see the [Road Map](https://docs.abp.io/en/abp/8.0/Road-Map) documentation to learn about the release schedule and planned features for the next releases. Please try ABP v8.0 RC and provide feedback to help us release a more stable version.
Thanks for being a part of this community!

BIN
docs/en/Blog-Posts/2023-11-15 v8_0_Preview/account-module-register.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.6 KiB

BIN
docs/en/Blog-Posts/2023-11-15 v8_0_Preview/community-talk-2023-8.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 130 KiB

BIN
docs/en/Blog-Posts/2023-11-15 v8_0_Preview/cover-image.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 235 KiB

BIN
docs/en/Blog-Posts/2023-11-15 v8_0_Preview/identity-users.gif

Binary file not shown.

After

Width:  |  Height:  |  Size: 688 KiB

BIN
docs/en/Blog-Posts/2023-11-15 v8_0_Preview/password-complexity-indicators.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

BIN
docs/en/Blog-Posts/2023-11-15 v8_0_Preview/suite-master-child-datagrid.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 110 KiB

BIN
docs/en/Blog-Posts/2023-11-15 v8_0_Preview/users-page.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 72 KiB

2
docs/en/Community-Articles/2023-10-28-EF-Core-8-Primitive-Collections/POST.md

@ -102,7 +102,7 @@ The SQL statement looks like this, and as you can see, it automatically serializ
Executed DbCommand (0ms) [Parameters= Executed DbCommand (0ms) [Parameters=
[@p0='Maserati' (Nullable = false) (Size = 8), [@p0='Maserati' (Nullable = false) (Size = 8),
@p1='[0,3]' (Nullable = false) (Size = 5), @p1='[0,3]' (Nullable = false) (Size = 5),
@p2='Flow' (Nullable = false) (Size = 4) @p2='GranTurismo' (Nullable = false) (Size = 4)
], CommandType='Text', CommandTimeout='30'] ], CommandType='Text', CommandTimeout='30']
INSERT INTO "Cars" ("Brand", "Colors", "Model") INSERT INTO "Cars" ("Brand", "Colors", "Model")
VALUES (@p0, @p1, @p2) VALUES (@p0, @p1, @p2)

1
docs/en/Community-Articles/2023-11-06-Blazor-Fullstack-Web-Ui/Post.md

@ -91,4 +91,5 @@ I summarized the new generation Blazor in a very simple way. This architecture w
* You can check Dan Roth's GitHub issue 👉 [github.com/dotnet/aspnetcore/issues/46636](https://github.com/dotnet/aspnetcore/issues/46636). * You can check Dan Roth's GitHub issue 👉 [github.com/dotnet/aspnetcore/issues/46636](https://github.com/dotnet/aspnetcore/issues/46636).
* Steven Sanderson's YouTube video is very good for understanding these concepts 👉 [Blazor United Prototype Video](https://youtu.be/48G_CEGXZZM). * Steven Sanderson's YouTube video is very good for understanding these concepts 👉 [Blazor United Prototype Video](https://youtu.be/48G_CEGXZZM).
* "Full Stack Web UI with Blazor" — .NET Conf 2023 video 👉 [learn.microsoft.com/en-us/shows/dotnetconf-2023/full-stack-web-ui-with-blazor-in-dotnet-8](https://learn.microsoft.com/en-us/shows/dotnetconf-2023/full-stack-web-ui-with-blazor-in-dotnet-8)

0
docs/en/Community-Articles/2023-11-97-AOT-Compilation/Post.md → docs/en/Community-Articles/2023-11-17-AOT-Compilation/Post.md

15
docs/en/Dependency-Injection.md

@ -269,6 +269,21 @@ public class MyService : ITransientDependency
} }
```` ````
#### IInjectPropertiesService
You can use the `IInjectPropertiesService` service to inject properties of an object. Generally, it is a service outside of DI, such as manually created services.
````C#
var injectPropertiesService = serviceProvider.GetRequiredService<IInjectPropertiesService>();
var instance = new TestService();
// Set any properties on instance that can be resolved by IServiceProvider.
injectPropertiesService.InjectProperties(instance);
// Set any null-valued properties on instance that can be resolved by the IServiceProvider.
injectPropertiesService.InjectUnsetProperties(instance);
````
### Resolve Service from IServiceProvider ### Resolve Service from IServiceProvider
You may want to resolve a service directly from ``IServiceProvider``. In that case, you can inject `IServiceProvider` into your class and use the ``GetService`` or the `GetRequiredService` method as shown below: You may want to resolve a service directly from ``IServiceProvider``. In that case, you can inject `IServiceProvider` into your class and use the ``GetService`` or the `GetRequiredService` method as shown below:

10
docs/en/Distributed-Event-Bus-RabbitMQ-Integration.md

@ -152,4 +152,14 @@ Configure<AbpRabbitMqEventBusOptions>(options =>
}); });
```` ````
**Example: Configure the queue and exchange optional arguments**
```csharp
Configure<AbpRabbitMqEventBusOptions>(options =>
{
options.ExchangeArguments["x-delayed-type"] = "direct";
options.QueueArguments["x-message-ttl"] = 60000;
});
```
Using these options classes can be combined with the `appsettings.json` way. Configuring an option property in the code overrides the value in the configuration file. Using these options classes can be combined with the `appsettings.json` way. Configuring an option property in the code overrides the value in the configuration file.

12
docs/en/Migration-Guides/Abp-8_0.md

@ -156,12 +156,12 @@ You can see the following list of NuGet libraries that have been upgraded with .
| AWSSDK.SecurityToken | 3.7.1.151 | 3.7.300.2 | | AWSSDK.SecurityToken | 3.7.1.151 | 3.7.300.2 |
| Azure.Messaging.ServiceBus | 7.8.1 | 7.17.0 | | Azure.Messaging.ServiceBus | 7.8.1 | 7.17.0 |
| Azure.Storage.Blobs | 12.15.0 | 12.19.1 | | Azure.Storage.Blobs | 12.15.0 | 12.19.1 |
| Blazorise | 1.3.1 | 1.4.0 | | Blazorise | 1.3.1 | 1.3.2 |
| Blazorise.Bootstrap5 | 1.3.1 | 1.4.0 | | Blazorise.Bootstrap5 | 1.3.1 | 1.3.2 |
| Blazorise.Icons.FontAwesome | 1.3.1 | 1.4.0 | | Blazorise.Icons.FontAwesome | 1.3.1 | 1.3.2 |
| Blazorise.Components | 1.3.1 | 1.4.0 | | Blazorise.Components | 1.3.1 | 1.3.2 |
| Blazorise.DataGrid | 1.3.1 | 1.4.0 | | Blazorise.DataGrid | 1.3.1 | 1.3.2 |
| Blazorise.Snackbar | 1.3.1 | 1.4.0 | | Blazorise.Snackbar | 1.3.1 | 1.3.2 |
| Confluent.Kafka | 1.8.2 | 2.3.0 | | Confluent.Kafka | 1.8.2 | 2.3.0 |
| Dapper | 2.0.123 | 2.1.21 | | Dapper | 2.0.123 | 2.1.21 |
| Dapr.AspNetCore | 1.9.0 | 1.12.0 | | Dapr.AspNetCore | 1.9.0 | 1.12.0 |

108
docs/en/Migration-Guides/OpenIddict4-to-5.md

@ -0,0 +1,108 @@
# OpenIddict 4.x to 5.x Migration Guide
The 5.0 release of OpenIddict is a major release that introduces breaking changes.
Check this blog [Introducing native applications, per-client token lifetimes and client assertions support in OpenIddict 5.0 preview1](https://kevinchalet.com/2023/10/20/introducing-native-applications-per-client-token-lifetimes-and-client-assertions-support-in-openiddict-5-0-preview1/) for the new features introduced in OpenIddict 5.0.
I will show the changes you need to make to do the migration.
> Please backup your database before doing the migration.
## OpenIddictApplication changes
1. The `Type(string)` of the `OpenIddictApplication` has been renamed to `ClientType(string)`.
2. The `ApplicationType(string)` has been added to the `OpenIddictApplication` entity.
3. The `JsonWebKeySet(string)` has been added to the `OpenIddictApplication` entity.
4. The `Settings(string)` has been added to the `OpenIddictApplication` entity.
The new migration looks like this:
````csharp
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace OpenIddict.Demo.Server.Migrations
{
/// <inheritdoc />
public partial class openiddict5 : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.RenameColumn(
name: "Type",
table: "OpenIddictApplications",
newName: "ClientType");
migrationBuilder.AddColumn<string>(
name: "ApplicationType",
table: "OpenIddictApplications",
type: "nvarchar(50)",
maxLength: 50,
nullable: true);
migrationBuilder.AddColumn<string>(
name: "JsonWebKeySet",
table: "OpenIddictApplications",
type: "nvarchar(max)",
nullable: true);
migrationBuilder.AddColumn<string>(
name: "Settings",
table: "OpenIddictApplications",
type: "nvarchar(max)",
nullable: true);
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "ApplicationType",
table: "OpenIddictApplications");
migrationBuilder.DropColumn(
name: "JsonWebKeySet",
table: "OpenIddictApplications");
migrationBuilder.DropColumn(
name: "Settings",
table: "OpenIddictApplications");
migrationBuilder.RenameColumn(
name: "ClientType",
table: "OpenIddictApplications",
newName: "Type");
}
}
}
````
## OpenIddictApplicationModel changes
1. The `Type(string)` of the `OpenIddictApplicationModel` has been renamed to `ClientType(string)`.
2. The `ApplicationType(string)` has been added to the `OpenIddictApplicationModel` entity.
3. The `JsonWebKeySet`([JsonWebKeySet](https://learn.microsoft.com/en-us/dotnet/api/microsoft.identitymodel.tokens.jsonwebkeyset)) has been added to the `OpenIddictApplicationModel` entity.
4. The `Settings(string)` has been added to the `OpenIddictApplicationModel` entity.
## OpenIddictApplicationDescriptor changes
You have to change the `Type` to `ClientType` when creating a new `AbpApplicationDescriptor` or `OpenIddictApplicationDescriptor`.
````csharp
var application = new AbpApplicationDescriptor {
ClientId = name,
- Type = type,
+ ClientType = type,
ClientSecret = secret,
ConsentType = consentType,
DisplayName = displayName,
````
## OpenIddict Pro module UI changes
You can change the `ApplicationType` when creating/editing a OpenIddict's application, also set time life of the tokens for each application.
![ropeniddict-pro-application-modal](images/openiddict-pro-application-modal.png)
![openiddict-pro-application-timelife-modal](images/openiddict-pro-application-timelife-modal.png)

BIN
docs/en/Migration-Guides/images/openiddict-pro-application-modal.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 291 KiB

BIN
docs/en/Migration-Guides/images/openiddict-pro-application-timelife-modal.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 203 KiB

2
docs/en/Repositories.md

@ -170,7 +170,7 @@ If your entity is a soft-delete entity, you can use the `HardDeleteAsync` method
Some features (like soft-delete, multi-tenancy and audit logging) won't work, so use this method carefully when you need it. Use the `DeleteAsync` method if you need to these features. Some features (like soft-delete, multi-tenancy and audit logging) won't work, so use this method carefully when you need it. Use the `DeleteAsync` method if you need to these features.
> Currently only [EF Core supports it](https://learn.microsoft.com/en-us/ef/core/what-is-new/ef-core-7.0/whatsnew#basic-executedelete-examples), For the ORMs doesn't support direct delete, we will fallback to the existing `DeleteAsync` method. > Currently only [EF Core supports it](https://learn.microsoft.com/en-us/ef/core/what-is-new/ef-core-7.0/whatsnew#basic-executedelete-examples), For the ORMs that don't support direct delete, we will fallback to the existing `DeleteAsync` method.
### Ensure Entities Exists ### Ensure Entities Exists

67
docs/en/UI/Angular/Sorting-Navigation-Elements.md

@ -1,46 +1,37 @@
# Sorting Navigation Elements # Sorting Navigation Elements
This documentation describes how the navigation elements are sorted and how to change this default behaviour.
When you want to add the `Navigation Element` you can use the `RoutesService`. For more details, see the [document](https://docs.abp.io/en/abp/latest/UI/Angular/Modifying-the-Menu#how-to-add-a-navigation-element). This documentation describes how the navigation elements are sorted and how to change this default behaviour.
However, in this documentation, we will talk more about how to sort the navigation elements with the `order` attribute from the `Routes Service`.
- When you want to add the `Navigation Element` you can use the `RoutesService`. For more details, see the [document](https://docs.abp.io/en/abp/latest/UI/Angular/Modifying-the-Menu#how-to-add-a-navigation-element).
- However, in this documentation, we will talk more about how to sort the navigation elements.
### Order Property ### Order Property
- This parameter is optional and is used for sorting purposes.
- If you define this property it will be sorted by the default sorting function.
- You can edit this function.
**Default Compare Function;** - Normally, you are able to sort your routes with this property. But you can customize our default sorting algorithm.
``compare-func.token.ts``
## Default Sorting algorithm
- To see our default sorting algorithm [click](https://github.com/abpframework/abp/blob/dev/npm/ng-packs/packages/core/src/lib/tokens/compare-func.token.ts) here.
**What does this function do?**
- if the order property is defined, then it will be sorted by the order value.
- if both of the navigation elements have the same order value then it will be sorted by the name.
- If the order property is not defined, it will be the last element and the unordered navs will be sorted by name.
# How to Customize
**`in app.module.ts`**
```ts ```ts
export const SORT_COMPARE_FUNC = new InjectionToken<0 | 1 | -1>('SORT_COMPARE_FUNC'); import { SORT_COMPARE_FUNC } from "@abp/ng.core";
export function compareFuncFactory() {
const localizationService = inject(LocalizationService);
const fn = (a,b) => {
const aName = localizationService.instant(a.name);
const bName = localizationService.instant(b.name);
const aNumber = a.order;
const bNumber = b.order;
if (!Number.isInteger(aNumber)) return 1;
if (!Number.isInteger(bNumber)) return -1;
if (aNumber > bNumber) return 1
if (aNumber < bNumber) return -1
if (aName > bName ) return 1;
if (aName < bName ) return -1;
return 0
}
return fn;
}
```
**What does this function do?**
- if the order property is defined, then it will be sorted by the order value.
- if both of the navigation elements have the same order value then it will be sorted by the name.
- If the order property is not defined, it will be the last element and the unordered navs will be sorted by name.
You can edit this sorting function behaviour as you wish. @NgModule({
providers: [
...{
provide: SORT_COMPARE_FUNC,
useFactory: yourCompareFuncFactory,
},
],
// imports, declarations, and bootstrap
})
export class AppModule {}
```

BIN
docs/en/images/book-mastering-abp-framework.png

Binary file not shown.

After

Width:  |  Height:  |  Size: 244 KiB

10
docs/zh-Hans/Distributed-Event-Bus-RabbitMQ-Integration.md

@ -152,4 +152,14 @@ Configure<AbpRabbitMqEventBusOptions>(options =>
}); });
```` ````
**示例:配置队列和交换机的额外参数**
```csharp
Configure<AbpRabbitMqEventBusOptions>(options =>
{
options.ExchangeArguments["x-delayed-type"] = "direct";
options.QueueArguments["x-message-ttl"] = 60000;
});
```
使用这些选项类可以与 `appsettings.json` 组合在一起. 在代码中配置选项属性会覆盖配置文件中的值. 使用这些选项类可以与 `appsettings.json` 组合在一起. 在代码中配置选项属性会覆盖配置文件中的值.

9
framework/src/Volo.Abp.AspNetCore.Components.Server/Volo/Abp/AspNetCore/Components/Server/AbpAspNetCoreComponentsServerModule.cs

@ -1,5 +1,7 @@
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Net;
using System.Net.Http;
using Microsoft.AspNetCore.Builder; using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting.StaticWebAssets; using Microsoft.AspNetCore.Hosting.StaticWebAssets;
using Microsoft.AspNetCore.Http.Connections; using Microsoft.AspNetCore.Http.Connections;
@ -8,6 +10,7 @@ using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.FileProviders; using Microsoft.Extensions.FileProviders;
using Microsoft.Extensions.Hosting; using Microsoft.Extensions.Hosting;
using Volo.Abp.AspNetCore.Auditing; using Volo.Abp.AspNetCore.Auditing;
using Volo.Abp.AspNetCore.Components.Server.Extensibility;
using Volo.Abp.AspNetCore.Components.Web; using Volo.Abp.AspNetCore.Components.Web;
using Volo.Abp.AspNetCore.Mvc; using Volo.Abp.AspNetCore.Mvc;
using Volo.Abp.AspNetCore.SignalR; using Volo.Abp.AspNetCore.SignalR;
@ -30,7 +33,11 @@ public class AbpAspNetCoreComponentsServerModule : AbpModule
public override void ConfigureServices(ServiceConfigurationContext context) public override void ConfigureServices(ServiceConfigurationContext context)
{ {
StaticWebAssetsLoader.UseStaticWebAssets(context.Services.GetHostingEnvironment(), context.Services.GetConfiguration()); StaticWebAssetsLoader.UseStaticWebAssets(context.Services.GetHostingEnvironment(), context.Services.GetConfiguration());
context.Services.AddHttpClient(); context.Services.AddHttpClient(nameof(BlazorServerLookupApiRequestService))
.ConfigurePrimaryHttpMessageHandler(() => new HttpClientHandler
{
AutomaticDecompression = DecompressionMethods.All
});
var serverSideBlazorBuilder = context.Services.AddServerSideBlazor(options => var serverSideBlazorBuilder = context.Services.AddServerSideBlazor(options =>
{ {
if (context.Services.GetHostingEnvironment().IsDevelopment()) if (context.Services.GetHostingEnvironment().IsDevelopment())

20
framework/src/Volo.Abp.AspNetCore.Components.Server/Volo/Abp/AspNetCore/Components/Server/Extensibility/BlazorServerLookupApiRequestService.cs

@ -41,27 +41,25 @@ public class BlazorServerLookupApiRequestService : ILookupApiRequestService, ITr
public async Task<string> SendAsync(string url) public async Task<string> SendAsync(string url)
{ {
var client = HttpClientFactory.CreateClient(); var client = HttpClientFactory.CreateClient(nameof(BlazorServerLookupApiRequestService));
var requestMessage = new HttpRequestMessage(HttpMethod.Get, url); var requestMessage = new HttpRequestMessage(HttpMethod.Get, url);
var uri = new Uri(url, UriKind.RelativeOrAbsolute); var uri = new Uri(url, UriKind.RelativeOrAbsolute);
if (!uri.IsAbsoluteUri) if (!uri.IsAbsoluteUri)
{ {
var baseUrl = string.Empty; var remoteServiceConfig = await RemoteServiceConfigurationProvider.GetConfigurationOrDefaultOrNullAsync("Default");
try if (remoteServiceConfig != null)
{ {
//Blazor tiered -- mode // Blazor tiered mode
var remoteServiceConfig = await RemoteServiceConfigurationProvider.GetConfigurationOrDefaultAsync("Default"); var baseUrl = remoteServiceConfig.BaseUrl;
baseUrl = remoteServiceConfig.BaseUrl;
client.BaseAddress = new Uri(baseUrl); client.BaseAddress = new Uri(baseUrl);
AddHeaders(requestMessage); AddHeaders(requestMessage);
await HttpClientAuthenticator.Authenticate(new RemoteServiceHttpClientAuthenticateContext(client, await HttpClientAuthenticator.Authenticate(new RemoteServiceHttpClientAuthenticateContext(client, requestMessage, new RemoteServiceConfiguration(baseUrl), string.Empty));
requestMessage, new RemoteServiceConfiguration(baseUrl), string.Empty));
} }
catch (AbpException) // Blazor-Server mode. else
{ {
baseUrl = NavigationManager.BaseUri; // Blazor server mode
client.BaseAddress = new Uri(baseUrl); client.BaseAddress = new Uri(NavigationManager.BaseUri);
foreach (var header in HttpContextAccessor.HttpContext!.Request.Headers) foreach (var header in HttpContextAccessor.HttpContext!.Request.Headers)
{ {
requestMessage.Headers.TryAddWithoutValidation(header.Key, header.Value.ToArray()); requestMessage.Headers.TryAddWithoutValidation(header.Key, header.Value.ToArray());

8
framework/src/Volo.Abp.AspNetCore.Components.WebAssembly/Volo/Abp/AspNetCore/Components/WebAssembly/Extensibility/WebAssemblyLookupApiRequestService.cs

@ -32,14 +32,18 @@ public class WebAssemblyLookupApiRequestService : ILookupApiRequestService, ITra
public async Task<string> SendAsync(string url) public async Task<string> SendAsync(string url)
{ {
var client = HttpClientFactory.CreateClient(); var client = HttpClientFactory.CreateClient(nameof(WebAssemblyLookupApiRequestService));
var requestMessage = new HttpRequestMessage(HttpMethod.Get, url); var requestMessage = new HttpRequestMessage(HttpMethod.Get, url);
AddHeaders(requestMessage); AddHeaders(requestMessage);
var uri = new Uri(url, UriKind.RelativeOrAbsolute); var uri = new Uri(url, UriKind.RelativeOrAbsolute);
if (!uri.IsAbsoluteUri) if (!uri.IsAbsoluteUri)
{ {
var remoteServiceConfig = await RemoteServiceConfigurationProvider.GetConfigurationOrDefaultAsync("Default"); var remoteServiceConfig = await RemoteServiceConfigurationProvider.GetConfigurationOrDefaultOrNullAsync("Default");
if (remoteServiceConfig == null)
{
throw new AbpException("Remote service configuration 'Default' was not found!");
}
client.BaseAddress = new Uri(remoteServiceConfig.BaseUrl); client.BaseAddress = new Uri(remoteServiceConfig.BaseUrl);
await HttpClientAuthenticator.Authenticate(new RemoteServiceHttpClientAuthenticateContext(client, requestMessage, new RemoteServiceConfiguration(remoteServiceConfig.BaseUrl), string.Empty)); await HttpClientAuthenticator.Authenticate(new RemoteServiceHttpClientAuthenticateContext(client, requestMessage, new RemoteServiceConfiguration(remoteServiceConfig.BaseUrl), string.Empty));
} }

4
framework/src/Volo.Abp.AspNetCore.Mvc.UI.Bootstrap/TagHelpers/Form/AbpInputTagHelperService.cs

@ -271,7 +271,7 @@ public class AbpInputTagHelperService : AbpTagHelperService<AbpInputTagHelper>
if (string.IsNullOrEmpty(TagHelper.Label)) if (string.IsNullOrEmpty(TagHelper.Label))
{ {
return await GetLabelAsHtmlUsingTagHelperAsync(context, output, isCheckbox) + GetRequiredSymbol(context, output); return await GetLabelAsHtmlUsingTagHelperAsync(context, output, isCheckbox);
} }
var label = new TagBuilder("label"); var label = new TagBuilder("label");
@ -392,6 +392,8 @@ public class AbpInputTagHelperService : AbpTagHelperService<AbpInputTagHelper>
} }
innerOutput.Content.AppendHtml($" <i class=\"{iconClass}\"></i>"); innerOutput.Content.AppendHtml($" <i class=\"{iconClass}\"></i>");
} }
innerOutput.Content.AppendHtml(GetRequiredSymbol(context, output));
return innerOutput.Render(_encoder); return innerOutput.Render(_encoder);
} }

11
framework/src/Volo.Abp.AspNetCore.Mvc.UI.Bootstrap/TagHelpers/Form/AbpSelectTagHelperService.cs

@ -185,11 +185,12 @@ public class AbpSelectTagHelperService : AbpTagHelperService<AbpSelectTagHelper>
label.AddCssClass("form-label"); label.AddCssClass("form-label");
label.Attributes.Add("for", GetIdAttributeValue(selectTag)); label.Attributes.Add("for", GetIdAttributeValue(selectTag));
label.InnerHtml.AppendHtml(_encoder.Encode(TagHelper.Label)); label.InnerHtml.AppendHtml(_encoder.Encode(TagHelper.Label));
label.InnerHtml.AppendHtml(GetRequiredSymbol(context, output));
return label.ToHtmlString() + GetRequiredSymbol(context, output); return label.ToHtmlString();
} }
return await GetLabelAsHtmlUsingTagHelperAsync(context, output) + GetRequiredSymbol(context, output); return await GetLabelAsHtmlUsingTagHelperAsync(context, output);
} }
protected virtual string GetRequiredSymbol(TagHelperContext context, TagHelperOutput output) protected virtual string GetRequiredSymbol(TagHelperContext context, TagHelperOutput output)
@ -304,7 +305,11 @@ public class AbpSelectTagHelperService : AbpTagHelperService<AbpSelectTagHelper>
ViewContext = TagHelper.ViewContext, ViewContext = TagHelper.ViewContext,
}; };
return await labelTagHelper.RenderAsync(new TagHelperAttributeList { { "class", "form-label" } }, context, _encoder, "label", TagMode.StartTagAndEndTag); var innerOutput = await labelTagHelper.ProcessAndGetOutputAsync(new TagHelperAttributeList { { "class", "form-label" } }, context, "label", TagMode.StartTagAndEndTag);
innerOutput.Content.AppendHtml(GetRequiredSymbol(context, output));
return innerOutput.Render(_encoder);
} }
protected virtual async Task<string> GetValidationAsHtmlAsync(TagHelperContext context, TagHelperOutput output, TagHelperOutput inputTag) protected virtual async Task<string> GetValidationAsHtmlAsync(TagHelperContext context, TagHelperOutput output, TagHelperOutput inputTag)

12
framework/src/Volo.Abp.AspNetCore.Mvc.UI.Theme.Shared/wwwroot/libs/abp/aspnetcore-mvc-ui-theme-shared/datatables/datatables-extensions.js

@ -32,6 +32,18 @@ var abp = abp || {};
} }
var _createDropdownItem = function (record, fieldItem, tableInstance) { var _createDropdownItem = function (record, fieldItem, tableInstance) {
if (fieldItem.divider) {
if (abp.utils.isFunction(fieldItem.divider)) {
return $(fieldItem.divider(record, tableInstance));
}
if (fieldItem.divider === true) {
return $('<li><hr class="dropdown-divider"></li>');
}
return $(fieldItem.divider);
}
var $li = $('<li/>'); var $li = $('<li/>');
var $a = $('<a/>').addClass('dropdown-item'); var $a = $('<a/>').addClass('dropdown-item');

1
framework/src/Volo.Abp.AspNetCore.Mvc/Volo/Abp/AspNetCore/Mvc/AspNetCoreApiDescriptionModelProvider.cs

@ -79,6 +79,7 @@ public class AspNetCoreApiDescriptionModelProvider : IApiDescriptionModelProvide
} }
} }
model.NormalizeOrder();
return model; return model;
} }

8
framework/src/Volo.Abp.AspNetCore.SignalR/Volo/Abp/AspNetCore/SignalR/AbpAspNetCoreSignalRModule.cs

@ -1,5 +1,6 @@
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq;
using System.Reflection; using System.Reflection;
using Microsoft.AspNetCore.Builder; using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Http.Connections; using Microsoft.AspNetCore.Http.Connections;
@ -54,10 +55,17 @@ public class AbpAspNetCoreSignalRModule : AbpModule
.GetRequiredService<IOptions<AbpSignalROptions>>() .GetRequiredService<IOptions<AbpSignalROptions>>()
.Value; .Value;
var hubWithRoutePatterns = new List<KeyValuePair<Type, string>>();
foreach (var hubConfig in signalROptions.Hubs) foreach (var hubConfig in signalROptions.Hubs)
{ {
routePatterns.AddIfNotContains(hubConfig.RoutePattern); routePatterns.AddIfNotContains(hubConfig.RoutePattern);
if (hubWithRoutePatterns.Any(x => x.Key == hubConfig.HubType && x.Value == hubConfig.RoutePattern))
{
throw new AbpException($"The hub type {hubConfig.HubType.FullName} is already registered with route pattern {hubConfig.RoutePattern}");
}
hubWithRoutePatterns.Add(new KeyValuePair<Type, string>(hubConfig.HubType, hubConfig.RoutePattern));
MapHubType( MapHubType(
hubConfig.HubType, hubConfig.HubType,
endpointContext.Endpoints, endpointContext.Endpoints,

44
framework/src/Volo.Abp.Autofac/Volo/Abp/Autofac/AutoFacInjectPropertiesService.cs

@ -0,0 +1,44 @@
using System;
using Autofac;
using Autofac.Extensions.DependencyInjection;
using Volo.Abp.DependencyInjection;
namespace Volo.Abp.Autofac;
public class AutoFacInjectPropertiesService : IInjectPropertiesService, ITransientDependency
{
protected IServiceProvider ServiceProvider { get; }
public AutoFacInjectPropertiesService(IServiceProvider serviceProvider)
{
ServiceProvider = serviceProvider;
}
public virtual TService InjectProperties<TService>(TService instance) where TService : notnull
{
return InjectProperties(instance, false);
}
public virtual TService InjectUnsetProperties<TService>(TService instance) where TService : notnull
{
return InjectProperties(instance, true);
}
protected virtual TService InjectProperties<TService>(TService instance, bool onlyForUnsetProperties)
where TService : notnull
{
if (instance == null)
{
throw new ArgumentNullException(nameof(instance));
}
if (ServiceProvider is not AutofacServiceProvider)
{
throw new AbpException($"The {nameof(ServiceProvider)} must be an instance of {nameof(AutofacServiceProvider)}!");
}
return onlyForUnsetProperties
? ServiceProvider.As<AutofacServiceProvider>().LifetimeScope.InjectUnsetProperties(instance)
: ServiceProvider.As<AutofacServiceProvider>().LifetimeScope.InjectProperties(instance);
}
}

2
framework/src/Volo.Abp.BlobStoring/Volo/Abp/BlobStoring/BlobContainer.cs

@ -179,7 +179,7 @@ public class BlobContainer : IBlobContainer
{ {
//TODO: Consider to throw some type of "not found" exception and handle on the HTTP status side //TODO: Consider to throw some type of "not found" exception and handle on the HTTP status side
throw new AbpException( throw new AbpException(
$"Could not found the requested BLOB '{name}' in the container '{ContainerName}'!"); $"Could not find the requested BLOB '{name}' in the container '{ContainerName}'!");
} }
return stream; return stream;

16
framework/src/Volo.Abp.Core/Volo/Abp/DependencyInjection/IInjectPropertiesService.cs

@ -0,0 +1,16 @@
using System;
namespace Volo.Abp.DependencyInjection;
public interface IInjectPropertiesService
{
/// <summary>
/// Set any properties on <paramref name="instance"/> that can be resolved by IServiceProvider.
/// </summary>
TService InjectProperties<TService>(TService instance) where TService : notnull;
/// <summary>
/// Set any null-valued properties on <paramref name="instance"/> that can be resolved by the IServiceProvider.
/// </summary>
TService InjectUnsetProperties<TService>(TService instance) where TService : notnull;
}

17
framework/src/Volo.Abp.Core/Volo/Abp/DependencyInjection/NullInjectPropertiesService.cs

@ -0,0 +1,17 @@
namespace Volo.Abp.DependencyInjection;
[Dependency(TryRegister = true)]
public class NullInjectPropertiesService : IInjectPropertiesService, ITransientDependency
{
public TService InjectProperties<TService>(TService instance)
where TService : notnull
{
return instance;
}
public TService InjectUnsetProperties<TService>(TService instance)
where TService : notnull
{
return instance;
}
}

9
framework/src/Volo.Abp.EventBus.RabbitMQ/Volo/Abp/EventBus/RabbitMq/AbpRabbitMqEventBusOptions.cs

@ -1,4 +1,5 @@
using Volo.Abp.RabbitMQ; using System.Collections.Generic;
using Volo.Abp.RabbitMQ;
namespace Volo.Abp.EventBus.RabbitMq; namespace Volo.Abp.EventBus.RabbitMq;
@ -13,9 +14,13 @@ public class AbpRabbitMqEventBusOptions
public string ExchangeName { get; set; } = default!; public string ExchangeName { get; set; } = default!;
public string? ExchangeType { get; set; } public string? ExchangeType { get; set; }
public ushort? PrefetchCount { get; set; } public ushort? PrefetchCount { get; set; }
public IDictionary<string, object> QueueArguments { get; set; } = new Dictionary<string, object>();
public IDictionary<string, object> ExchangeArguments { get; set; } = new Dictionary<string, object>();
public string GetExchangeTypeOrDefault() public string GetExchangeTypeOrDefault()
{ {
return string.IsNullOrEmpty(ExchangeType) return string.IsNullOrEmpty(ExchangeType)

6
framework/src/Volo.Abp.EventBus.RabbitMQ/Volo/Abp/EventBus/RabbitMq/RabbitMqDistributedEventBus.cs

@ -79,14 +79,16 @@ public class RabbitMqDistributedEventBus : DistributedEventBusBase, ISingletonDe
new ExchangeDeclareConfiguration( new ExchangeDeclareConfiguration(
AbpRabbitMqEventBusOptions.ExchangeName, AbpRabbitMqEventBusOptions.ExchangeName,
type: AbpRabbitMqEventBusOptions.GetExchangeTypeOrDefault(), type: AbpRabbitMqEventBusOptions.GetExchangeTypeOrDefault(),
durable: true durable: true,
arguments: AbpRabbitMqEventBusOptions.ExchangeArguments
), ),
new QueueDeclareConfiguration( new QueueDeclareConfiguration(
AbpRabbitMqEventBusOptions.ClientName, AbpRabbitMqEventBusOptions.ClientName,
durable: true, durable: true,
exclusive: false, exclusive: false,
autoDelete: false, autoDelete: false,
prefetchCount: AbpRabbitMqEventBusOptions.PrefetchCount prefetchCount: AbpRabbitMqEventBusOptions.PrefetchCount,
arguments: AbpRabbitMqEventBusOptions.QueueArguments
), ),
AbpRabbitMqEventBusOptions.ConnectionName AbpRabbitMqEventBusOptions.ConnectionName
); );

2
framework/src/Volo.Abp.ExceptionHandling/Volo/Abp/ExceptionHandling/Localization/en-GB.json

@ -11,7 +11,7 @@
"DefaultErrorMessage403": "You are not authorised!", "DefaultErrorMessage403": "You are not authorised!",
"DefaultErrorMessage403Detail": "You are not allowed to perform this operation!", "DefaultErrorMessage403Detail": "You are not allowed to perform this operation!",
"DefaultErrorMessage404": "Resource not found!", "DefaultErrorMessage404": "Resource not found!",
"DefaultErrorMessage404Detail": "The resource requested could not found on the server!", "DefaultErrorMessage404Detail": "The resource requested could not be found on the server!",
"EntityNotFoundErrorMessage": "There is no entity {0} with id = {1}!", "EntityNotFoundErrorMessage": "There is no entity {0} with id = {1}!",
"Error": "Error", "Error": "Error",
"UnhandledException": "Unhandled exception!", "UnhandledException": "Unhandled exception!",

2
framework/src/Volo.Abp.ExceptionHandling/Volo/Abp/ExceptionHandling/Localization/en.json

@ -11,7 +11,7 @@
"DefaultErrorMessage403": "You are not authorized!", "DefaultErrorMessage403": "You are not authorized!",
"DefaultErrorMessage403Detail": "You are not allowed to perform this operation!", "DefaultErrorMessage403Detail": "You are not allowed to perform this operation!",
"DefaultErrorMessage404": "Resource not found!", "DefaultErrorMessage404": "Resource not found!",
"DefaultErrorMessage404Detail": "The resource requested could not found on the server!", "DefaultErrorMessage404Detail": "The resource requested could not be found on the server!",
"EntityNotFoundErrorMessage": "There is no entity {0} with id = {1}!", "EntityNotFoundErrorMessage": "There is no entity {0} with id = {1}!",
"AbpDbConcurrencyErrorMessage": "The data you have submitted has already changed by another user/client. Please discard the changes you've done and try from the beginning.", "AbpDbConcurrencyErrorMessage": "The data you have submitted has already changed by another user/client. Please discard the changes you've done and try from the beginning.",
"Error": "Error", "Error": "Error",

2
framework/src/Volo.Abp.Http.Client/Volo/Abp/Http/Client/DynamicProxying/ApiDescriptionFinder.cs

@ -82,7 +82,7 @@ public class ApiDescriptionFinder : IApiDescriptionFinder, ITransientDependency
} }
} }
throw new AbpException($"Could not found remote action for method: {method} on the URL: {baseUrl}"); throw new AbpException($"Could not find remote action for method: {method} on the URL: {baseUrl}");
} }
public virtual async Task<ApplicationApiDescriptionModel> GetApiDescriptionAsync(HttpClient client, string baseUrl) public virtual async Task<ApplicationApiDescriptionModel> GetApiDescriptionAsync(HttpClient client, string baseUrl)

7
framework/src/Volo.Abp.Http/Volo/Abp/Http/Modeling/ApplicationApiDescriptionModel.cs

@ -22,7 +22,7 @@ public class ApplicationApiDescriptionModel
return new ApplicationApiDescriptionModel return new ApplicationApiDescriptionModel
{ {
Modules = new ConcurrentDictionary<string, ModuleApiDescriptionModel>(), //TODO: Why ConcurrentDictionary? Modules = new ConcurrentDictionary<string, ModuleApiDescriptionModel>(), //TODO: Why ConcurrentDictionary?
Types = new Dictionary<string, TypeApiDescriptionModel>() Types = new SortedDictionary<string, TypeApiDescriptionModel>()
}; };
} }
@ -55,4 +55,9 @@ public class ApplicationApiDescriptionModel
return subModel; return subModel;
} }
public void NormalizeOrder()
{
Modules = Modules.OrderBy(x => x.Key).ToDictionary(x => x.Key, x => x.Value);
}
} }

2
framework/src/Volo.Abp.Http/Volo/Abp/Http/Modeling/ModuleApiDescriptionModel.cs

@ -35,7 +35,7 @@ public class ModuleApiDescriptionModel
{ {
RootPath = rootPath, RootPath = rootPath,
RemoteServiceName = remoteServiceName, RemoteServiceName = remoteServiceName,
Controllers = new Dictionary<string, ControllerApiDescriptionModel>() Controllers = new SortedDictionary<string, ControllerApiDescriptionModel>()
}; };
} }

5
framework/src/Volo.Abp.RabbitMQ/Volo/Abp/RabbitMQ/ExchangeDeclareConfiguration.cs

@ -18,12 +18,13 @@ public class ExchangeDeclareConfiguration
string exchangeName, string exchangeName,
string type, string type,
bool durable = false, bool durable = false,
bool autoDelete = false) bool autoDelete = false,
IDictionary<string, object>? arguments = null)
{ {
ExchangeName = exchangeName; ExchangeName = exchangeName;
Type = type; Type = type;
Durable = durable; Durable = durable;
AutoDelete = autoDelete; AutoDelete = autoDelete;
Arguments = new Dictionary<string, object>(); Arguments = arguments?? new Dictionary<string, object>();
} }
} }

5
framework/src/Volo.Abp.RabbitMQ/Volo/Abp/RabbitMQ/QueueDeclareConfiguration.cs

@ -23,13 +23,14 @@ public class QueueDeclareConfiguration
bool durable = true, bool durable = true,
bool exclusive = false, bool exclusive = false,
bool autoDelete = false, bool autoDelete = false,
ushort? prefetchCount = null) ushort? prefetchCount = null,
IDictionary<string, object>? arguments = null)
{ {
QueueName = queueName; QueueName = queueName;
Durable = durable; Durable = durable;
Exclusive = exclusive; Exclusive = exclusive;
AutoDelete = autoDelete; AutoDelete = autoDelete;
Arguments = new Dictionary<string, object>(); Arguments = arguments?? new Dictionary<string, object>();
PrefetchCount = prefetchCount; PrefetchCount = prefetchCount;
} }

2
framework/test/Volo.Abp.AspNetCore.SignalR.Tests/Volo.Abp.AspNetCore.SignalR.Tests.csproj

@ -14,7 +14,7 @@
<ItemGroup> <ItemGroup>
<ProjectReference Include="..\..\src\Volo.Abp.AspNetCore.SignalR\Volo.Abp.AspNetCore.SignalR.csproj" /> <ProjectReference Include="..\..\src\Volo.Abp.AspNetCore.SignalR\Volo.Abp.AspNetCore.SignalR.csproj" />
<ProjectReference Include="..\..\src\Volo.Abp.Autofac\Volo.Abp.Autofac.csproj" /> <ProjectReference Include="..\..\src\Volo.Abp.Autofac\Volo.Abp.Autofac.csproj" />
<ProjectReference Include="..\AbpTestBase\AbpTestBase.csproj" /> <ProjectReference Include="..\Volo.Abp.AspNetCore.Tests\Volo.Abp.AspNetCore.Tests.csproj" />
</ItemGroup> </ItemGroup>
</Project> </Project>

24
framework/test/Volo.Abp.AspNetCore.SignalR.Tests/Volo/Abp/AspNetCore/SignalR/AbpAspNetCoreSignalRTestModule.cs

@ -1,14 +1,34 @@
using Volo.Abp.Autofac; using System;
using Microsoft.AspNetCore.Builder;
using Volo.Abp.AspNetCore.TestBase;
using Volo.Abp.Autofac;
using Volo.Abp.Modularity; using Volo.Abp.Modularity;
namespace Volo.Abp.AspNetCore.SignalR; namespace Volo.Abp.AspNetCore.SignalR;
[DependsOn( [DependsOn(
typeof(AbpAspNetCoreSignalRModule), typeof(AbpAspNetCoreSignalRModule),
typeof(AbpTestBaseModule), typeof(AbpAspNetCoreTestBaseModule),
typeof(AbpAutofacModule) typeof(AbpAutofacModule)
)] )]
public class AbpAspNetCoreSignalRTestModule : AbpModule public class AbpAspNetCoreSignalRTestModule : AbpModule
{ {
public static Exception UseConfiguredEndpointsException { get; set; }
public override void OnApplicationInitialization(ApplicationInitializationContext context)
{
var app = context.GetApplicationBuilder();
app.UseRouting();
UseConfiguredEndpointsException = null;
try
{
app.UseConfiguredEndpoints();
}
catch (Exception e)
{
UseConfiguredEndpointsException = e;
}
}
} }

70
framework/test/Volo.Abp.AspNetCore.SignalR.Tests/Volo/Abp/AspNetCore/SignalR/AbpSignalROptions_Tests.cs

@ -1,11 +1,13 @@
using Microsoft.Extensions.Options; using System.Linq;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Options;
using Shouldly; using Shouldly;
using Volo.Abp.AspNetCore.SignalR.SampleHubs; using Volo.Abp.AspNetCore.SignalR.SampleHubs;
using Xunit; using Xunit;
namespace Volo.Abp.AspNetCore.SignalR; namespace Volo.Abp.AspNetCore.SignalR;
public class AbpSignalROptions_Tests : AbpAspNetCoreSignalRTestBase public class AbpSignalROptions_Tests : AbpAspNetCoreTestBase<Program>
{ {
private readonly AbpSignalROptions _options; private readonly AbpSignalROptions _options;
@ -14,12 +16,74 @@ public class AbpSignalROptions_Tests : AbpAspNetCoreSignalRTestBase
_options = GetRequiredService<IOptions<AbpSignalROptions>>().Value; _options = GetRequiredService<IOptions<AbpSignalROptions>>().Value;
} }
[Fact(Skip = "Can not run this test since AspNet Core environment has not been properly set!")] protected override void ConfigureServices(IServiceCollection services)
{
services.AddTransient<RegularHubClass1>();
services.AddTransient<RegularHubClass12>();
services.AddTransient<RegularHubClass2>();
services.AddTransient<RegularHubClass22>();
}
[Fact]
public void Should_Auto_Add_Maps() public void Should_Auto_Add_Maps()
{ {
_options.Hubs.ShouldContain(h => h.HubType == typeof(RegularHub)); _options.Hubs.ShouldContain(h => h.HubType == typeof(RegularHub));
_options.Hubs.ShouldContain(h => h.HubType == typeof(RegularAbpHub)); _options.Hubs.ShouldContain(h => h.HubType == typeof(RegularAbpHub));
_options.Hubs.ShouldNotContain(h => h.HubType == typeof(DisableConventionalRegistrationHub)); _options.Hubs.ShouldNotContain(h => h.HubType == typeof(DisableConventionalRegistrationHub));
_options.Hubs.ShouldNotContain(h => h.HubType == typeof(DisableAutoHubMapHub)); _options.Hubs.ShouldNotContain(h => h.HubType == typeof(DisableAutoHubMapHub));
_options.Hubs.ShouldContain(h => h.HubType == typeof(RegularHubClass1));
_options.Hubs.ShouldContain(h => h.HubType == typeof(RegularHubClass12));
_options.Hubs.ShouldContain(h => h.HubType == typeof(RegularHubClass2));
_options.Hubs.ShouldContain(h => h.HubType == typeof(RegularHubClass22));
}
}
[Collection("AbpAspNetCoreSignalR")]
public class AbpSignalSameRroutePattern_Tests : AbpAspNetCoreTestBase<Program>
{
protected override void ConfigureServices(IServiceCollection services)
{
services.AddTransient<RegularHubClass1>();
services.AddTransient<RegularHubClass12>();
services.AddTransient<RegularHubClass1, RegularHubClass12>();
}
[Fact]
public void Should_Throw_Exception_If_HubType_Has_Same_RoutePattern()
{
AbpAspNetCoreSignalRTestModule.UseConfiguredEndpointsException.ShouldNotBeNull();
AbpAspNetCoreSignalRTestModule.UseConfiguredEndpointsException.Message.ShouldBe($"The hub type {typeof(RegularHubClass12).FullName} is already registered with route pattern {HubRouteAttribute.GetRoutePattern(typeof(RegularHubClass12))}");
}
}
[Collection("AbpAspNetCoreSignalR")]
public class AbpSignalDifferentRroutePattern_Tests : AbpAspNetCoreTestBase<Program>
{
protected override void ConfigureServices(IServiceCollection services)
{
services.AddTransient<RegularHubClass2>();
services.AddTransient<RegularHubClass22>();
services.AddTransient<RegularHubClass2, RegularHubClass22>();
services.Configure<AbpSignalROptions>(options =>
{
var firstHub = options.Hubs.FirstOrDefault(x => x.HubType == typeof(RegularHubClass22));
if (firstHub != null)
{
firstHub.RoutePattern = "/signalr-hubs/regular-hub-class-22";
}
var lastHub = options.Hubs.LastOrDefault(x => x.HubType == typeof(RegularHubClass22));
if (lastHub != null)
{
lastHub.RoutePattern = "/signalr-hubs/regular-hub-class-22-1";
}
});
}
[Fact]
public void Should_Work_If_Same_HubType_Has_Different_RoutePattern()
{
AbpAspNetCoreSignalRTestModule.UseConfiguredEndpointsException.ShouldBeNull();
} }
} }

10
framework/test/Volo.Abp.AspNetCore.SignalR.Tests/Volo/Abp/AspNetCore/SignalR/Program.cs

@ -0,0 +1,10 @@
using Microsoft.AspNetCore.Builder;
using Volo.Abp.AspNetCore.SignalR;
using Volo.Abp.AspNetCore.TestBase;
var builder = WebApplication.CreateBuilder();
await builder.RunAbpModuleAsync<AbpAspNetCoreSignalRTestModule>();
public partial class Program
{
}

37
framework/test/Volo.Abp.AspNetCore.SignalR.Tests/Volo/Abp/AspNetCore/SignalR/SampleHubs/RegularHubBase.cs

@ -0,0 +1,37 @@
using Microsoft.AspNetCore.SignalR;
using Volo.Abp.DependencyInjection;
namespace Volo.Abp.AspNetCore.SignalR.SampleHubs;
public abstract class RegularHubBase<THub> : Hub<THub> where THub : class
{
}
[DisableConventionalRegistration]
[ExposeServices(typeof(RegularHubClass1))]
public class RegularHubClass1 : RegularHubBase<RegularHubClass1>
{
}
[DisableConventionalRegistration]
[ExposeServices(typeof(RegularHubClass12), typeof(RegularHubClass1))]
public class RegularHubClass12 : RegularHubClass1
{
}
[DisableConventionalRegistration]
[ExposeServices(typeof(RegularHubClass2))]
public class RegularHubClass2 : RegularHubBase<RegularHubClass2>
{
}
[DisableConventionalRegistration]
[ExposeServices(typeof(RegularHubClass22), typeof(RegularHubClass2))]
public class RegularHubClass22 : RegularHubClass2
{
}

67
framework/test/Volo.Abp.Autofac.Tests/Volo/Abp/Autofac/AutoFacInjectingPropertiesService_Tests.cs

@ -0,0 +1,67 @@
using Microsoft.Extensions.DependencyInjection;
using Shouldly;
using Volo.Abp.Autofac.Interception;
using Volo.Abp.DependencyInjection;
using Xunit;
namespace Volo.Abp.Autofac;
public class AutoFacInjectingPropertiesService_Tests : Autofac_Interception_Test
{
[Fact]
public void AutoFacInjectingPropertiesService_Should_Replaces_NullInjectingPropertiesService()
{
ServiceProvider.GetRequiredService<IInjectPropertiesService>().GetType().ShouldBe(typeof(AutoFacInjectPropertiesService));
}
[Fact]
public void InjectProperties()
{
var injectPropertiesService = ServiceProvider.GetRequiredService<IInjectPropertiesService>();
var serviceB = new TestServiceB();
injectPropertiesService.InjectProperties(serviceB);
serviceB.NullTestServiceA.ShouldNotBeNull();
serviceB.NullTestServiceA.Name.ShouldBe("Default Name");
serviceB.NotNullTestServiceA.ShouldNotBeNull();
serviceB.NotNullTestServiceA.Name.ShouldBe("Default Name");
}
[Fact]
public void InjectUnsetProperties()
{
var injectPropertiesService = ServiceProvider.GetRequiredService<IInjectPropertiesService>();
var serviceB = new TestServiceB();
injectPropertiesService.InjectUnsetProperties(serviceB);
serviceB.NullTestServiceA.ShouldNotBeNull();
serviceB.NullTestServiceA.Name.ShouldBe("Default Name");
serviceB.NotNullTestServiceA.ShouldNotBeNull();
serviceB.NotNullTestServiceA.Name.ShouldBe("My Name"); // This is not null property.
}
}
interface ITestServiceA
{
public string Name { get; set; }
}
class TestServiceA : ITestServiceA, ITransientDependency
{
public string Name { get; set; } = "Default Name";
}
interface ITestServiceB
{
}
class TestServiceB : ITestServiceB, ITransientDependency
{
public ITestServiceA NullTestServiceA { get; set; }
public ITestServiceA NotNullTestServiceA { get; set; } = new TestServiceA()
{
Name = "My Name"
};
}

2
framework/test/Volo.Abp.BlobStoring.Tests/Volo/Abp/BlobStoring/BlobContainer_Tests.cs

@ -61,7 +61,7 @@ public abstract class BlobContainer_Tests<TStartupModule> : AbpIntegratedTest<TS
using (CurrentTenant.Change(null)) using (CurrentTenant.Change(null))
{ {
// Could not found the requested BLOB... // Could not find the requested BLOB...
await Assert.ThrowsAsync<AbpException>(async () => await Assert.ThrowsAsync<AbpException>(async () =>
await Container.GetAllBytesAsync(blobName) await Container.GetAllBytesAsync(blobName)
); );

2
latest-versions.json

@ -1,6 +1,6 @@
[ [
{ {
"version": "7.4.2", "version": "7.4.4",
"releaseDate": "", "releaseDate": "",
"type": "stable", "type": "stable",
"message": "" "message": ""

62
modules/audit-logging/src/Volo.Abp.AuditLogging.Domain.Shared/Volo/Abp/AuditLogging/Localization/en.json

@ -1,18 +1,18 @@
{ {
"culture": "en", "culture": "en",
"texts": { "texts": {
"Permission:AuditLogging": "Audit Logging", "Permission:AuditLogging": "Audit logging",
"Permission:AuditLogs": "Audit Logs", "Permission:AuditLogs": "Audit logs",
"Menu:AuditLogging": "Audit Logs", "Menu:AuditLogging": "Audit logs",
"AuditLogs": "Audit Logs", "AuditLogs": "Audit logs",
"HttpStatus": "HTTP Status", "HttpStatus": "HTTP status",
"HttpMethod": "HTTP Method", "HttpMethod": "HTTP method",
"HttpMethodFilter": "HTTP Method Filter", "HttpMethodFilter": "HTTP method filter",
"HttpRequest": "HTTP Request", "HttpRequest": "HTTP Request",
"User": "User", "User": "User",
"UserNameFilter": "User Filter", "UserNameFilter": "User filter",
"HasException": "Has Exception", "HasException": "Has exception",
"IpAddress": "IP Address", "IpAddress": "IP address",
"Time": "Time", "Time": "Time",
"Date": "Date", "Date": "Date",
"Duration": "Duration", "Duration": "Duration",
@ -23,33 +23,33 @@
"ClientName": "Client Name", "ClientName": "Client Name",
"BrowserInfo": "Browser Info", "BrowserInfo": "Browser Info",
"Url": "URL", "Url": "URL",
"UserName": "User Name", "UserName": "User name",
"TenantImpersonator": "Tenant Impersonator", "TenantImpersonator": "Tenant Impersonator",
"UserImpersonator": "User Impersonator", "UserImpersonator": "User Impersonator",
"UrlFilter": "URL Filter", "UrlFilter": "URL filter",
"Exceptions": "Exceptions", "Exceptions": "Exceptions",
"Comments": "Comments", "Comments": "Comments",
"HttpStatusCode": "HTTP Status Code", "HttpStatusCode": "HTTP status code",
"HttpStatusCodeFilter": "HTTP Status Code Filter", "HttpStatusCodeFilter": "HTTP status code filter",
"ServiceName": "Service", "ServiceName": "Service",
"MethodName": "Method", "MethodName": "Method",
"CorrelationId": "Correlation Id", "CorrelationId": "Correlation Id",
"ApplicationName": "Application Name", "ApplicationName": "Application name",
"ExecutionDuration": "Duration", "ExecutionDuration": "Duration",
"ExtraProperties": "Extra properties", "ExtraProperties": "Extra properties",
"MaxDuration": "Max. Duration", "MaxDuration": "Max. duration",
"MinDuration": "Min. Duration", "MinDuration": "Min. duration",
"MinMaxDuration": "Duration (Min. - Max.)", "MinMaxDuration": "Duration (Min. - Max.)",
"{0}Milliseconds": "{0} milliseconds", "{0}Milliseconds": "{0} milliseconds",
"ExecutionTime": "Time", "ExecutionTime": "Time",
"Parameters": "Parameters", "Parameters": "Parameters",
"EntityTypeFullName": "Entity Type Full Name", "EntityTypeFullName": "Entity Type Full Name",
"Entity": "Entity", "Entity": "Entity",
"ChangeType": "Change Type", "ChangeType": "Change type",
"ChangeTime": "Time", "ChangeTime": "Time",
"NewValue": "New Value", "NewValue": "New value",
"OriginalValue": "Original Value", "OriginalValue": "Original value",
"PropertyName": "Property Name", "PropertyName": "Property name",
"PropertyTypeFullName": "Property Type Full Name", "PropertyTypeFullName": "Property Type Full Name",
"Yes": "Yes", "Yes": "Yes",
"No": "No", "No": "No",
@ -60,23 +60,23 @@
"Success": "Success", "Success": "Success",
"Fault": "Fault", "Fault": "Fault",
"NoChanges": "No change(s)", "NoChanges": "No change(s)",
"EntityChanges": "Entity Changes", "EntityChanges": "Entity changes",
"EntityId": "Entity Id", "EntityId": "Entity Id",
"EntityChangeStartTime": "Min Change Date", "EntityChangeStartTime": "Min change date",
"EntityChangeEndTime": "Max Change Date", "EntityChangeEndTime": "Max change date",
"EntityHistory": "Entity History", "EntityHistory": "Entity history",
"DaysAgoTitle": "{0} {1}.", "DaysAgoTitle": "{0} {1}.",
"DaysAgoWithUserTitle": "{0} {1} by {2}.", "DaysAgoWithUserTitle": "{0} {1} by {2}.",
"Created": "Created", "Created": "Created",
"Updated": "Updated", "Updated": "Updated",
"Deleted": "Deleted", "Deleted": "Deleted",
"ChangeHistory": "Change History", "ChangeHistory": "Change history",
"FullChangeHistory": "Full Change History", "FullChangeHistory": "Full change history",
"ChangeDetails": "Change Details", "ChangeDetails": "Change details",
"DurationMs": "Duration (ms)", "DurationMs": "Duration (ms)",
"StartDate": "Start Date", "StartDate": "Start date",
"EndDate": "End Date", "EndDate": "End date",
"Feature:AuditLoggingGroup": "Audit Logging", "Feature:AuditLoggingGroup": "Audit logging",
"Feature:AuditLoggingEnable": "Enabled audit logging page", "Feature:AuditLoggingEnable": "Enabled audit logging page",
"Feature:AuditLoggingEnableDescription": "Enable audit logging page in the application." "Feature:AuditLoggingEnableDescription": "Enable audit logging page in the application."
} }

4
modules/audit-logging/src/Volo.Abp.AuditLogging.Domain.Shared/Volo/Abp/AuditLogging/Localization/tr.json

@ -53,9 +53,9 @@
"Yes": "Evet", "Yes": "Evet",
"No": "Hayır", "No": "Hayır",
"UserNameFilter": "Kullanıcı Filtresi", "UserNameFilter": "Kullanıcı Filtresi",
"AverageExecutionDurationInLogsPerDay": "Ortalama işlem süresi", "AverageExecutionDurationInLogsPerDay": "Ortalama İşlem Süresi",
"AverageExecutionDurationInMilliseconds": "Milisaniye cinsinden ortalama işlem süresi", "AverageExecutionDurationInMilliseconds": "Milisaniye cinsinden ortalama işlem süresi",
"ErrorRateInLogs": "Loglardaki hata oranı", "ErrorRateInLogs": "Loglardaki Hata Oranı",
"Success": "Başarılı", "Success": "Başarılı",
"Fault": "Hatalı", "Fault": "Hatalı",
"NoChanges": "Değişiklik yok", "NoChanges": "Değişiklik yok",

74
modules/cms-kit/src/Volo.CmsKit.Domain.Shared/Volo/CmsKit/Localization/Resources/en.json

@ -7,7 +7,7 @@
"BlogFeatureNotAvailable": "This feature is not available now. Enable with 'GlobalFeatureManager' to use it.", "BlogFeatureNotAvailable": "This feature is not available now. Enable with 'GlobalFeatureManager' to use it.",
"BlogId": "Blog", "BlogId": "Blog",
"BlogPostDeletionConfirmationMessage": "The blog post '{0}' will be deleted. Are you sure?", "BlogPostDeletionConfirmationMessage": "The blog post '{0}' will be deleted. Are you sure?",
"BlogPosts": "Blog Posts", "BlogPosts": "Blog posts",
"Blogs": "Blogs", "Blogs": "Blogs",
"ChoosePreference": "Choose Preference...", "ChoosePreference": "Choose Preference...",
"Cms": "CMS", "Cms": "CMS",
@ -32,18 +32,18 @@
"Content": "Content", "Content": "Content",
"ContentDeletionConfirmationMessage": "Are you sure to delete this content?", "ContentDeletionConfirmationMessage": "Are you sure to delete this content?",
"Contents": "Contents", "Contents": "Contents",
"CoverImage": "Cover Image", "CoverImage": "Cover image",
"CreateBlogPostPage": "New Blog Post", "CreateBlogPostPage": "New blog post",
"CreationTime": "Creation Time", "CreationTime": "Creation time",
"Delete": "Delete", "Delete": "Delete",
"Detail": "Detail", "Detail": "Detail",
"Details": "Details", "Details": "Details",
"DisplayName": "Display Name", "DisplayName": "Display name",
"DoYouPreferAdditionalEmails": "Do you prefer additional emails?", "DoYouPreferAdditionalEmails": "Do you prefer additional emails?",
"Edit": "Edit", "Edit": "Edit",
"EndDate": "End Date", "EndDate": "End date",
"EntityId": "Entity Id", "EntityId": "Entity Id",
"EntityType": "Entity Type", "EntityType": "Entity type",
"ExportCSV": "Export CSV", "ExportCSV": "Export CSV",
"Features": "Features", "Features": "Features",
"GenericDeletionConfirmationMessage": "Are you sure to delete '{0}'?", "GenericDeletionConfirmationMessage": "Are you sure to delete '{0}'?",
@ -55,21 +55,21 @@
"LoginToReact": "Login to react", "LoginToReact": "Login to react",
"LoginToReply": "Login to reply", "LoginToReply": "Login to reply",
"MainMenu": "Main Menu", "MainMenu": "Main Menu",
"MakeMainMenu": "Make Main Menu", "MakeMainMenu": "Make main menu",
"Menu:CMS": "CMS", "Menu:CMS": "CMS",
"Menus": "Menus", "Menus": "Menus",
"MenuDeletionConfirmationMessage": "The menu '{0}' will be deleted. Are you sure?", "MenuDeletionConfirmationMessage": "The menu '{0}' will be deleted. Are you sure?",
"MenuItemDeletionConfirmationMessage": "Are sure to delete this menu item?", "MenuItemDeletionConfirmationMessage": "Are sure to delete this menu item?",
"MenuItemMoveConfirmMessage": "Are you sure you want to move '{0}' under '{1}'?", "MenuItemMoveConfirmMessage": "Are you sure you want to move '{0}' under '{1}'?",
"MenuItems": "Menu Items", "MenuItems": "Menu items",
"Message": "Message", "Message": "Message",
"MessageDeletionConfirmationMessage": "This comment will be deleted completely.", "MessageDeletionConfirmationMessage": "This comment will be deleted completely.",
"NewBlog": "New Blog", "NewBlog": "New blog",
"NewBlogPost": "New Blog Post", "NewBlogPost": "New blog post",
"NewMenu": "New Menu", "NewMenu": "New menu",
"NewMenuItem": "New Root Menu Item", "NewMenuItem": "New root menu item",
"NewPage": "New Page", "NewPage": "New page",
"NewTag": "New Tag", "NewTag": "New tag",
"NoMenuItems": "There is no menu item yet!", "NoMenuItems": "There is no menu item yet!",
"OK": "OK", "OK": "OK",
"PageDeletionConfirmationMessage": "Are you sure to delete this page?", "PageDeletionConfirmationMessage": "Are you sure to delete this page?",
@ -77,50 +77,50 @@
"Pages": "Pages", "Pages": "Pages",
"PageSlugInformation": "Slug is used on url. Your url will be '/{{slug}}'.", "PageSlugInformation": "Slug is used on url. Your url will be '/{{slug}}'.",
"BlogSlugInformation": "Slug is used on url. Your url will be '/{0}/{{slug}}'.", "BlogSlugInformation": "Slug is used on url. Your url will be '/{0}/{{slug}}'.",
"Permission:BlogManagement": "Blog Management", "Permission:BlogManagement": "Blog management",
"Permission:BlogManagement.Create": "Create", "Permission:BlogManagement.Create": "Create",
"Permission:BlogManagement.Delete": "Delete", "Permission:BlogManagement.Delete": "Delete",
"Permission:BlogManagement.Features": "Features", "Permission:BlogManagement.Features": "Features",
"Permission:BlogManagement.Update": "Update", "Permission:BlogManagement.Update": "Update",
"Permission:BlogPostManagement": "Blog Post Management", "Permission:BlogPostManagement": "Blog post management",
"Permission:BlogPostManagement.Create": "Create", "Permission:BlogPostManagement.Create": "Create",
"Permission:BlogPostManagement.Delete": "Delete", "Permission:BlogPostManagement.Delete": "Delete",
"Permission:BlogPostManagement.Update": "Update", "Permission:BlogPostManagement.Update": "Update",
"Permission:BlogPostManagement.Publish": "Publish", "Permission:BlogPostManagement.Publish": "Publish",
"Permission:CmsKit": "CmsKit Admin", "Permission:CmsKit": "CmsKit admin",
"Permission:Comments": "Comment Management", "Permission:Comments": "Comment management",
"Permission:Comments.Delete": "Delete", "Permission:Comments.Delete": "Delete",
"Permission:Contents": "Content Management", "Permission:Contents": "Content management",
"Permission:Contents.Create": "Create Content", "Permission:Contents.Create": "Create content",
"Permission:Contents.Delete": "Delete Content", "Permission:Contents.Delete": "Delete content",
"Permission:Contents.Update": "Update Content", "Permission:Contents.Update": "Update content",
"Permission:MediaDescriptorManagement": "Media Management", "Permission:MediaDescriptorManagement": "Media management",
"Permission:MediaDescriptorManagement:Create": "Create", "Permission:MediaDescriptorManagement:Create": "Create",
"Permission:MediaDescriptorManagement:Delete": "Delete", "Permission:MediaDescriptorManagement:Delete": "Delete",
"Permission:MenuItemManagement": "Menu Item Management", "Permission:MenuItemManagement": "Menu item management",
"Permission:MenuItemManagement.Create": "Create", "Permission:MenuItemManagement.Create": "Create",
"Permission:MenuItemManagement.Delete": "Delete", "Permission:MenuItemManagement.Delete": "Delete",
"Permission:MenuItemManagement.Update": "Update", "Permission:MenuItemManagement.Update": "Update",
"Permission:MenuManagement": "Menu Management", "Permission:MenuManagement": "Menu management",
"Permission:MenuManagement.Create": "Create", "Permission:MenuManagement.Create": "Create",
"Permission:MenuManagement.Delete": "Delete", "Permission:MenuManagement.Delete": "Delete",
"Permission:MenuManagement.Update": "Update", "Permission:MenuManagement.Update": "Update",
"Permission:Menus": "Menu Management", "Permission:Menus": "Menu management",
"Permission:Menus.Create": "Create", "Permission:Menus.Create": "Create",
"Permission:Menus.Delete": "Delete", "Permission:Menus.Delete": "Delete",
"Permission:Menus.Update": "Update", "Permission:Menus.Update": "Update",
"Permission:PageManagement": "Page Management", "Permission:PageManagement": "Page management",
"Permission:PageManagement:Create": "Create", "Permission:PageManagement:Create": "Create",
"Permission:PageManagement:Delete": "Delete", "Permission:PageManagement:Delete": "Delete",
"Permission:PageManagement:Update": "Update", "Permission:PageManagement:Update": "Update",
"Permission:PageManagement:SetAsHomePage": "Set As Home Page", "Permission:PageManagement:SetAsHomePage": "Set as home page",
"Permission:TagManagement": "Tag Management", "Permission:TagManagement": "Tag management",
"Permission:TagManagement.Create": "Create", "Permission:TagManagement.Create": "Create",
"Permission:TagManagement.Delete": "Delete", "Permission:TagManagement.Delete": "Delete",
"Permission:TagManagement.Update": "Update", "Permission:TagManagement.Update": "Update",
"Permission:GlobalResources": "Global Resources", "Permission:GlobalResources": "Global resources",
"Permission:CmsKitPublic": "CmsKit Public", "Permission:CmsKitPublic": "CmsKit public",
"Permission:Comments.DeleteAll": "Delete All", "Permission:Comments.DeleteAll": "Delete all",
"PickYourReaction": "Pick your reaction", "PickYourReaction": "Pick your reaction",
"Rating": "Rating", "Rating": "Rating",
"RatingUndoMessage": "Your rating will be undo.", "RatingUndoMessage": "Your rating will be undo.",
@ -130,9 +130,9 @@
"Reply": "Reply", "Reply": "Reply",
"ReplyTo": "Reply to", "ReplyTo": "Reply to",
"SamplePageMessage": "A sample page for the Pro module", "SamplePageMessage": "A sample page for the Pro module",
"SaveChanges": "Save Changes", "SaveChanges": "Save changes",
"Script": "Script", "Script": "Script",
"SelectAll": "Select All", "SelectAll": "Select all",
"Send": "Send", "Send": "Send",
"SendMessage": "Send Message", "SendMessage": "Send Message",
"SelectedAuthor": "Author", "SelectedAuthor": "Author",
@ -167,7 +167,7 @@
"YourMessage": "Your Message", "YourMessage": "Your Message",
"YourReply": "Your reply", "YourReply": "Your reply",
"MarkdownSupported": "<a href=\"https://www.markdownguide.org/basic-syntax/\">Markdown</a> supported.", "MarkdownSupported": "<a href=\"https://www.markdownguide.org/basic-syntax/\">Markdown</a> supported.",
"GlobalResources": "Global Resources", "GlobalResources": "Global resources",
"SavedSuccessfully": "Saved successfully", "SavedSuccessfully": "Saved successfully",
"CmsKit.BlogPost.Status.0": "Draft", "CmsKit.BlogPost.Status.0": "Draft",
"CmsKit.BlogPost.Status.1": "Published", "CmsKit.BlogPost.Status.1": "Published",
@ -197,7 +197,7 @@
"CompletedSettingAsHomePage": "Set as home page", "CompletedSettingAsHomePage": "Set as home page",
"IsHomePage": "Is Home Page", "IsHomePage": "Is Home Page",
"RemovedSettingAsHomePage": "Removed setting the home page", "RemovedSettingAsHomePage": "Removed setting the home page",
"Feature:CmsKitGroup": "Cms Kit", "Feature:CmsKitGroup": "Cms kit",
"Feature:BlogEnable": "Blogpost", "Feature:BlogEnable": "Blogpost",
"Feature:BlogEnableDescription": "CMS Kit's blogpost system that allows create blogs and posts dynamically in the application.", "Feature:BlogEnableDescription": "CMS Kit's blogpost system that allows create blogs and posts dynamically in the application.",
"Feature:CommentEnable": "Commenting", "Feature:CommentEnable": "Commenting",

18
modules/cms-kit/src/Volo.CmsKit.Public.Web/Security/Captcha/CaptchaOptions.cs

@ -1,19 +1,17 @@
using System; using System;
using SixLabors.Fonts; using ImageMagick;
using SixLabors.ImageSharp;
using SixLabors.ImageSharp.Formats;
namespace Volo.CmsKit.Public.Web.Security.Captcha; namespace Volo.CmsKit.Public.Web.Security.Captcha;
public class CaptchaOptions public class CaptchaOptions
{ {
public Color[] TextColor { get; set; } = new Color[] public MagickColor[] TextColor { get; set; } = new MagickColor[]
{ {
Color.Blue, Color.Black, Color.Black, Color.Brown, Color.Gray, Color.Green MagickColors.Blue, MagickColors.Black, MagickColors.Black, MagickColors.Brown, MagickColors.Gray, MagickColors.Green
}; };
public Color[] DrawLinesColor { get; set; } = new Color[] public MagickColor[] DrawLinesColor { get; set; } = new MagickColor[]
{ {
Color.Blue, Color.Black, Color.Black, Color.Brown, Color.Gray, Color.Green MagickColors.Blue, MagickColors.Black, MagickColors.Black, MagickColors.Brown, MagickColors.Gray, MagickColors.Green
}; };
public float MinLineThickness { get; set; } = 0.7f; public float MinLineThickness { get; set; } = 0.7f;
@ -26,15 +24,15 @@ public class CaptchaOptions
public ushort NoiseRate { get; set; } = 500; public ushort NoiseRate { get; set; } = 500;
public Color[] NoiseRateColor { get; set; } = new Color[] { Color.Gray }; public MagickColor[] NoiseRateColor { get; set; } = new MagickColor[] { MagickColors.Gray };
public byte FontSize { get; set; } = 32; public byte FontSize { get; set; } = 32;
public FontStyle FontStyle { get; set; } = FontStyle.Regular; public FontStyleType FontStyle { get; set; } = FontStyleType.Normal;
public EncoderTypes EncoderType { get; set; } = EncoderTypes.Png; public EncoderTypes EncoderType { get; set; } = EncoderTypes.Png;
public IImageEncoder Encoder => RandomTextGenerator.GetEncoder(EncoderType); public MagickFormat Encoder => RandomTextGenerator.GetEncoder(EncoderType);
public byte DrawLines { get; set; } = 2; public byte DrawLines { get; set; } = 2;

12
modules/cms-kit/src/Volo.CmsKit.Public.Web/Security/Captcha/RandomTextGenerator.cs

@ -1,21 +1,19 @@
using System; using System;
using System.Security.Cryptography; using System.Security.Cryptography;
using System.Text; using System.Text;
using SixLabors.ImageSharp.Formats; using ImageMagick;
using SixLabors.ImageSharp.Formats.Jpeg;
using SixLabors.ImageSharp.Formats.Png;
namespace Volo.CmsKit.Public.Web.Security.Captcha; namespace Volo.CmsKit.Public.Web.Security.Captcha;
public static class RandomTextGenerator public static class RandomTextGenerator
{ {
private static readonly char[] AllowedChars = "abcdefghijkmnpqrstuvwxyzABCDEFGHJKLMNPQRSTUVXYZW23456789".ToCharArray(); private static readonly char[] AllowedChars = "abcdefghijkmnpqrstuvwxyzABCDEFGHJKLMNPQRSTUVXYZW23456789".ToCharArray();
public static IImageEncoder GetEncoder(EncoderTypes encoderType) public static MagickFormat GetEncoder(EncoderTypes encoderType)
{ {
IImageEncoder encoder = encoderType switch var encoder = encoderType switch
{ {
EncoderTypes.Png => new PngEncoder(), EncoderTypes.Png => MagickFormat.Png,
EncoderTypes.Jpeg => new JpegEncoder(), EncoderTypes.Jpeg => MagickFormat.Jpeg,
_ => throw new ArgumentException($"Encoder '{encoderType}' not found!") _ => throw new ArgumentException($"Encoder '{encoderType}' not found!")
}; };

134
modules/cms-kit/src/Volo.CmsKit.Public.Web/Security/Captcha/SimpleMathsCaptchaGenerator.cs

@ -1,21 +1,13 @@
using System; using System;
using System.IO;
using System.Linq; using System.Linq;
using System.Numerics;
using System.Threading.Tasks; using System.Threading.Tasks;
using SixLabors.Fonts;
using SixLabors.ImageSharp;
using SixLabors.ImageSharp.Drawing.Processing;
using SixLabors.ImageSharp.PixelFormats;
using SixLabors.ImageSharp.Processing;
using Volo.Abp; using Volo.Abp;
using Volo.CmsKit.Localization; using Volo.CmsKit.Localization;
using Microsoft.Extensions.Localization; using Microsoft.Extensions.Localization;
using Volo.Abp.DependencyInjection; using Volo.Abp.DependencyInjection;
using Color = SixLabors.ImageSharp.Color;
using PointF = SixLabors.ImageSharp.PointF;
using Volo.Abp.Caching; using Volo.Abp.Caching;
using Microsoft.Extensions.Caching.Distributed; using Microsoft.Extensions.Caching.Distributed;
using ImageMagick;
namespace Volo.CmsKit.Public.Web.Security.Captcha; namespace Volo.CmsKit.Public.Web.Security.Captcha;
@ -108,93 +100,79 @@ public class SimpleMathsCaptchaGenerator : ITransientDependency
private byte[] GenerateInternal(string stringText, CaptchaOptions options) private byte[] GenerateInternal(string stringText, CaptchaOptions options)
{ {
byte[] result; var random = new Random();
var family = MagickNET.FontFamilies.First();
var drawables = new Drawables()
.Font(family, options.FontStyle, FontWeight.Normal, FontStretch.Normal)
.FontPointSize(options.FontSize)
.StrokeColor(MagickColors.Transparent);
var size = (ushort)(drawables.FontTypeMetrics(stringText)?.TextWidth ?? 0);
using var image = new MagickImage(MagickColors.White, size + 15, options.Height);
using (var image = new Image<Rgba32>(options.Width, options.Height)) double position = 0;
var startWith = (byte)random.Next(5, 10);
foreach (var character in stringText)
{ {
float position = 0; var text = character.ToString();
var random = new Random(); var color = options.TextColor[random.Next(0, options.TextColor.Length)];
var startWith = (byte)random.Next(5, 10); drawables.FillColor(new MagickColor(color.R, color.G, color.B, color.A))
image.Mutate(ctx => ctx.BackgroundColor(Color.Transparent)); .Text(startWith + position,
RandomTextGenerator.GenerateNextFloat(image.BaseHeight / 2.3, image.BaseHeight / 1.7), text);
var fontFamily = SystemFonts.Families
.FirstOrDefault(x => x.GetAvailableStyles().Contains(options.FontStyle), SystemFonts.Families.First())
.Name;
var font = SystemFonts.CreateFont(fontFamily, options.FontSize, options.FontStyle);
foreach (var character in stringText)
{
var text = character.ToString();
var color = options.TextColor[random.Next(0, options.TextColor.Length)];
var location = new PointF(startWith + position, random.Next(6, 13));
image.Mutate(ctx => ctx.DrawText(text, font, color, location));
position += TextMeasurer.MeasureSize(character.ToString(), new TextOptions (font)
{
Origin = location
}).Width;
}
//add rotation position += drawables.FontTypeMetrics(text)?.TextWidth ?? 0;
var rotation = GetRotation(options); }
image.Mutate(ctx => ctx.Transform(rotation));
// add rotation
var rotation = GetRotation(options);
drawables.Rotation(rotation);
// add the dynamic image to original image drawables.Draw(image);
var size = (ushort)TextMeasurer.MeasureSize(stringText, new TextOptions(font)).Width;
var img = new Image<Rgba32>(size + 15, options.Height);
img.Mutate(ctx => ctx.BackgroundColor(Color.White));
Parallel.For(0, options.DrawLines, i => Parallel.For(0, options.DrawLines, _ =>
{
// ReSharper disable once AccessToDisposedClosure
if (image is { IsDisposed: false })
{ {
var x0 = random.Next(0, random.Next(0, 30)); var x0 = random.Next(0, random.Next(0, 30));
var y0 = random.Next(10, img.Height); var y0 = random.Next(10, image.Height);
var x1 = random.Next(30, img.Width); var x1 = random.Next(30, image.Width);
var y1 = random.Next(0, img.Height); var y1 = random.Next(0, image.Height);
img.Mutate(ctx => image.Draw(new Drawables()
ctx.DrawLine(options.TextColor[random.Next(0, options.TextColor.Length)], .StrokeColor(options.DrawLinesColor[random.Next(0, options.DrawLinesColor.Length)])
RandomTextGenerator.GenerateNextFloat(options.MinLineThickness, options.MaxLineThickness), .StrokeWidth(RandomTextGenerator.GenerateNextFloat(options.MinLineThickness,
new PointF[] { new PointF(x0, y0), new PointF(x1, y1) }) options.MaxLineThickness))
); .Line(x0, y0, x1, y1));
}); }
});
img.Mutate(ctx => ctx.DrawImage(image, 0.80f));
Parallel.For(0, options.NoiseRate, _ => Parallel.For(0, options.NoiseRate, _ =>
{
if (image is { IsDisposed: false })
{ {
var x0 = random.Next(0, img.Width - 1); var x = random.Next(0, image.Width);
var y0 = random.Next(0, img.Height - 1); var y = random.Next(0, image.Height);
img.Mutate( image.Draw(new Drawables()
ctx => ctx .FillColor(options.NoiseRateColor[random.Next(0, options.NoiseRateColor.Length)])
.DrawLine(options.NoiseRateColor[random.Next(0, options.NoiseRateColor.Length)], .Point(x, y)
RandomTextGenerator.GenerateNextFloat(0.5, 1.5),
new PointF[] { new Vector2(x0, y0), new Vector2(x0 + 0.005f, y0 + 0.005f) })
); );
});
img.Mutate(x =>
{
x.Resize(options.Width, options.Height);
});
using (var ms = new MemoryStream())
{
img.Save(ms, options.Encoder);
result = ms.ToArray();
} }
} });
return result; image.Resize(new MagickGeometry(options.Width, options.Height) { IgnoreAspectRatio = true });
return image.ToByteArray(options.Encoder);
} }
private static AffineTransformBuilder GetRotation(CaptchaOptions options) private double GetRotation(CaptchaOptions options)
{ {
var random = new Random(); var random = new Random();
var width = random.Next(10, options.Width);
var height = random.Next(10, options.Height);
var pointF = new PointF(width, height);
var rotationDegrees = random.Next(0, options.MaxRotationDegrees); var rotationDegrees = random.Next(0, options.MaxRotationDegrees);
return new AffineTransformBuilder().PrependRotationDegrees(rotationDegrees, pointF); return rotationDegrees;
} }
} }

3
modules/cms-kit/src/Volo.CmsKit.Public.Web/Volo.CmsKit.Public.Web.csproj

@ -18,8 +18,7 @@
<PackageReference Include="Microsoft.Extensions.FileProviders.Embedded" /> <PackageReference Include="Microsoft.Extensions.FileProviders.Embedded" />
<PackageReference Include="Markdig.Signed" /> <PackageReference Include="Markdig.Signed" />
<PackageReference Include="HtmlSanitizer" /> <PackageReference Include="HtmlSanitizer" />
<PackageReference Include="SixLabors.ImageSharp"/> <PackageReference Include="Magick.NET-Q16-AnyCPU" />
<PackageReference Include="SixLabors.ImageSharp.Drawing" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>

2
modules/docs/src/Volo.Docs.Web/Pages/Documents/Project/Index.cshtml

@ -318,7 +318,7 @@
<select class="doc-section-combobox form-select" <select class="doc-section-combobox form-select"
aria-describedby="@("Section" + parameter.Name + "ComboboxAddonId")" aria-describedby="@("Section" + parameter.Name + "ComboboxAddonId")"
id="@("Section" + parameter.Name + "ComboboxId")" data-key="@parameter.Name"> id="@("Section" + parameter.Name + "ComboboxId")" data-key="@parameter.Name">
@foreach (var value in parameter.Values) @foreach (var value in parameter.Values.OrderBy(p => p.Value))
{ {
@if (value.Key == (Model.UserPreferences.ContainsKey(parameter.Name) ? Model.UserPreferences[parameter.Name] : null)) @if (value.Key == (Model.UserPreferences.ContainsKey(parameter.Name) ? Model.UserPreferences[parameter.Name] : null))
{ {

6
modules/feature-management/src/Volo.Abp.FeatureManagement.Domain.Shared/Volo/Abp/FeatureManagement/Localization/Domain/en.json

@ -3,12 +3,12 @@
"texts": { "texts": {
"Features": "Features", "Features": "Features",
"NoFeatureFoundMessage": "There isn't any available feature.", "NoFeatureFoundMessage": "There isn't any available feature.",
"ManageHostFeatures": "Manage Host features", "ManageHostFeatures": "Manage host features",
"ManageHostFeaturesText": "You can manage the host side features by clicking the following button.", "ManageHostFeaturesText": "You can manage the host side features by clicking the following button.",
"Permission:FeatureManagement": "Feature management", "Permission:FeatureManagement": "Feature management",
"Permission:FeatureManagement.ManageHostFeatures": "Manage Host features", "Permission:FeatureManagement.ManageHostFeatures": "Manage host features",
"Volo.Abp.FeatureManagement:InvalidFeatureValue": "{0} feature value is not valid!", "Volo.Abp.FeatureManagement:InvalidFeatureValue": "{0} feature value is not valid!",
"Menu:FeatureManagement": "Feature Management", "Menu:FeatureManagement": "Feature management",
"ResetToDefault": "Reset to default", "ResetToDefault": "Reset to default",
"ResetedToDefault": "Reseted to default", "ResetedToDefault": "Reseted to default",
"AreYouSure": "Are you sure?", "AreYouSure": "Are you sure?",

13
modules/openiddict/app/OpenIddict.Demo.API/Program.cs

@ -1,11 +1,19 @@
using System.Text;
using Microsoft.AspNetCore.Authentication.JwtBearer; using Microsoft.AspNetCore.Authentication.JwtBearer;
using Microsoft.IdentityModel.Tokens;
var builder = WebApplication.CreateBuilder(args); var builder = WebApplication.CreateBuilder(args);
builder.Logging.ClearProviders(); builder.Logging.ClearProviders();
builder.Logging.AddConsole(); builder.Logging.AddConsole();
builder.Services.AddCors(options =>
{
options.AddDefaultPolicy(policy =>
{
policy.WithOrigins("https://localhost:44304")
.AllowAnyHeader()
.AllowAnyMethod();
});
});
// Add services to the container. // Add services to the container.
builder.Services.AddControllers(); builder.Services.AddControllers();
@ -31,6 +39,7 @@ if (app.Environment.IsDevelopment())
app.UseHttpsRedirection(); app.UseHttpsRedirection();
app.UseCors();
app.UseAuthentication(); app.UseAuthentication();
app.UseAuthorization(); app.UseAuthorization();

35
modules/openiddict/app/OpenIddict.Demo.Client.BlazorWASM/Pages/Index.razor

@ -1,7 +1,11 @@
@page "/" @page "/"
@using System.Security.Claims @using System.Security.Claims
@using System.Text.Json
@using Microsoft.AspNetCore.Components.WebAssembly.Authentication
@using System.Net.Http.Headers
@inject AuthenticationStateProvider AuthenticationStateProvider @inject AuthenticationStateProvider AuthenticationStateProvider
@inject IAccessTokenProvider AccessTokenProvider
<PageTitle>Index</PageTitle> <PageTitle>Index</PageTitle>
@ -17,14 +21,31 @@ Welcome to your new app.
@if (_claims.Count() > 0) @if (_claims.Count() > 0)
{ {
<p>
@_accessToken
</p>
<ul> <ul>
@foreach (var claim in _claims) @foreach (var claim in _claims)
{ {
<li>@claim.Type: @claim.Value</li> <li>@claim.Type: @claim.Value</li>
} }
</ul> </ul>
}
<code style="display: block; white-space: pre-wrap; text-align: left">
@{
var apiResponse = "No API response";
if (_claimsResponseString != null)
{
apiResponse = JsonSerializer.Serialize(JsonDocument.Parse(_claimsResponseString), new JsonSerializerOptions
{
WriteIndented = true
});
}
}
@apiResponse;
</code>
}
@code { @code {
@ -35,6 +56,8 @@ Welcome to your new app.
} }
private IEnumerable<Claim> _claims = Enumerable.Empty<Claim>(); private IEnumerable<Claim> _claims = Enumerable.Empty<Claim>();
private string? _accessToken;
private string? _claimsResponseString;
private async Task GetClaimsPrincipalData() private async Task GetClaimsPrincipalData()
{ {
@ -43,8 +66,16 @@ Welcome to your new app.
if (user.Identity.IsAuthenticated) if (user.Identity.IsAuthenticated)
{ {
_claims = user.Claims; _claims = user.Claims;
var result = await AccessTokenProvider.RequestAccessToken();
result.TryGetToken(out var token);
_accessToken = token?.Value;
var client = new HttpClient();
var request = new HttpRequestMessage(HttpMethod.Get, "https://localhost:44303/api/claims");
request.Headers.Authorization = new AuthenticationHeaderValue("Bearer", _accessToken);
_claimsResponseString = await (await client.SendAsync(request)).Content.ReadAsStringAsync();
} }
} }
} }

1
modules/openiddict/app/OpenIddict.Demo.Client.BlazorWASM/Program.cs

@ -21,6 +21,7 @@ builder.Services.AddOidcAuthentication(options =>
options.ProviderOptions.DefaultScopes.Add("roles"); options.ProviderOptions.DefaultScopes.Add("roles");
options.ProviderOptions.DefaultScopes.Add("email"); options.ProviderOptions.DefaultScopes.Add("email");
options.ProviderOptions.DefaultScopes.Add("phone"); options.ProviderOptions.DefaultScopes.Add("phone");
options.ProviderOptions.DefaultScopes.Add("AbpAPI");
}); });
await builder.Build().RunAsync(); await builder.Build().RunAsync();

19
modules/openiddict/app/OpenIddict.Demo.Client.Mvc/Pages/Index.cshtml

@ -45,24 +45,5 @@
} }
@apiResponse; @apiResponse;
</code> </code>
request = new HttpRequestMessage(HttpMethod.Get, "https://localhost:44301/api/claims");
request.Headers.Authorization = new AuthenticationHeaderValue("Bearer", await HttpContext.GetTokenAsync("access_token"));
response = await client.SendAsync(request);
<code style="display: block; white-space: pre-wrap; text-align: left">
@{
apiResponse = response.StatusCode.ToString();
if (response.IsSuccessStatusCode)
{
apiResponse = JsonSerializer.Serialize(JsonDocument.Parse(await response.Content.ReadAsStringAsync()), new JsonSerializerOptions
{
WriteIndented = true
});
}
}
@apiResponse;
</code>
} }
</div> </div>

Some files were not shown because too many files changed in this diff

Loading…
Cancel
Save