Merge release/2.2 and replace submodules
* Replace the aspnet/JsonPatch git submodule and merge the master branch of its source to this repo * Likewise for aspnet/DotNetTools * And aspnet/HtmlAbstractions * merge latest infrastructure changes from the release/2.2 branch
This commit is contained in:
commit
6cc9f6f130
|
|
@ -1,3 +1,4 @@
|
|||
|
||||
trigger:
|
||||
- master
|
||||
- release/*
|
||||
|
|
@ -5,31 +6,18 @@ trigger:
|
|||
jobs:
|
||||
- template: jobs/default-build.yml
|
||||
parameters:
|
||||
jobName: PR_FastCheck
|
||||
jobDisplayName: Fast Check
|
||||
agentOs: Windows
|
||||
jobName: Windows_FastCheck
|
||||
jobDisplayName: Windows - Fast Check
|
||||
buildArgs: "/t:FastCheck"
|
||||
artifacts:
|
||||
publish: false
|
||||
- job: RepoBuilds
|
||||
pool:
|
||||
vmImage: vs2017-win2016
|
||||
strategy:
|
||||
maxParallel: 3
|
||||
matrix:
|
||||
DataProtection:
|
||||
_FolderName: DataProtection
|
||||
WebSockets:
|
||||
_FolderName: WebSockets
|
||||
steps:
|
||||
- script: src/$(_FolderName)/build.cmd -ci
|
||||
displayName: Run src/$(_FolderName)/build.cmd
|
||||
- task: PublishTestResults@2
|
||||
displayName: Publish test results
|
||||
condition: always()
|
||||
inputs:
|
||||
testRunner: vstest
|
||||
testResultsFiles: 'src/$(_FolderName)/artifacts/logs/**/*.trx'
|
||||
- template: jobs/default-build.yml
|
||||
parameters:
|
||||
jobName: Windows_Build
|
||||
jobDisplayName: "Build: Windows"
|
||||
agentOs: Windows
|
||||
beforeBuild:
|
||||
- powershell: "& ./src/IISIntegration/tools/UpdateIISExpressCertificate.ps1"
|
||||
displayName: Setup IISExpress test certificates
|
||||
- template: jobs/iisintegration-job.yml
|
||||
parameters:
|
||||
TestGroupName: IIS
|
||||
|
|
|
|||
|
|
@ -63,6 +63,7 @@ jobs:
|
|||
- job: ${{ coalesce(parameters.jobName, parameters.agentOs) }}
|
||||
displayName: ${{ coalesce(parameters.jobDisplayName, parameters.agentOs) }}
|
||||
dependsOn: ${{ parameters.dependsOn }}
|
||||
timeoutInMinutes: 90
|
||||
workspace:
|
||||
clean: all
|
||||
strategy:
|
||||
|
|
|
|||
|
|
@ -26,18 +26,10 @@
|
|||
path = modules/Diagnostics
|
||||
url = https://github.com/aspnet/Diagnostics.git
|
||||
branch = master
|
||||
[submodule "modules/DotNetTools"]
|
||||
path = modules/DotNetTools
|
||||
url = https://github.com/aspnet/DotNetTools.git
|
||||
branch = master
|
||||
[submodule "modules/Hosting"]
|
||||
path = modules/Hosting
|
||||
url = https://github.com/aspnet/Hosting.git
|
||||
branch = master
|
||||
[submodule "modules/HtmlAbstractions"]
|
||||
path = modules/HtmlAbstractions
|
||||
url = https://github.com/aspnet/HtmlAbstractions.git
|
||||
branch = master
|
||||
[submodule "modules/HttpAbstractions"]
|
||||
path = modules/HttpAbstractions
|
||||
url = https://github.com/aspnet/HttpAbstractions.git
|
||||
|
|
@ -58,10 +50,6 @@
|
|||
path = modules/JavaScriptServices
|
||||
url = https://github.com/aspnet/JavaScriptServices.git
|
||||
branch = master
|
||||
[submodule "modules/JsonPatch"]
|
||||
path = modules/JsonPatch
|
||||
url = https://github.com/aspnet/JsonPatch.git
|
||||
branch = master
|
||||
[submodule "modules/KestrelHttpServer"]
|
||||
path = modules/KestrelHttpServer
|
||||
url = https://github.com/aspnet/KestrelHttpServer.git
|
||||
|
|
|
|||
|
|
@ -17,6 +17,8 @@
|
|||
replace PackageLicenseUrl with PackageLicenseExpression.
|
||||
-->
|
||||
<NoWarn>$(NoWarn);NU5125</NoWarn>
|
||||
<!-- Suppress warnings about using SemVer 2.0. -->
|
||||
<NoWarn>$(NoWarn);NU5105</NoWarn>
|
||||
|
||||
<!-- Contact email address for NuGet packages and Linux installers. -->
|
||||
<MaintainerEmail>nugetaspnet@microsoft.com</MaintainerEmail>
|
||||
|
|
@ -49,6 +51,16 @@
|
|||
<BuildProjectReferences Condition=" '$(NoBuild)' == 'true' ">false</BuildProjectReferences>
|
||||
</PropertyGroup>
|
||||
|
||||
<!-- Certificate names used for Authenticode signing. -->
|
||||
<PropertyGroup Condition=" '$(DisableCodeSigning)' != 'true' ">
|
||||
<AssemblySigningCertName>Microsoft400</AssemblySigningCertName>
|
||||
<AssemblySigning3rdPartyCertName>3PartySHA2</AssemblySigning3rdPartyCertName>
|
||||
<PowerShellSigningCertName>Microsoft400</PowerShellSigningCertName>
|
||||
<PackageSigningCertName>NuGet</PackageSigningCertName>
|
||||
<VsixSigningCertName>VsixSHA2</VsixSigningCertName>
|
||||
<JarSigningCertName>MicrosoftJAR</JarSigningCertName>
|
||||
</PropertyGroup>
|
||||
|
||||
<Import Project="build\external-dependencies.props" />
|
||||
<Import Project="build\sources.props" />
|
||||
|
||||
|
|
@ -75,8 +87,16 @@
|
|||
<SuppressNETCoreSdkPreviewMessage>true</SuppressNETCoreSdkPreviewMessage>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup>
|
||||
<StandardTestTfms>netcoreapp2.2;net461</StandardTestTfms>
|
||||
</PropertyGroup>
|
||||
|
||||
<Import Project="eng\Dependencies.props" />
|
||||
<Import Project="eng\PatchConfig.props" />
|
||||
<Import Project="eng\ProjectReferences.props" />
|
||||
<Import Project="eng\targets\RuntimeIdentifiers.props" />
|
||||
<Import Project="eng\targets\Cpp.Common.props" Condition="'$(MSBuildProjectExtension)' == '.vcxproj'" />
|
||||
<Import Project="eng\targets\CSharp.Common.props" Condition="'$(MSBuildProjectExtension)' == '.csproj'" />
|
||||
<Import Project="eng\targets\SharedFx.Common.props" Condition="'$(MSBuildProjectExtension)' == '.shfxproj'" />
|
||||
<Import Project="eng\targets\Wix.Common.props" Condition="'$(MSBuildProjectExtension)' == '.wixproj'" />
|
||||
|
||||
|
|
|
|||
|
|
@ -1,9 +1,46 @@
|
|||
<Project>
|
||||
<!-- Properties which should be set after the project has been evaluated -->
|
||||
<PropertyGroup Condition=" '$(MSBuildProjectExtension)' == '.csproj' ">
|
||||
<PackageId Condition=" '$(PackageId)' == '' ">$(AssemblyName)</PackageId>
|
||||
<IsPackable Condition="'$(IsPackable)' == '' AND ( '$(IsTestProject)' == 'true' OR '$(IsTestAssetProject)' == 'true' OR '$(IsBenchmarkProject)' == 'true' OR '$(IsSampleProject)' == 'true' ) ">false</IsPackable>
|
||||
</PropertyGroup>
|
||||
|
||||
<Import Project="eng\Baseline.props" />
|
||||
|
||||
<PropertyGroup Condition=" '$(IsPackable)' != 'false' AND '$(AspNetCorePatchVersion)' != '0' ">
|
||||
<!-- Always include framework metapackages in patch updates. -->
|
||||
<IsPackageInThisPatch Condition="'$(IsFrameworkMetapackage)' == 'true'">true</IsPackageInThisPatch>
|
||||
<IsPackageInThisPatch Condition="'$(IsPackageInThisPatch)' == ''">$(PackagesInPatch.Contains(' $(PackageId);'))</IsPackageInThisPatch>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition=" '$(IsPackable)' != 'false' AND '$(IsServicingBuild)' == 'true' ">
|
||||
<!-- Used to distinguish between packages building -->
|
||||
<IsPackableInNonServicingBuild>true</IsPackableInNonServicingBuild>
|
||||
<!-- Suppress creation of .nupkg for servicing builds. -->
|
||||
<IsPackable Condition=" '$(IsPackageInThisPatch)' != 'true' ">false</IsPackable>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition=" '$(IsPackageInThisPatch)' != 'true' AND '$(BaselinePackageVersion)' != '' ">
|
||||
<!-- This keeps assembly and package versions consistent across patches. If a package is not included in a patch, its version should stay at the baseline. -->
|
||||
<AssemblyVersion>$(BaselinePackageVersion).0</AssemblyVersion>
|
||||
<!--
|
||||
Ideally, we would also set the project version to match the baseline in case NuGet turns a ProjectReference into a nuspec depenendency, but
|
||||
NuGet does not currently handle conflicts between packages and projects which have the same package id/version.
|
||||
See https://github.com/NuGet/Home/issues/6795.
|
||||
|
||||
Because we still use static analysis to scrape versions, only set this during static analysis, which can be detected by checking for both NoBuild and DesignTimeBuild.
|
||||
-->
|
||||
<Version Condition="'$(NoBuild)' == 'true' AND '$(DesignTimeBuild)' == 'true'">$(BaselinePackageVersion)</Version>
|
||||
<PackageVersion Condition="'$(NoBuild)' == 'true' AND '$(DesignTimeBuild)' == 'true'">$(BaselinePackageVersion)</PackageVersion>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup>
|
||||
<!-- Implementation projects are the projects which produce nuget packages or shipping assemblies. -->
|
||||
<IsImplementationProject Condition=" '$(IsImplementationProject)' == '' AND '$(IsTestAssetProject)' != 'true' AND '$(IsTestProject)' != 'true' AND '$(IsBenchmarkProject)' != 'true' AND '$(IsSampleProject)' != 'true' ">true</IsImplementationProject>
|
||||
|
||||
<!-- Suppress KoreBuild warnings about the mismatch of repo version and local project version. The versioning in this mega repo is sufficiently complicated that KoreBuild's validation isn't helpful. -->
|
||||
<VerifyVersion>false</VerifyVersion>
|
||||
|
||||
<EnableApiCheck Condition=" '$(EnableApiCheck)' != '' ">$(IsImplementationProject)</EnableApiCheck>
|
||||
<IsPackable Condition="'$(IsPackable)' == '' AND '$(IsImplementationProject)' == 'true' ">true</IsPackable>
|
||||
<IsPackable Condition="'$(IsPackable)' == '' ">false</IsPackable>
|
||||
|
|
@ -16,6 +53,7 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<Import Project="eng\targets\Cpp.Common.targets" Condition="'$(MSBuildProjectExtension)' == '.vcxproj'" />
|
||||
<Import Project="eng\targets\CSharp.Common.targets" Condition="'$(MSBuildProjectExtension)' == '.csproj'" />
|
||||
<Import Project="eng\targets\SharedFx.Common.targets" Condition="'$(MSBuildProjectExtension)' == '.shfxproj'" />
|
||||
<Import Project="eng\targets\Wix.Common.targets" Condition="'$(MSBuildProjectExtension)' == '.wixproj'" />
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -43,6 +43,7 @@
|
|||
<FilesToSign Include="Microsoft.Extensions.Options.DataAnnotations.dll" Certificate="$(AssemblySigningCertName)" Container="Microsoft.AspNetCore.App" />
|
||||
<FilesToSign Include="Microsoft.Extensions.Options.dll" Certificate="$(AssemblySigningCertName)" Container="Microsoft.AspNetCore.App" />
|
||||
<FilesToSign Include="Microsoft.Extensions.Primitives.dll" Certificate="$(AssemblySigningCertName)" Container="Microsoft.AspNetCore.App" />
|
||||
<FilesToSign Include="Microsoft.Extensions.WebEncoders.dll" Certificate="$(AssemblySigningCertName)" Container="Microsoft.AspNetCore.App" />
|
||||
<!-- These files came from the aspnet/EntityFrameworkCore build, but have to be re-signed because we crossgen them. -->
|
||||
<FilesToSign Include="Microsoft.EntityFrameworkCore.Abstractions.dll" Certificate="$(AssemblySigningCertName)" Container="Microsoft.AspNetCore.App" />
|
||||
<FilesToSign Include="Microsoft.EntityFrameworkCore.Design.dll" Certificate="$(AssemblySigningCertName)" Container="Microsoft.AspNetCore.App" />
|
||||
|
|
|
|||
|
|
@ -4,7 +4,7 @@
|
|||
<CodeSignDependsOn>$(CodeSignDependsOn);CollectFileSignInfo</CodeSignDependsOn>
|
||||
</PropertyGroup>
|
||||
|
||||
<Target Name="CollectFileSignInfo" DependsOnTargets="_PrepareRepositories">
|
||||
<Target Name="CollectFileSignInfo" DependsOnTargets="_PrepareRepositories;GetProjectArtifactInfo;GetFxProjectArtifactInfo">
|
||||
|
||||
<ItemGroup>
|
||||
<_RepositoryProject Remove="@(_RepositoryProject)" />
|
||||
|
|
@ -12,6 +12,10 @@
|
|||
<AdditionalProperties>RepositoryRoot=%(Repository.RootPath)</AdditionalProperties>
|
||||
<Build>%(Repository.Build)</Build>
|
||||
</_RepositoryProject>
|
||||
<_ShippedRepositoryProject Include="$(MSBuildProjectFullPath)" Condition="'%(ShippedRepository.Identity)' != ''">
|
||||
<AdditionalProperties>RepositoryRoot=%(ShippedRepository.RootPath)</AdditionalProperties>
|
||||
<Build>false</Build>
|
||||
</_ShippedRepositoryProject>
|
||||
</ItemGroup>
|
||||
|
||||
<PropertyGroup>
|
||||
|
|
@ -28,21 +32,37 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<MSBuild Projects="@(_RepositoryProject)"
|
||||
Condition="@(_RepositoryProject->Count()) != 0"
|
||||
Targets="_GetFileSignInfo"
|
||||
Properties="$(GetFileSignInfoProps);$(DesignTimeBuildProps);DesignTimeBuild=true;Configuration=$(Configuration);BuildNumber=$(BuildNumber);CustomAfterKoreBuildTargets=$(MSBuildThisFileFullPath)"
|
||||
BuildInParallel="true">
|
||||
<Output TaskParameter="TargetOutputs" ItemName="_RepoFileSignInfo" />
|
||||
</MSBuild>
|
||||
<MSBuild Projects="@(_ShippedRepositoryProject)"
|
||||
Condition="@(_ShippedRepositoryProject->Count()) != 0"
|
||||
Targets="_GetFileSignInfo"
|
||||
Properties="$(GetFileSignInfoProps);$(DesignTimeBuildProps);IsFinalBuild=true;DesignTimeBuild=true;Configuration=$(Configuration);BuildNumber=$(BuildNumber);CustomAfterKoreBuildTargets=$(MSBuildThisFileFullPath)"
|
||||
BuildInParallel="true">
|
||||
<Output TaskParameter="TargetOutputs" ItemName="_ShippedRepoFileSignInfo" />
|
||||
</MSBuild>
|
||||
|
||||
<ItemGroup>
|
||||
<!-- If repos were not built, only use this info to collect the mapping of FileName -> Certificate. Otherwise, include .nupkg and .zips in signing. -->
|
||||
<_FilesToSign Include="@(_RepoFileSignInfo)" Condition="'%(_RepoFileSignInfo.IsFileToSign)' == 'true' AND ('$(_ReposWereBuilt)' == 'true' OR '%(_RepoFileSignInfo.Container)' != '' ) " />
|
||||
<_FilesToSign Include="@(_ShippedRepoFileSignInfo)" Condition="'%(_ShippedRepoFileSignInfo.IsFileToSign)' == 'true' AND '%(_ShippedRepoFileSignInfo.Container)' != '' " />
|
||||
<FilesToSign Include="@(_FilesToSign)" />
|
||||
|
||||
<!-- Normalize FilesToExcludeFromSigning to filename + extension. -->
|
||||
<_Temp Remove="@(_Temp)" />
|
||||
<_Temp Include="@(FilesToExcludeFromSigning)" />
|
||||
<FilesToExcludeFromSigning Remove="@(FilesToExcludeFromSigning)" />
|
||||
<FilesToExcludeFromSigning Include="@(_Temp->'%(FileName)%(Extension)')" />
|
||||
<_Temp Remove="@(_Temp)" />
|
||||
|
||||
<FilesToExcludeFromSigning Include="@(_ShippedRepoFileSignInfo->'%(FileName)%(Extension)')" Condition="'%(_ShippedRepoFileSignInfo.IsFileToExcludeFromSign)' == 'true'" />
|
||||
<FilesToExcludeFromSigning Include="@(_RepoFileSignInfo->'%(FileName)%(Extension)')" Condition="'%(_RepoFileSignInfo.IsFileToExcludeFromSign)' == 'true'" />
|
||||
<!-- Workaround for the way we have both repo and Universe builds, crossgen AND uncrossgened outputs. This prevents duplicate configuration between 'exclude' and 'sign' options. -->
|
||||
<FilesToExcludeFromSigning Remove="@(FilesToSign->'%(FileName)%(Extension)')" />
|
||||
<FilesToExcludeFromSigning Remove="@(_FilesToSign->'%(FileName)%(Extension)')" />
|
||||
</ItemGroup>
|
||||
</Target>
|
||||
|
||||
|
|
|
|||
|
|
@ -8,9 +8,7 @@
|
|||
<ArchiveProjects Include="$(RepositoryRoot)src\PackageArchive\Archive.*\*.*proj" />
|
||||
</ItemGroup>
|
||||
|
||||
<Target Name="BuildFallbackArchive" DependsOnTargets="ResolveRepoInfo;GeneratePropsFiles">
|
||||
|
||||
|
||||
<Target Name="BuildFallbackArchive" DependsOnTargets="GetProjectArtifactInfo;GetFxProjectArtifactInfo;ResolveRepoInfo;GeneratePropsFiles">
|
||||
<PropertyGroup>
|
||||
<ArchiveBuildProps>
|
||||
DotNetRestoreSourcePropsPath=$(GeneratedRestoreSourcesPropsPath);
|
||||
|
|
|
|||
|
|
@ -2,21 +2,22 @@
|
|||
<PropertyGroup>
|
||||
<UnitTestFxProject>$(RepositoryRoot)src\Framework\Framework.UnitTests\Framework.UnitTests.csproj</UnitTestFxProject>
|
||||
<UnitTestFxProject>$([MSBuild]::NormalizePath($(UnitTestFxProject)))</UnitTestFxProject>
|
||||
<CodeSignDependsOn>$(CodeSignDependsOn);GetSharedFxFilesToSign</CodeSignDependsOn>
|
||||
<CodeSignDependsOn Condition="'$(_ProjectsOnly)' != 'true'">$(CodeSignDependsOn);GetSharedFxFilesToSign</CodeSignDependsOn>
|
||||
<BuildSharedFxDependsOn>_BuildSharedFxProjects;TestSharedFx</BuildSharedFxDependsOn>
|
||||
<BuildSharedFxDependsOn Condition="'$(TestOnly)' != 'true'">$(BuildSharedFxDependsOn);CodeSign</BuildSharedFxDependsOn>
|
||||
<RedistNetCorePath>$(IntermediateDir)ar\$(SharedFxRid)\</RedistNetCorePath>
|
||||
<GetArtifactInfoDependsOn>$(GetArtifactInfo);GetFxProjectArtifactInfo</GetArtifactInfoDependsOn>
|
||||
<BuildRuntimeSiteExtension Condition="'$(SharedFxRid)' == 'win-x64' OR '$(SharedFxRid)' == 'win-x86'">true</BuildRuntimeSiteExtension>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectToBuild Include="$(RepositoryRoot)src\Framework\**\*.pkgproj" />
|
||||
<ProjectToBuild Include="$(RepositoryRoot)src\Framework\**\*.shfxproj" />
|
||||
<ProjectToBuild Include="$(UnitTestFxProject)" />
|
||||
<ProjectToBuild Condition=" '$(BuildRuntimeArchive)' != 'false' " Include="$(RepositoryRoot)src\Installers\Archive\*.*proj" />
|
||||
<ProjectToBuild Condition=" '$(BuildRuntimeSiteExtension)' == 'true' " Include="$(RepositoryRoot)src\Installers\RuntimeSiteExtension\Microsoft.AspNetCore.Runtime.SiteExtension.pkgproj" />
|
||||
<ProjectToBuild Condition=" '$(SharedFxRid)' == 'linux-x64' AND '$(LinuxInstallerType)' == 'deb' " Include="$(RepositoryRoot)src\Installers\Debian\*.*proj" />
|
||||
<ProjectToBuild Condition=" '$(SharedFxRid)' == 'linux-x64' AND '$(LinuxInstallerType)' == 'rpm' " Include="$(RepositoryRoot)src\Installers\Rpm\*.*proj" />
|
||||
<FxProjectToBuild Include="$(RepositoryRoot)src\Framework\**\*.pkgproj" />
|
||||
<FxProjectToBuild Include="$(RepositoryRoot)src\Framework\**\*.shfxproj" />
|
||||
<FxProjectToBuild Include="$(UnitTestFxProject)" />
|
||||
<FxProjectToBuild Condition=" '$(BuildRuntimeArchive)' != 'false' " Include="$(RepositoryRoot)src\Installers\Archive\*.*proj" />
|
||||
<FxProjectToBuild Condition=" '$(BuildRuntimeSiteExtension)' == 'true' " Include="$(RepositoryRoot)src\Installers\RuntimeSiteExtension\Microsoft.AspNetCore.Runtime.SiteExtension.pkgproj" />
|
||||
<FxProjectToBuild Condition=" '$(SharedFxRid)' == 'linux-x64' AND '$(LinuxInstallerType)' == 'deb' " Include="$(RepositoryRoot)src\Installers\Debian\*.*proj" />
|
||||
<FxProjectToBuild Condition=" '$(SharedFxRid)' == 'linux-x64' AND '$(LinuxInstallerType)' == 'rpm' " Include="$(RepositoryRoot)src\Installers\Rpm\*.*proj" />
|
||||
</ItemGroup>
|
||||
|
||||
<Target Name="BuildSharedFx" DependsOnTargets="$(BuildSharedFxDependsOn)" />
|
||||
|
|
@ -43,7 +44,7 @@
|
|||
<Target Name="_BuildSharedFxProjects" DependsOnTargets="GeneratePropsFiles;ResolveCommitHash">
|
||||
|
||||
<PropertyGroup>
|
||||
<_RestoreGraphProjectInput>@(ProjectToBuild)</_RestoreGraphProjectInput>
|
||||
<_RestoreGraphProjectInput>@(FxProjectToBuild)</_RestoreGraphProjectInput>
|
||||
<SharedFxBuildProperties>
|
||||
$(BuildProperties);
|
||||
SharedFxRid=$(SharedFxRid);
|
||||
|
|
@ -58,11 +59,11 @@
|
|||
Targets="Restore"
|
||||
Properties="$(SharedFxBuildProperties);RestoreGraphProjectInput=$(_RestoreGraphProjectInput);_DummyTarget=Restore" />
|
||||
|
||||
<MSBuild Projects="@(ProjectToBuild)"
|
||||
<MSBuild Projects="@(FxProjectToBuild)"
|
||||
Properties="$(SharedFxBuildProperties)"
|
||||
BuildInParallel="true" />
|
||||
|
||||
<MSBuild Projects="@(ProjectToBuild)"
|
||||
<MSBuild Projects="@(FxProjectToBuild)"
|
||||
Targets="Pack"
|
||||
Properties="$(SharedFxBuildProperties);NoBuild=true"
|
||||
BuildInParallel="true"
|
||||
|
|
@ -100,4 +101,35 @@
|
|||
<Error Text="SharedFx.UnitTests failed with exit code '$(VsTestExitCode)'." Condition=" $(VsTestExitCode) != 0 " />
|
||||
</Target>
|
||||
|
||||
<Target Name="GetFxProjectArtifactInfo" Returns="@(ArtifactInfo)">
|
||||
<PropertyGroup>
|
||||
<_InspectionTargetsFile>$(MSBuildProjectDirectory)\Project.Inspection.targets</_InspectionTargetsFile>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<_Temp Remove="@(_Temp)" />
|
||||
</ItemGroup>
|
||||
|
||||
<MSBuild Targets="GetArtifactInfo"
|
||||
Projects="@(FxProjectToBuild)"
|
||||
Condition="@(FxProjectToBuild->Count()) != 0"
|
||||
Properties="$(BuildProperties);DesignTimeBuild=true;EnableApiCheck=false;NoBuild=true;CustomAfterMicrosoftCommonTargets=$(_InspectionTargetsFile);CustomAfterMicrosoftCommonCrossTargetingTargets=$(_InspectionTargetsFile)"
|
||||
BuildInParallel="$(BuildInParallel)"
|
||||
RemoveProperties="$(_BuildPropertiesToRemove)">
|
||||
|
||||
<Output TaskParameter="TargetOutputs" ItemName="_Temp" />
|
||||
</MSBuild>
|
||||
|
||||
<ItemGroup>
|
||||
<!-- Output from this target may include items representing assemblies inside the nupkg. -->
|
||||
<ArtifactInfo Include="@(_Temp)" Condition="'%(_Temp.Container)' == ''" />
|
||||
|
||||
<!-- Nupkgs or assemblies in the nupkg that should be signed -->
|
||||
<FilesToSign Include="@(_Temp)" Condition=" '%(_Temp.ShouldBeSigned)' == 'true' " />
|
||||
|
||||
<!-- Nupkgs or assemblies in the nupkg that should not be signed -->
|
||||
<FilesToExcludeFromSigning Include="@(_Temp)" Condition=" '%(_Temp.ShouldBeSigned)' != 'true' " />
|
||||
</ItemGroup>
|
||||
</Target>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -175,7 +175,6 @@
|
|||
<PackageArtifact Include="Microsoft.Extensions.Identity.Stores" Category="ship" />
|
||||
<PackageArtifact Include="Microsoft.Extensions.Localization.Abstractions" Category="ship" />
|
||||
<PackageArtifact Include="Microsoft.Extensions.Localization" Category="ship" />
|
||||
<PackageArtifact Include="Microsoft.Extensions.WebEncoders" Category="ship" />
|
||||
<PackageArtifact Include="Microsoft.Net.Http.Headers" Category="ship" />
|
||||
<PackageArtifact Include="Microsoft.NET.Sdk.Razor" Category="ship" />
|
||||
<PackageArtifact Include="Microsoft.Owin.Security.Interop" Category="ship" />
|
||||
|
|
|
|||
|
|
@ -7,16 +7,12 @@
|
|||
</ItemDefinitionGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<RepositoryBuildOrder Include="JsonPatch" Order="1" />
|
||||
<RepositoryBuildOrder Include="DotNetTools" Order="1" />
|
||||
<RepositoryBuildOrder Include="HtmlAbstractions" Order="1" />
|
||||
<RepositoryBuildOrder Include="Razor" Order="6" />
|
||||
<RepositoryBuildOrder Include="HttpAbstractions" Order="6" />
|
||||
<RepositoryBuildOrder Include="HttpClientFactory" Order="6" />
|
||||
<RepositoryBuildOrder Include="Hosting" Order="7" />
|
||||
<RepositoryBuildOrder Include="KestrelHttpServer" Order="8" />
|
||||
<RepositoryBuildOrder Include="HttpSysServer" Order="8" />
|
||||
<RepositoryBuildOrder Include="DataProtection" Order="9" RootPath="$(RepositoryRoot)src\DataProtection\" />
|
||||
<RepositoryBuildOrder Include="BasicMiddleware" Order="9" />
|
||||
<RepositoryBuildOrder Include="Antiforgery" Order="10" />
|
||||
<RepositoryBuildOrder Include="IISIntegration" Order="10" RootPath="$(RepositoryRoot)src\IISIntegration\" />
|
||||
|
|
@ -28,7 +24,6 @@
|
|||
<RepositoryBuildOrder Include="Routing" Order="12" />
|
||||
<RepositoryBuildOrder Include="Diagnostics" Order="12" />
|
||||
<RepositoryBuildOrder Include="Localization" Order="13" />
|
||||
<RepositoryBuildOrder Include="WebSockets" Order="13" RootPath="$(RepositoryRoot)src\WebSockets\" />
|
||||
<RepositoryBuildOrder Include="Security" Order="13" />
|
||||
<RepositoryBuildOrder Include="MetaPackages" Order="13" />
|
||||
<RepositoryBuildOrder Include="Mvc" Order="14" />
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
<!-- This file is temporary while we rework dependencies management. It is used when building individual folders as if they were repos. -->
|
||||
<Project>
|
||||
<PropertyGroup>
|
||||
<InternalAspNetCoreSdkPackageVersion Condition="'$(InternalAspNetCoreSdkPackageVersion)' == ''">3.0.0-alpha1-20181108.8</InternalAspNetCoreSdkPackageVersion>
|
||||
<InternalAspNetCoreSdkPackageVersion Condition="'$(InternalAspNetCoreSdkPackageVersion)' == ''">3.0.0-build-20181114.5</InternalAspNetCoreSdkPackageVersion>
|
||||
<MicrosoftAspNetCoreAspNetCoreModulePackageVersion>3.0.0-alpha1-10717</MicrosoftAspNetCoreAspNetCoreModulePackageVersion>
|
||||
<MicrosoftAspNetCoreAuthenticationCorePackageVersion>3.0.0-alpha1-10717</MicrosoftAspNetCoreAuthenticationCorePackageVersion>
|
||||
<MicrosoftAspNetCoreConnectionsAbstractionsPackageVersion>3.0.0-alpha1-10717</MicrosoftAspNetCoreConnectionsAbstractionsPackageVersion>
|
||||
|
|
|
|||
|
|
@ -31,67 +31,68 @@
|
|||
<SystemThreadingTasksExtensionsPackageVersion>4.6.0-preview1-26907-04</SystemThreadingTasksExtensionsPackageVersion>
|
||||
<SystemValueTuplePackageVersion>4.6.0-preview1-26829-04</SystemValueTuplePackageVersion>
|
||||
<!-- Packages from aspnet/Extensions -->
|
||||
<InternalAspNetCoreAnalyzersPackageVersion>3.0.0-preview-181108-06</InternalAspNetCoreAnalyzersPackageVersion>
|
||||
<MicrosoftAspNetCoreAnalyzerTestingPackageVersion>3.0.0-preview-181108-06</MicrosoftAspNetCoreAnalyzerTestingPackageVersion>
|
||||
<MicrosoftAspNetCoreBenchmarkRunnerSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftAspNetCoreBenchmarkRunnerSourcesPackageVersion>
|
||||
<MicrosoftAspNetCoreCertificatesGenerationSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftAspNetCoreCertificatesGenerationSourcesPackageVersion>
|
||||
<MicrosoftAspNetCoreTestingPackageVersion>3.0.0-preview-181108-06</MicrosoftAspNetCoreTestingPackageVersion>
|
||||
<MicrosoftExtensionsActivatorUtilitiesSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsActivatorUtilitiesSourcesPackageVersion>
|
||||
<MicrosoftExtensionsCachingAbstractionsPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsCachingAbstractionsPackageVersion>
|
||||
<MicrosoftExtensionsCachingMemoryPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsCachingMemoryPackageVersion>
|
||||
<MicrosoftExtensionsCachingSqlServerPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsCachingSqlServerPackageVersion>
|
||||
<MicrosoftExtensionsCachingStackExchangeRedisPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsCachingStackExchangeRedisPackageVersion>
|
||||
<MicrosoftExtensionsClosedGenericMatcherSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsClosedGenericMatcherSourcesPackageVersion>
|
||||
<MicrosoftExtensionsCommandLineUtilsSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsCommandLineUtilsSourcesPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationAbstractionsPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsConfigurationAbstractionsPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationAzureKeyVaultPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsConfigurationAzureKeyVaultPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationBinderPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsConfigurationBinderPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationCommandLinePackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsConfigurationCommandLinePackageVersion>
|
||||
<MicrosoftExtensionsConfigurationEnvironmentVariablesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsConfigurationEnvironmentVariablesPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationFileExtensionsPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsConfigurationFileExtensionsPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationIniPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsConfigurationIniPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationJsonPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsConfigurationJsonPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationKeyPerFilePackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsConfigurationKeyPerFilePackageVersion>
|
||||
<MicrosoftExtensionsConfigurationPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsConfigurationPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationUserSecretsPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsConfigurationUserSecretsPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationXmlPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsConfigurationXmlPackageVersion>
|
||||
<MicrosoftExtensionsCopyOnWriteDictionarySourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsCopyOnWriteDictionarySourcesPackageVersion>
|
||||
<MicrosoftExtensionsDependencyInjectionAbstractionsPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsDependencyInjectionAbstractionsPackageVersion>
|
||||
<MicrosoftExtensionsDependencyInjectionPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsDependencyInjectionPackageVersion>
|
||||
<MicrosoftExtensionsDependencyInjectionSpecificationTestsPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsDependencyInjectionSpecificationTestsPackageVersion>
|
||||
<MicrosoftExtensionsDiagnosticAdapterPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsDiagnosticAdapterPackageVersion>
|
||||
<MicrosoftExtensionsFileProvidersAbstractionsPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsFileProvidersAbstractionsPackageVersion>
|
||||
<MicrosoftExtensionsFileProvidersCompositePackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsFileProvidersCompositePackageVersion>
|
||||
<MicrosoftExtensionsFileProvidersEmbeddedPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsFileProvidersEmbeddedPackageVersion>
|
||||
<MicrosoftExtensionsFileProvidersPhysicalPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsFileProvidersPhysicalPackageVersion>
|
||||
<MicrosoftExtensionsFileSystemGlobbingPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsFileSystemGlobbingPackageVersion>
|
||||
<MicrosoftExtensionsHashCodeCombinerSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsHashCodeCombinerSourcesPackageVersion>
|
||||
<MicrosoftExtensionsLoggingAbstractionsPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsLoggingAbstractionsPackageVersion>
|
||||
<MicrosoftExtensionsLoggingAzureAppServicesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsLoggingAzureAppServicesPackageVersion>
|
||||
<MicrosoftExtensionsLoggingConfigurationPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsLoggingConfigurationPackageVersion>
|
||||
<MicrosoftExtensionsLoggingConsolePackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsLoggingConsolePackageVersion>
|
||||
<MicrosoftExtensionsLoggingDebugPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsLoggingDebugPackageVersion>
|
||||
<MicrosoftExtensionsLoggingEventSourcePackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsLoggingEventSourcePackageVersion>
|
||||
<MicrosoftExtensionsLoggingPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsLoggingPackageVersion>
|
||||
<MicrosoftExtensionsLoggingTestingPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsLoggingTestingPackageVersion>
|
||||
<MicrosoftExtensionsLoggingTraceSourcePackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsLoggingTraceSourcePackageVersion>
|
||||
<MicrosoftExtensionsNonCapturingTimerSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsNonCapturingTimerSourcesPackageVersion>
|
||||
<MicrosoftExtensionsObjectMethodExecutorSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsObjectMethodExecutorSourcesPackageVersion>
|
||||
<MicrosoftExtensionsObjectPoolPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsObjectPoolPackageVersion>
|
||||
<MicrosoftExtensionsOptionsConfigurationExtensionsPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsOptionsConfigurationExtensionsPackageVersion>
|
||||
<MicrosoftExtensionsOptionsDataAnnotationsPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsOptionsDataAnnotationsPackageVersion>
|
||||
<MicrosoftExtensionsOptionsPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsOptionsPackageVersion>
|
||||
<MicrosoftExtensionsParameterDefaultValueSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsParameterDefaultValueSourcesPackageVersion>
|
||||
<MicrosoftExtensionsPrimitivesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsPrimitivesPackageVersion>
|
||||
<MicrosoftExtensionsProcessSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsProcessSourcesPackageVersion>
|
||||
<MicrosoftExtensionsPropertyActivatorSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsPropertyActivatorSourcesPackageVersion>
|
||||
<MicrosoftExtensionsPropertyHelperSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsPropertyHelperSourcesPackageVersion>
|
||||
<MicrosoftExtensionsRazorViewsSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsRazorViewsSourcesPackageVersion>
|
||||
<MicrosoftExtensionsSecurityHelperSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsSecurityHelperSourcesPackageVersion>
|
||||
<MicrosoftExtensionsStackTraceSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsStackTraceSourcesPackageVersion>
|
||||
<MicrosoftExtensionsTypeNameHelperSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsTypeNameHelperSourcesPackageVersion>
|
||||
<MicrosoftExtensionsValueStopwatchSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsValueStopwatchSourcesPackageVersion>
|
||||
<MicrosoftExtensionsWebEncodersSourcesPackageVersion>3.0.0-preview-181108-06</MicrosoftExtensionsWebEncodersSourcesPackageVersion>
|
||||
<InternalAspNetCoreAnalyzersPackageVersion>3.0.0-preview-181113-11</InternalAspNetCoreAnalyzersPackageVersion>
|
||||
<MicrosoftAspNetCoreAnalyzerTestingPackageVersion>3.0.0-preview-181113-11</MicrosoftAspNetCoreAnalyzerTestingPackageVersion>
|
||||
<MicrosoftAspNetCoreBenchmarkRunnerSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftAspNetCoreBenchmarkRunnerSourcesPackageVersion>
|
||||
<MicrosoftAspNetCoreCertificatesGenerationSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftAspNetCoreCertificatesGenerationSourcesPackageVersion>
|
||||
<MicrosoftAspNetCoreTestingPackageVersion>3.0.0-preview-181113-11</MicrosoftAspNetCoreTestingPackageVersion>
|
||||
<MicrosoftExtensionsActivatorUtilitiesSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsActivatorUtilitiesSourcesPackageVersion>
|
||||
<MicrosoftExtensionsCachingAbstractionsPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsCachingAbstractionsPackageVersion>
|
||||
<MicrosoftExtensionsCachingMemoryPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsCachingMemoryPackageVersion>
|
||||
<MicrosoftExtensionsCachingSqlServerPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsCachingSqlServerPackageVersion>
|
||||
<MicrosoftExtensionsCachingStackExchangeRedisPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsCachingStackExchangeRedisPackageVersion>
|
||||
<MicrosoftExtensionsClosedGenericMatcherSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsClosedGenericMatcherSourcesPackageVersion>
|
||||
<MicrosoftExtensionsCommandLineUtilsSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsCommandLineUtilsSourcesPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationAbstractionsPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsConfigurationAbstractionsPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationAzureKeyVaultPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsConfigurationAzureKeyVaultPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationBinderPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsConfigurationBinderPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationCommandLinePackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsConfigurationCommandLinePackageVersion>
|
||||
<MicrosoftExtensionsConfigurationEnvironmentVariablesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsConfigurationEnvironmentVariablesPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationFileExtensionsPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsConfigurationFileExtensionsPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationIniPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsConfigurationIniPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationJsonPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsConfigurationJsonPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationKeyPerFilePackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsConfigurationKeyPerFilePackageVersion>
|
||||
<MicrosoftExtensionsConfigurationPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsConfigurationPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationUserSecretsPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsConfigurationUserSecretsPackageVersion>
|
||||
<MicrosoftExtensionsConfigurationXmlPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsConfigurationXmlPackageVersion>
|
||||
<MicrosoftExtensionsCopyOnWriteDictionarySourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsCopyOnWriteDictionarySourcesPackageVersion>
|
||||
<MicrosoftExtensionsDependencyInjectionAbstractionsPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsDependencyInjectionAbstractionsPackageVersion>
|
||||
<MicrosoftExtensionsDependencyInjectionPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsDependencyInjectionPackageVersion>
|
||||
<MicrosoftExtensionsDependencyInjectionSpecificationTestsPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsDependencyInjectionSpecificationTestsPackageVersion>
|
||||
<MicrosoftExtensionsDiagnosticAdapterPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsDiagnosticAdapterPackageVersion>
|
||||
<MicrosoftExtensionsFileProvidersAbstractionsPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsFileProvidersAbstractionsPackageVersion>
|
||||
<MicrosoftExtensionsFileProvidersCompositePackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsFileProvidersCompositePackageVersion>
|
||||
<MicrosoftExtensionsFileProvidersEmbeddedPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsFileProvidersEmbeddedPackageVersion>
|
||||
<MicrosoftExtensionsFileProvidersPhysicalPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsFileProvidersPhysicalPackageVersion>
|
||||
<MicrosoftExtensionsFileSystemGlobbingPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsFileSystemGlobbingPackageVersion>
|
||||
<MicrosoftExtensionsHashCodeCombinerSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsHashCodeCombinerSourcesPackageVersion>
|
||||
<MicrosoftExtensionsLoggingAbstractionsPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsLoggingAbstractionsPackageVersion>
|
||||
<MicrosoftExtensionsLoggingAzureAppServicesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsLoggingAzureAppServicesPackageVersion>
|
||||
<MicrosoftExtensionsLoggingConfigurationPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsLoggingConfigurationPackageVersion>
|
||||
<MicrosoftExtensionsLoggingConsolePackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsLoggingConsolePackageVersion>
|
||||
<MicrosoftExtensionsLoggingDebugPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsLoggingDebugPackageVersion>
|
||||
<MicrosoftExtensionsLoggingEventSourcePackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsLoggingEventSourcePackageVersion>
|
||||
<MicrosoftExtensionsLoggingPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsLoggingPackageVersion>
|
||||
<MicrosoftExtensionsLoggingTestingPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsLoggingTestingPackageVersion>
|
||||
<MicrosoftExtensionsLoggingTraceSourcePackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsLoggingTraceSourcePackageVersion>
|
||||
<MicrosoftExtensionsNonCapturingTimerSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsNonCapturingTimerSourcesPackageVersion>
|
||||
<MicrosoftExtensionsObjectMethodExecutorSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsObjectMethodExecutorSourcesPackageVersion>
|
||||
<MicrosoftExtensionsObjectPoolPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsObjectPoolPackageVersion>
|
||||
<MicrosoftExtensionsOptionsConfigurationExtensionsPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsOptionsConfigurationExtensionsPackageVersion>
|
||||
<MicrosoftExtensionsOptionsDataAnnotationsPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsOptionsDataAnnotationsPackageVersion>
|
||||
<MicrosoftExtensionsOptionsPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsOptionsPackageVersion>
|
||||
<MicrosoftExtensionsParameterDefaultValueSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsParameterDefaultValueSourcesPackageVersion>
|
||||
<MicrosoftExtensionsPrimitivesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsPrimitivesPackageVersion>
|
||||
<MicrosoftExtensionsProcessSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsProcessSourcesPackageVersion>
|
||||
<MicrosoftExtensionsPropertyActivatorSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsPropertyActivatorSourcesPackageVersion>
|
||||
<MicrosoftExtensionsPropertyHelperSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsPropertyHelperSourcesPackageVersion>
|
||||
<MicrosoftExtensionsRazorViewsSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsRazorViewsSourcesPackageVersion>
|
||||
<MicrosoftExtensionsSecurityHelperSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsSecurityHelperSourcesPackageVersion>
|
||||
<MicrosoftExtensionsStackTraceSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsStackTraceSourcesPackageVersion>
|
||||
<MicrosoftExtensionsTypeNameHelperSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsTypeNameHelperSourcesPackageVersion>
|
||||
<MicrosoftExtensionsValueStopwatchSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsValueStopwatchSourcesPackageVersion>
|
||||
<MicrosoftExtensionsWebEncodersSourcesPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsWebEncodersSourcesPackageVersion>
|
||||
<MicrosoftExtensionsWebEncodersPackageVersion>3.0.0-preview-181113-11</MicrosoftExtensionsWebEncodersPackageVersion>
|
||||
<!-- Packages from aspnet/EntityFrameworkCore -->
|
||||
<MicrosoftEntityFrameworkCoreAbstractionsPackageVersion>3.0.0-preview-181109-02</MicrosoftEntityFrameworkCoreAbstractionsPackageVersion>
|
||||
<MicrosoftEntityFrameworkCoreAnalyzersPackageVersion>3.0.0-preview-181109-02</MicrosoftEntityFrameworkCoreAnalyzersPackageVersion>
|
||||
|
|
@ -116,10 +117,12 @@
|
|||
<!-- Determined by build tools -->
|
||||
<InternalAspNetCoreSdkPackageVersion>$(KoreBuildVersion)</InternalAspNetCoreSdkPackageVersion>
|
||||
<InternalAspNetCoreSiteExtensionSdkPackageVersion>$(KoreBuildVersion)</InternalAspNetCoreSiteExtensionSdkPackageVersion>
|
||||
<InternalAspNetCoreSdkPackageVersion Condition=" '$(KoreBuildVersion)' == '' ">2.2.1-build-20181114.3</InternalAspNetCoreSdkPackageVersion>
|
||||
</PropertyGroup>
|
||||
|
||||
<!-- These are package versions that should not be overridden or updated by automation. -->
|
||||
<PropertyGroup Label="Package Versions: Pinned">
|
||||
<!-- 3rd party dependencies -->
|
||||
<AngleSharpPackageVersion>0.9.9</AngleSharpPackageVersion>
|
||||
<BenchmarkDotNetPackageVersion>0.10.13</BenchmarkDotNetPackageVersion>
|
||||
|
||||
|
|
@ -212,6 +215,7 @@
|
|||
<PollyPackageVersion>6.0.1</PollyPackageVersion>
|
||||
<SeleniumFirefoxWebDriverPackageVersion>0.20.0</SeleniumFirefoxWebDriverPackageVersion>
|
||||
<SeleniumSupportPackageVersion>3.12.1</SeleniumSupportPackageVersion>
|
||||
<SeleniumWebDriverChromeDriverPackageVersion>2.43.0</SeleniumWebDriverChromeDriverPackageVersion>
|
||||
<SeleniumWebDriverMicrosoftDriverPackageVersion>17.17134.0</SeleniumWebDriverMicrosoftDriverPackageVersion>
|
||||
<SeleniumWebDriverPackageVersion>3.12.1</SeleniumWebDriverPackageVersion>
|
||||
<SerilogExtensionsLoggingPackageVersion>1.4.0</SerilogExtensionsLoggingPackageVersion>
|
||||
|
|
|
|||
|
|
@ -71,6 +71,7 @@
|
|||
<ExternalDependency Include="Microsoft.Extensions.TypeNameHelper.Sources" Version="$(MicrosoftExtensionsTypeNameHelperSourcesPackageVersion)" />
|
||||
<ExternalDependency Include="Microsoft.Extensions.ValueStopwatch.Sources" Version="$(MicrosoftExtensionsValueStopwatchSourcesPackageVersion)" />
|
||||
<ExternalDependency Include="Microsoft.Extensions.WebEncoders.Sources" Version="$(MicrosoftExtensionsWebEncodersSourcesPackageVersion)" />
|
||||
<ExternalDependency Include="Microsoft.Extensions.WebEncoders" Version="$(MicrosoftExtensionsWebEncodersPackageVersion)" />
|
||||
<ExternalDependency Include="Microsoft.EntityFrameworkCore.Abstractions" Version="$(MicrosoftEntityFrameworkCoreAbstractionsPackageVersion)" />
|
||||
<ExternalDependency Include="Microsoft.EntityFrameworkCore.Analyzers" Version="$(MicrosoftEntityFrameworkCoreAnalyzersPackageVersion)" />
|
||||
<ExternalDependency Include="Microsoft.EntityFrameworkCore.Design" Version="$(MicrosoftEntityFrameworkCoreDesignPackageVersion)" />
|
||||
|
|
|
|||
|
|
@ -4,6 +4,8 @@
|
|||
<PropertyGroup>
|
||||
<!-- This repo does not have solutions to build -->
|
||||
<DisableDefaultTargets>true</DisableDefaultTargets>
|
||||
<DisableDefaultItems>true</DisableDefaultItems>
|
||||
<BuildSolutions>false</BuildSolutions>
|
||||
|
||||
<SkipTests>false</SkipTests>
|
||||
<SkipTests Condition="'$(CompileOnly)' == 'true'">true</SkipTests>
|
||||
|
|
@ -13,8 +15,6 @@
|
|||
|
||||
<DependencyPackageDir>$(RepositoryRoot).deps\build\</DependencyPackageDir>
|
||||
<SignedDependencyPackageDir>$(RepositoryRoot).deps\Signed\Packages\</SignedDependencyPackageDir>
|
||||
<!-- SignCheck currently fails when verifying vsix files. See https://github.com/dotnet/arcade/issues/1306. -->
|
||||
<DisableSignCheck>true</DisableSignCheck>
|
||||
<SignCheckExclusionsFile>$(RepositoryRoot)eng\signcheck.exclusions.txt</SignCheckExclusionsFile>
|
||||
<!-- This creates false-positives on many of the native .dll's we produce or re-distribute from other teams. -->
|
||||
<DisableSignCheckStrongName>true</DisableSignCheckStrongName>
|
||||
|
|
@ -49,6 +49,22 @@
|
|||
<SharedFrameworkName Include="Microsoft.AspNetCore.App" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectToExclude Include="
|
||||
$(RepositoryRoot)src\Middleware\WebSockets\samples\**\*.csproj;
|
||||
$(RepositoryRoot)src\Tools\dotnet-watch\test\TestProjects\**\*.csproj;
|
||||
" />
|
||||
|
||||
<ProjectToBuild Include="
|
||||
$(RepositoryRoot)src\Features\JsonPatch\**\*.*proj;
|
||||
$(RepositoryRoot)src\DataProtection\**\*.*proj;
|
||||
$(RepositoryRoot)src\Html\**\*.*proj;
|
||||
$(RepositoryRoot)src\Tools\**\*.*proj;
|
||||
$(RepositoryRoot)src\Middleware\**\*.*proj;
|
||||
"
|
||||
Exclude="@(ProjectToExclude)" />
|
||||
</ItemGroup>
|
||||
|
||||
<!-- Properties for publishing -->
|
||||
<PropertyGroup>
|
||||
<!-- myget = non-orchestrated builds -->
|
||||
|
|
|
|||
|
|
@ -15,20 +15,60 @@
|
|||
<GeneratedRestoreSourcesPropsPath>$(IntermediateDir)sources.g.props</GeneratedRestoreSourcesPropsPath>
|
||||
<GeneratedBrandingPropsPath>$(IntermediateDir)branding.g.props</GeneratedBrandingPropsPath>
|
||||
|
||||
<PrepareDependsOn>SetTeamCityBuildNumberToVersion;$(PrepareDependsOn);VerifyPackageArtifactConfig;VerifyExternalDependencyConfig;PrepareOutputPaths</PrepareDependsOn>
|
||||
<PrepareDependsOn>SetTeamCityBuildNumberToVersion;$(PrepareDependsOn)</PrepareDependsOn>
|
||||
<PrepareDependsOn Condition="'$(_ProjectsOnly)' != 'true'">$(PrepareDependsOn);VerifyPackageArtifactConfig;VerifyExternalDependencyConfig;PrepareOutputPaths</PrepareDependsOn>
|
||||
<CleanDependsOn>$(CleanDependsOn);CleanArtifacts;CleanRepoArtifacts</CleanDependsOn>
|
||||
<RestoreDependsOn>$(RestoreDependsOn);InstallDotNet</RestoreDependsOn>
|
||||
<CompileDependsOn>$(CompileDependsOn);BuildRepositories;BuildSharedFx</CompileDependsOn>
|
||||
<PackageDependsOn Condition="'$(TestOnly)' != 'true'">$(PackageDependsOn);CheckExpectedPackagesExist;CodeSign</PackageDependsOn>
|
||||
<TestDependsOn>$(TestDependsOn);_TestRepositories</TestDependsOn>
|
||||
<GetArtifactInfoDependsOn>$(GetArtifactInfoDependsOn);ResolveRepoInfo</GetArtifactInfoDependsOn>
|
||||
<RestoreDependsOn>$(RestoreDependsOn);InstallDotNet;RestoreProjects</RestoreDependsOn>
|
||||
<CompileDependsOn>$(CompileDependsOn);BuildProjects</CompileDependsOn>
|
||||
<CompileDependsOn Condition="'$(_ProjectsOnly)' != 'true'">$(CompileDependsOn);PackProjects;BuildRepositories;BuildSharedFx</CompileDependsOn>
|
||||
<PackageDependsOn Condition=" '$(_ProjectsOnly)' == 'true'">$(PackageDependsOn);PackProjects</PackageDependsOn>
|
||||
<PackageDependsOn Condition="'$(TestOnly)' != 'true' AND '$(_ProjectsOnly)' != 'true'">$(PackageDependsOn);CheckExpectedPackagesExist</PackageDependsOn>
|
||||
<PackageDependsOn Condition="'$(TestOnly)' != 'true'">$(PackageDependsOn);CodeSign</PackageDependsOn>
|
||||
<TestDependsOn>$(TestDependsOn);TestProjects</TestDependsOn>
|
||||
<TestDependsOn Condition="'$(_ProjectsOnly)' != 'true'">$(TestDependsOn);_TestRepositories</TestDependsOn>
|
||||
<GetArtifactInfoDependsOn>$(GetArtifactInfoDependsOn);GetProjectArtifactInfo</GetArtifactInfoDependsOn>
|
||||
<GetArtifactInfoDependsOn Condition="'$(_ProjectsOnly)' != 'true'">$(GetArtifactInfoDependsOn);ResolveRepoInfo</GetArtifactInfoDependsOn>
|
||||
</PropertyGroup>
|
||||
|
||||
<Target Name="PrepareOutputPaths">
|
||||
<MakeDir Directories="$(ArtifactsDir);$(BuildDir)" />
|
||||
</Target>
|
||||
|
||||
<Target Name="ResolveRepoInfo" DependsOnTargets="_PrepareRepositories;GetLineupPackageInfo">
|
||||
<Target Name="GenerateProjectList" DependsOnTargets="ResolveProjects">
|
||||
<MSBuild Projects="@(ProjectToBuild)"
|
||||
Targets="GetReferencesProvided"
|
||||
BuildInParallel="true"
|
||||
SkipNonexistentTargets="true"
|
||||
SkipNonexistentProjects="true" >
|
||||
|
||||
<Output TaskParameter="TargetOutputs" ItemName="_ProjectReferenceProvider"/>
|
||||
</MSBuild>
|
||||
|
||||
<PropertyGroup>
|
||||
<ProjectListFile>$(MSBuildThisFileDirectory)..\eng\ProjectReferences.props</ProjectListFile>
|
||||
<ProjectListContent>
|
||||
<![CDATA[
|
||||
<!-- This file is automatically generated. Run `build.cmd /t:GenerateProjectList` to update. -->
|
||||
<Project>
|
||||
<ItemGroup>
|
||||
@(_ProjectReferenceProvider->'<ProjectReferenceProvider Include="%(Identity)" ProjectPath="%24(RepositoryRoot)%(ProjectFileRelativePath)" />', '%0A ')
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
]]>
|
||||
</ProjectListContent>
|
||||
</PropertyGroup>
|
||||
|
||||
<WriteLinesToFile File="$(ProjectListFile)" Lines="$(ProjectListContent)" Overwrite="true" />
|
||||
</Target>
|
||||
|
||||
<Target Name="_ResolveProjectArtifactsInfoShipped" AfterTargets="GetProjectArtifactInfo">
|
||||
<ItemGroup>
|
||||
<ShippedArtifactInfo Include="@(ArtifactInfo)" Condition="'%(ArtifactInfo.IsShipped)' == 'true'" />
|
||||
<ArtifactInfo Remove="@(ShippedArtifactInfo)" />
|
||||
</ItemGroup>
|
||||
</Target>
|
||||
|
||||
<Target Name="ResolveRepoInfo" DependsOnTargets="_ResolveProjectArtifactsInfoShipped;_PrepareRepositories;GetLineupPackageInfo">
|
||||
<!-- We need to pass the NETCoreApp package versions to msbuild so that it doesn't complain about us using a different one than it was restored against. -->
|
||||
<PropertyGroup>
|
||||
<DesignTimeBuildProps>$(BuildProperties);MicrosoftNETCoreAppPackageVersion=$(MicrosoftNETCoreAppPackageVersion);</DesignTimeBuildProps>
|
||||
|
|
@ -238,14 +278,15 @@
|
|||
<Target Name="BuildRepositories"
|
||||
DependsOnTargets="_PrepareRepositories;GeneratePropsFiles;ComputeGraph;_BuildRepositories" />
|
||||
|
||||
<Target Name="ListExpectedPackages" DependsOnTargets="ResolveRepoInfo">
|
||||
<Target Name="ListExpectedPackages" DependsOnTargets="GetProjectArtifactInfo;GetFxProjectArtifactInfo;ResolveRepoInfo">
|
||||
<WriteLinesToFile File="$(RepositoryRoot)artifacts\packages.csv" Lines="PackageId,Version;@(ArtifactInfo->WithMetadataValue('ArtifactType', 'NuGetPackage')->'%(PackageId),%(Version)')" Overwrite="true" />
|
||||
</Target>
|
||||
|
||||
<Target Name="ComputeGraph" DependsOnTargets="ResolveRepoInfo;GeneratePropsFiles">
|
||||
<Target Name="ComputeGraph" DependsOnTargets="GetProjectArtifactInfo;GetFxProjectArtifactInfo;ResolveRepoInfo;GeneratePropsFiles">
|
||||
<ItemGroup>
|
||||
<_UndeclaredPackageArtifact Include="%(ArtifactInfo.PackageId)" Condition="'%(ArtifactInfo.ArtifactType)' == 'NuGetPackage'" />
|
||||
<_UndeclaredPackageArtifact Remove="@(PackageArtifact)" />
|
||||
<RepositoryBuildOrder Remove="@(ShippedRepository)" />
|
||||
</ItemGroup>
|
||||
|
||||
<Error Text="Undeclared package artifacts. Add these to artifacts.props:%0A - @(_UndeclaredPackageArtifact, '%0A - ')"
|
||||
|
|
|
|||
|
|
@ -7,6 +7,13 @@
|
|||
$(DotNetAdditionalRestoreSources);
|
||||
$(DotNetRestoreSources);
|
||||
</RestoreSources>
|
||||
|
||||
<!-- This is the 2.2.0 RTM feed. This is necessary until 2.2.0 ships to nuget.org -->
|
||||
<RestoreSources>
|
||||
$(RestoreSources);
|
||||
https://dotnetfeed.blob.core.windows.net/orchestrated-release-2-2/20181110-02/final/index.json;
|
||||
</RestoreSources>
|
||||
|
||||
<RestoreSources Condition=" '$(DotNetBuildOffline)' != 'true' ">
|
||||
$(RestoreSources);
|
||||
https://dotnetfeed.blob.core.windows.net/dotnet-core/index.json;
|
||||
|
|
|
|||
|
|
@ -41,18 +41,14 @@
|
|||
<Repository Include="AzureIntegration" />
|
||||
<Repository Include="BasicMiddleware" />
|
||||
<Repository Include="CORS" />
|
||||
<Repository Include="DataProtection" RootPath="$(RepositoryRoot)src\DataProtection\" />
|
||||
<Repository Include="Diagnostics" />
|
||||
<Repository Include="DotNetTools" />
|
||||
<Repository Include="Hosting" />
|
||||
<Repository Include="HtmlAbstractions" />
|
||||
<Repository Include="HttpAbstractions" />
|
||||
<Repository Include="HttpClientFactory" />
|
||||
<Repository Include="HttpSysServer" />
|
||||
<Repository Include="Identity" />
|
||||
<Repository Include="IISIntegration" RootPath="$(RepositoryRoot)src\IISIntegration\" />
|
||||
<Repository Include="JavaScriptServices" />
|
||||
<Repository Include="JsonPatch" />
|
||||
<Repository Include="KestrelHttpServer" />
|
||||
<Repository Include="Localization" />
|
||||
<Repository Include="MetaPackages" PatchPolicy="CascadeVersions" />
|
||||
|
|
@ -65,7 +61,6 @@
|
|||
<Repository Include="SignalR" />
|
||||
<Repository Include="StaticFiles" />
|
||||
<Repository Include="Templating" PatchPolicy="AlwaysUpdateAndCascadeVersions" />
|
||||
<Repository Include="WebSockets" RootPath="$(RepositoryRoot)src\WebSockets\" />
|
||||
|
||||
<!-- Test-only repos -->
|
||||
<Repository Include="AuthSamples" PatchPolicy="AlwaysUpdateAndCascadeVersions" />
|
||||
|
|
|
|||
|
|
@ -6,6 +6,7 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Remove="Internal.AspNetCore.Sdk" />
|
||||
<PackageReference Include="Microsoft.DotNet.Archive" Version="$(MicrosoftDotNetArchivePackageVersion)" />
|
||||
<PackageReference Include="NuGet.Build.Tasks" Version="$(NuGetInMSBuildVersion)" PrivateAssets="All" />
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyModel" Version="$(DevDependency_MicrosoftExtensionsDependencyModelPackageVersion)" PrivateAssets="All" />
|
||||
|
|
|
|||
|
|
@ -0,0 +1,41 @@
|
|||
Preparing new servicing updates
|
||||
===============================
|
||||
|
||||
In order to prepare this repo to build a new servicing update, the following changes need to be made.
|
||||
|
||||
* Increment the patch version in the [version.props](/version.props) file in the repository root.
|
||||
|
||||
```diff
|
||||
- <AspNetCorePatchVersion>7</AspNetCorePatchVersion>
|
||||
+ <AspNetCorePatchVersion>8</AspNetCorePatchVersion>
|
||||
```
|
||||
|
||||
* Update the package archive baselines. This is used to make sure each build of the package archives we give to Azure only contains new files and does
|
||||
not require overwriting existing files. See [src/PackageArchive/ZipManifestGenerator/](/src/PackageArchive/ZipManifestGenerator/README.md) for instructions on how to run this tool.
|
||||
|
||||
* Update the package baselines. This is used to ensure packages keep a consistent set of dependencies between releases.
|
||||
See [eng/tools/BaselineGenerator/](/eng/tools/BaselineGenerator/README.md) for instructions on how to run this tool.
|
||||
|
||||
* **For packages with source code in this repo (not a submodule):** Update the list of packages in [eng/PatchConfig.props](/eng/PatchConfig.props) to list which packages should be patching in this release.
|
||||
|
||||
* **For packages still building from submodules:** Update the list of repositories which will contain changes in [build/submodules.props](/build/submodules.props).
|
||||
|
||||
* `<ShippedRepository>` items represent repos which were released in a previous patch, and will not contain servicing updates in the next patch.
|
||||
* `<Repository>` items represent repos which will produce new packages in this patch.
|
||||
* It is usually best to move everything to `<ShippedRepository>` and then iteratively add them back to `<Repository>` as new repos receive approval to patch.
|
||||
* Don't change the `PatchPolicy` attribute. The build system uses this to ensure patching rules are obeyed.
|
||||
|
||||
* For each repository still listed as a `<Repository>`, update the version.props file in that submodule. For example, https://github.com/aspnet/Templating/pull/824
|
||||
|
||||
* The version prefix in repos should match the version of ASP.NET Core.
|
||||
* Exception: SignalR, which is "1.1", not "2.1".
|
||||
* This leaves holes in versioning, which is okay. This may mean you increment the patch value by more than one. Example:
|
||||
* EF Core ships patches in 2.1.4 as "2.1.4"
|
||||
* EF Core does not ship patches in 2.1.5 or 2.1.6
|
||||
* EF Core ships in 2.1.7, therefore, EFCore's version.props file should jump from 2.1.4 to 2.1.7.
|
||||
|
||||
```diff
|
||||
<!-- Example change to modules/EntityFrameworkCore/version.props -->
|
||||
- <VersionPrefix>2.1.4</VersionPrefix>
|
||||
+ <VersionPrefix>2.1.7</VersionPrefix>
|
||||
```
|
||||
|
|
@ -0,0 +1,116 @@
|
|||
<!-- Auto generated. Do not edit manually, use eng/tools/BaselineGenerator/ to recreate. -->
|
||||
<Project>
|
||||
<PropertyGroup>
|
||||
<MSBuildAllProjects>$(MSBuildAllProjects);$(MSBuildThisFileFullPath)</MSBuildAllProjects>
|
||||
<AspNetCoreBaselineVersion>2.2.0</AspNetCoreBaselineVersion>
|
||||
</PropertyGroup>
|
||||
<!-- Package: Microsoft.AspNetCore.Cryptography.Internal-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.Cryptography.Internal' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.Cryptography.Internal' AND '$(TargetFramework)' == 'netstandard2.0' " />
|
||||
<!-- Package: Microsoft.AspNetCore.Cryptography.KeyDerivation-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.Cryptography.KeyDerivation' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.Cryptography.KeyDerivation' AND '$(TargetFramework)' == 'netcoreapp2.0' ">
|
||||
<BaselinePackageReference Include="Microsoft.AspNetCore.Cryptography.Internal" Version="[2.2.0, )" />
|
||||
</ItemGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.Cryptography.KeyDerivation' AND '$(TargetFramework)' == 'netstandard2.0' ">
|
||||
<BaselinePackageReference Include="Microsoft.AspNetCore.Cryptography.Internal" Version="[2.2.0, )" />
|
||||
</ItemGroup>
|
||||
<!-- Package: Microsoft.AspNetCore.DataProtection-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection' AND '$(TargetFramework)' == 'netstandard2.0' ">
|
||||
<BaselinePackageReference Include="Microsoft.AspNetCore.DataProtection.Abstractions" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="Microsoft.AspNetCore.Cryptography.Internal" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="Microsoft.AspNetCore.Hosting.Abstractions" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="Microsoft.Extensions.DependencyInjection.Abstractions" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="Microsoft.Extensions.Options" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="Microsoft.Win32.Registry" Version="[4.5.0, )" />
|
||||
<BaselinePackageReference Include="System.Security.Cryptography.Xml" Version="[4.5.0, )" />
|
||||
<BaselinePackageReference Include="System.Security.Principal.Windows" Version="[4.5.0, )" />
|
||||
</ItemGroup>
|
||||
<!-- Package: Microsoft.AspNetCore.DataProtection.Abstractions-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.Abstractions' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.Abstractions' AND '$(TargetFramework)' == 'netstandard2.0' " />
|
||||
<!-- Package: Microsoft.AspNetCore.DataProtection.AzureKeyVault-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.AzureKeyVault' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.AzureKeyVault' AND '$(TargetFramework)' == 'netstandard2.0' ">
|
||||
<BaselinePackageReference Include="Microsoft.AspNetCore.DataProtection" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="Microsoft.Azure.KeyVault" Version="[2.3.2, )" />
|
||||
<BaselinePackageReference Include="Microsoft.IdentityModel.Clients.ActiveDirectory" Version="[3.19.8, )" />
|
||||
</ItemGroup>
|
||||
<!-- Package: Microsoft.AspNetCore.DataProtection.AzureStorage-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.AzureStorage' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.AzureStorage' AND '$(TargetFramework)' == 'netstandard2.0' ">
|
||||
<BaselinePackageReference Include="Microsoft.AspNetCore.DataProtection" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="WindowsAzure.Storage" Version="[8.1.4, )" />
|
||||
</ItemGroup>
|
||||
<!-- Package: Microsoft.AspNetCore.DataProtection.EntityFrameworkCore-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.EntityFrameworkCore' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.EntityFrameworkCore' AND '$(TargetFramework)' == 'netstandard2.0' ">
|
||||
<BaselinePackageReference Include="Microsoft.AspNetCore.DataProtection" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="Microsoft.EntityFrameworkCore" Version="[2.2.0, )" />
|
||||
</ItemGroup>
|
||||
<!-- Package: Microsoft.AspNetCore.DataProtection.Extensions-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.Extensions' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.Extensions' AND '$(TargetFramework)' == 'netstandard2.0' ">
|
||||
<BaselinePackageReference Include="Microsoft.AspNetCore.DataProtection" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="Microsoft.Extensions.DependencyInjection" Version="[2.2.0, )" />
|
||||
</ItemGroup>
|
||||
<!-- Package: Microsoft.AspNetCore.DataProtection.StackExchangeRedis-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.StackExchangeRedis' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.StackExchangeRedis' AND '$(TargetFramework)' == 'netstandard2.0' ">
|
||||
<BaselinePackageReference Include="Microsoft.AspNetCore.DataProtection" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="StackExchange.Redis" Version="[2.0.513, )" />
|
||||
</ItemGroup>
|
||||
<!-- Package: Microsoft.AspNetCore.DataProtection.SystemWeb-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.SystemWeb' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.DataProtection.SystemWeb' AND '$(TargetFramework)' == 'net461' ">
|
||||
<BaselinePackageReference Include="Microsoft.AspNetCore.DataProtection" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="Microsoft.Extensions.DependencyInjection" Version="[2.2.0, )" />
|
||||
</ItemGroup>
|
||||
<!-- Package: Microsoft.AspNetCore.Html.Abstractions-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.Html.Abstractions' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.Html.Abstractions' AND '$(TargetFramework)' == 'netstandard2.0' ">
|
||||
<BaselinePackageReference Include="System.Text.Encodings.Web" Version="[4.5.0, )" />
|
||||
</ItemGroup>
|
||||
<!-- Package: Microsoft.AspNetCore.JsonPatch-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.JsonPatch' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.JsonPatch' AND '$(TargetFramework)' == 'netstandard2.0' ">
|
||||
<BaselinePackageReference Include="Microsoft.CSharp" Version="[4.5.0, )" />
|
||||
<BaselinePackageReference Include="Newtonsoft.Json" Version="[11.0.2, )" />
|
||||
</ItemGroup>
|
||||
<!-- Package: Microsoft.AspNetCore.WebSockets-->
|
||||
<PropertyGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.WebSockets' ">
|
||||
<BaselinePackageVersion>2.2.0</BaselinePackageVersion>
|
||||
</PropertyGroup>
|
||||
<ItemGroup Condition=" '$(PackageId)' == 'Microsoft.AspNetCore.WebSockets' AND '$(TargetFramework)' == 'netstandard2.0' ">
|
||||
<BaselinePackageReference Include="Microsoft.AspNetCore.Http.Extensions" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="Microsoft.Extensions.Options" Version="[2.2.0, )" />
|
||||
<BaselinePackageReference Include="System.Net.WebSockets.WebSocketProtocol" Version="[4.5.1, )" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,72 @@
|
|||
<!-- This file is a work in progress as we merge repos and move content here from build/dependencies.props. -->
|
||||
|
||||
<Project>
|
||||
<PropertyGroup>
|
||||
<MSBuildAllProjects>$(MSBuildAllProjects);$(MSBuildThisFileFullPath)</MSBuildAllProjects>
|
||||
</PropertyGroup>
|
||||
|
||||
<Import Project="dependencies.temp.props" />
|
||||
|
||||
<ItemGroup Label="ProdCon dependencies">
|
||||
<!-- These dependencies must use version variables because they may be overriden by ProdCon builds. -->
|
||||
<LatestPackageReference Include="Microsoft.AspNetCore.Certificates.Generation.Sources" Version="$(MicrosoftAspNetCoreCertificatesGenerationSourcesPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.AspNetCore.Testing" Version="$(MicrosoftAspNetCoreTestingPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.CSharp" Version="$(MicrosoftCSharpPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.EntityFrameworkCore.InMemory" Version="$(MicrosoftEntityFrameworkCoreInMemoryPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.EntityFrameworkCore" Version="$(MicrosoftEntityFrameworkCorePackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.ClosedGenericMatcher.Sources" Version="$(MicrosoftExtensionsClosedGenericMatcherSourcesPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.CommandLineUtils.Sources" Version="$(MicrosoftExtensionsCommandLineUtilsSourcesPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.Configuration.CommandLine" Version="$(MicrosoftExtensionsConfigurationCommandLinePackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.Configuration.EnvironmentVariables" Version="$(MicrosoftExtensionsConfigurationEnvironmentVariablesPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.Configuration.Json" Version="$(MicrosoftExtensionsConfigurationJsonPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.Configuration.UserSecrets" Version="$(MicrosoftExtensionsConfigurationUserSecretsPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.Configuration" Version="$(MicrosoftExtensionsConfigurationPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.DependencyInjection.Abstractions" Version="$(MicrosoftExtensionsDependencyInjectionAbstractionsPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.DependencyInjection" Version="$(MicrosoftExtensionsDependencyInjectionPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="$(MicrosoftExtensionsLoggingAbstractionsPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.Logging.Console" Version="$(MicrosoftExtensionsLoggingConsolePackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.Logging.Testing" Version="$(MicrosoftExtensionsLoggingTestingPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.Logging" Version="$(MicrosoftExtensionsLoggingPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.Options" Version="$(MicrosoftExtensionsOptionsPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.Process.Sources" Version="$(MicrosoftExtensionsProcessSourcesPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.WebEncoders.Sources" Version="$(MicrosoftExtensionsWebEncodersSourcesPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Extensions.WebEncoders" Version="$(MicrosoftExtensionsWebEncodersPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.IdentityModel.Clients.ActiveDirectory" Version="$(MicrosoftIdentityModelClientsActiveDirectoryPackageVersion)" />
|
||||
<LatestPackageReference Include="Microsoft.Win32.Registry" Version="$(MicrosoftWin32RegistryPackageVersion)" />
|
||||
<LatestPackageReference Include="System.Data.SqlClient" Version="$(SystemDataSqlClientPackageVersion)" />
|
||||
<LatestPackageReference Include="System.Net.WebSockets.WebSocketProtocol" Version="$(SystemNetWebSocketsWebSocketProtocolPackageVersion)" />
|
||||
<LatestPackageReference Include="System.Security.Cryptography.Cng" Version="$(SystemSecurityCryptographyCngPackageVersion)" />
|
||||
<LatestPackageReference Include="System.Security.Cryptography.Xml" Version="$(SystemSecurityCryptographyXmlPackageVersion)" />
|
||||
<LatestPackageReference Include="System.Security.Principal.Windows" Version="$(SystemSecurityPrincipalWindowsPackageVersion)" />
|
||||
<LatestPackageReference Include="System.Text.Encodings.Web" Version="$(SystemTextEncodingsWebPackageVersion)" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup Label="External dependencies">
|
||||
<LatestPackageReference Include="Microsoft.Azure.KeyVault" Version="2.3.2" />
|
||||
<LatestPackageReference Include="Microsoft.NET.Test.Sdk" Version="15.9.0" />
|
||||
<LatestPackageReference Include="Moq" Version="4.10.0" />
|
||||
<!-- This version is required by MSBuild tasks or Visual Studio extensions. -->
|
||||
<LatestPackageReference Include="Newtonsoft.Json" Version="9.0.1" Condition="'$(UseMSBuildJsonNet)' == 'true'" />
|
||||
<!-- This version should be used by runtime packages -->
|
||||
<LatestPackageReference Include="Newtonsoft.Json" Version="11.0.2" Condition="'$(UseMSBuildJsonNet)' != 'true'" />
|
||||
<LatestPackageReference Include="StackExchange.Redis" Version="2.0.513" />
|
||||
<LatestPackageReference Include="WindowsAzure.Storage" Version="8.1.4" />
|
||||
<LatestPackageReference Include="xunit.abstractions" Version="2.0.1" />
|
||||
<LatestPackageReference Include="xunit.analyzers" Version="0.10.0" />
|
||||
<LatestPackageReference Include="xunit.assert" Version="2.3.1" />
|
||||
<LatestPackageReference Include="xunit.extensibility.core" Version="2.3.1" />
|
||||
<LatestPackageReference Include="xunit.extensibility.execution" Version="2.3.1" />
|
||||
<LatestPackageReference Include="xunit.runner.visualstudio" Version="2.4.0" />
|
||||
<LatestPackageReference Include="xunit" Version="2.4.0" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup Condition=" '$(AddImplicitReferences)' != 'false' AND '$(IsTestProject)' == 'true' AND '$(MSBuildProjectExtension)' == '.csproj' ">
|
||||
<Reference Include="Microsoft.AspNetCore.Testing" />
|
||||
<Reference Include="Microsoft.NET.Test.Sdk" />
|
||||
<Reference Include="Moq" />
|
||||
<Reference Include="xunit" />
|
||||
<Reference Include="xunit.analyzers" />
|
||||
<Reference Include="xunit.runner.visualstudio" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,41 @@
|
|||
{
|
||||
"adx": {
|
||||
"rules": [
|
||||
"AdxVerificationCompositeRule"
|
||||
],
|
||||
"packages": {
|
||||
"dotnet-watch": {
|
||||
"packageTypes": [
|
||||
"DotnetTool"
|
||||
]
|
||||
},
|
||||
"dotnet-sql-cache": {
|
||||
"packageTypes": [
|
||||
"DotnetTool"
|
||||
]
|
||||
},
|
||||
"dotnet-user-secrets": {
|
||||
"packageTypes": [
|
||||
"DotnetTool"
|
||||
]
|
||||
},
|
||||
"dotnet-dev-certs": {
|
||||
"packageTypes": [
|
||||
"DotnetTool"
|
||||
]
|
||||
},
|
||||
"Microsoft.AspNetCore.DeveloperCertificates.XPlat": {
|
||||
"Exclusions": {
|
||||
"DOC_MISSING": {
|
||||
"lib/netcoreapp3.0/Microsoft.AspNetCore.DeveloperCertificates.XPlat.dll": "Docs not required to shipoob package"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"Default": {
|
||||
"rules": [
|
||||
"DefaultCompositeRule"
|
||||
]
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,14 @@
|
|||
<Project>
|
||||
<PropertyGroup>
|
||||
<MSBuildAllProjects>$(MSBuildAllProjects);$(MSBuildThisFileFullPath)</MSBuildAllProjects>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition=" '$(VersionPrefix)' == '2.2.1' ">
|
||||
<PackagesInPatch>
|
||||
Microsoft.AspNetCore.Server.IIS;
|
||||
Microsoft.AspNetCore.Server.IISIntegration;
|
||||
Microsoft.AspNetCore.Server.IntegrationTesting.IIS;
|
||||
</PackagesInPatch>
|
||||
</PropertyGroup>
|
||||
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,23 @@
|
|||
<!-- This file is automatically generated. Run `build.cmd /t:GenerateProjectList` to update. -->
|
||||
<Project>
|
||||
<ItemGroup>
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.JsonPatch" ProjectPath="$(RepositoryRoot)src\Features\JsonPatch\src\Microsoft.AspNetCore.JsonPatch.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.DataProtection.Abstractions" ProjectPath="$(RepositoryRoot)src\DataProtection\Abstractions\src\Microsoft.AspNetCore.DataProtection.Abstractions.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.DataProtection.AzureKeyVault" ProjectPath="$(RepositoryRoot)src\DataProtection\AzureKeyVault\src\Microsoft.AspNetCore.DataProtection.AzureKeyVault.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.DataProtection.AzureStorage" ProjectPath="$(RepositoryRoot)src\DataProtection\AzureStorage\src\Microsoft.AspNetCore.DataProtection.AzureStorage.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.Cryptography.Internal" ProjectPath="$(RepositoryRoot)src\DataProtection\Cryptography.Internal\src\Microsoft.AspNetCore.Cryptography.Internal.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.Cryptography.KeyDerivation" ProjectPath="$(RepositoryRoot)src\DataProtection\Cryptography.KeyDerivation\src\Microsoft.AspNetCore.Cryptography.KeyDerivation.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.DataProtection" ProjectPath="$(RepositoryRoot)src\DataProtection\DataProtection\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.DataProtection.EntityFrameworkCore" ProjectPath="$(RepositoryRoot)src\DataProtection\EntityFrameworkCore\src\Microsoft.AspNetCore.DataProtection.EntityFrameworkCore.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.DataProtection.Extensions" ProjectPath="$(RepositoryRoot)src\DataProtection\Extensions\src\Microsoft.AspNetCore.DataProtection.Extensions.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.DataProtection.StackExchangeRedis" ProjectPath="$(RepositoryRoot)src\DataProtection\StackExchangeRedis\src\Microsoft.AspNetCore.DataProtection.StackExchangeRedis.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.DataProtection.SystemWeb" ProjectPath="$(RepositoryRoot)src\DataProtection\SystemWeb\src\Microsoft.AspNetCore.DataProtection.SystemWeb.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.Html.Abstractions" ProjectPath="$(RepositoryRoot)src\Html\Abstractions\src\Microsoft.AspNetCore.Html.Abstractions.csproj" />
|
||||
<ProjectReferenceProvider Include="dotnet-dev-certs" ProjectPath="$(RepositoryRoot)src\Tools\dotnet-dev-certs\src\dotnet-dev-certs.csproj" />
|
||||
<ProjectReferenceProvider Include="dotnet-sql-cache" ProjectPath="$(RepositoryRoot)src\Tools\dotnet-sql-cache\src\dotnet-sql-cache.csproj" />
|
||||
<ProjectReferenceProvider Include="dotnet-user-secrets" ProjectPath="$(RepositoryRoot)src\Tools\dotnet-user-secrets\src\dotnet-user-secrets.csproj" />
|
||||
<ProjectReferenceProvider Include="dotnet-watch" ProjectPath="$(RepositoryRoot)src\Tools\dotnet-watch\src\dotnet-watch.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.DeveloperCertificates.XPlat" ProjectPath="$(RepositoryRoot)src\Tools\FirstRunCertGenerator\src\Microsoft.AspNetCore.DeveloperCertificates.XPlat.csproj" />
|
||||
<ProjectReferenceProvider Include="Microsoft.AspNetCore.WebSockets" ProjectPath="$(RepositoryRoot)src\Middleware\WebSockets\src\Microsoft.AspNetCore.WebSockets.csproj" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<!--
|
||||
This file is temporary until aspnet/Hosting, Diagnostics, StaticFiles, and HttpAbstractions are merged into this repo.
|
||||
This is required to provide dependencies for samples and tests.
|
||||
-->
|
||||
<Project>
|
||||
<ItemGroup>
|
||||
<LatestPackageReference Include="Microsoft.AspNetCore.Diagnostics" Version="3.0.0-alpha1-10717" />
|
||||
<LatestPackageReference Include="Microsoft.AspNetCore.Server.IISIntegration" Version="3.0.0-alpha1-10717" />
|
||||
<LatestPackageReference Include="Microsoft.AspNetCore.StaticFiles" Version="3.0.0-alpha1-10717" />
|
||||
<LatestPackageReference Include="Microsoft.AspNetCore.Hosting" Version="3.0.0-alpha1-10717" />
|
||||
<LatestPackageReference Include="Microsoft.AspNetCore.Hosting.Abstractions" Version="3.0.0-alpha1-10717" />
|
||||
<LatestPackageReference Include="Microsoft.AspNetCore.Http.Features" Version="3.0.0-alpha1-10717" />
|
||||
<LatestPackageReference Include="Microsoft.AspNetCore.Http.Abstractions" Version="3.0.0-alpha1-10717" />
|
||||
<LatestPackageReference Include="Microsoft.AspNetCore.Http.Extensions" Version="3.0.0-alpha1-10717" />
|
||||
<LatestPackageReference Include="Microsoft.AspNetCore.Http" Version="3.0.0-alpha1-10717" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,14 @@
|
|||
<Project>
|
||||
|
||||
<PropertyGroup>
|
||||
<LangVersion>7.2</LangVersion>
|
||||
|
||||
<!-- Instructs the compiler to use SHA256 instead of SHA1 when adding file hashes to PDBs. -->
|
||||
<ChecksumAlgorithm>SHA256</ChecksumAlgorithm>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Internal.AspNetCore.Sdk" PrivateAssets="All" Version="$(InternalAspNetCoreSdkPackageVersion)" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
<Project>
|
||||
|
||||
<Import Project="Packaging.targets" />
|
||||
<Import Project="ResolveReferences.targets" />
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,30 @@
|
|||
<Project>
|
||||
|
||||
<Target Name="EnsureBaselineIsUpdated"
|
||||
Condition="'$(IsServicingBuild)' == 'true' AND '$(AspNetCoreBaselineVersion)' != '$(PreviousAspNetCoreReleaseVersion)'"
|
||||
BeforeTargets="BeforeBuild">
|
||||
<Error Text="The package baseline ($(AspNetCoreBaselineVersion)) is out of date with the latest release of this repo ($(PreviousAspNetCoreReleaseVersion)).
|
||||
See $(RepositoryRoot)eng\tools\BaselineGenerator\README.md for instructions on updating this baseline." />
|
||||
</Target>
|
||||
|
||||
<!-- Temporary: this target is used to gather version information to pass to submodule builds. This can be removed after we finish merging submodules. -->
|
||||
<Target Name="GetBaselineArtifactInfo"
|
||||
Condition="'$(IsPackableInNonServicingBuild)' == 'true' AND '$(IsSubfolderBuild)' != 'true' "
|
||||
Returns="@(ArtifactInfo)"
|
||||
BeforeTargets="GetArtifactInfo">
|
||||
|
||||
<PropertyGroup>
|
||||
<FullPackageOutputPath>$(PackageOutputPath)$(PackageId).$(PackageVersion).nupkg</FullPackageOutputPath>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ArtifactInfo Include="$(FullPackageOutputPath)">
|
||||
<ArtifactType>NuGetPackage</ArtifactType>
|
||||
<PackageId>$(PackageId)</PackageId>
|
||||
<Version>$(PackageVersion)</Version>
|
||||
<RepositoryRoot>$(RepositoryRoot)</RepositoryRoot>
|
||||
<IsShipped>true</IsShipped>
|
||||
</ArtifactInfo>
|
||||
</ItemGroup>
|
||||
</Target>
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,135 @@
|
|||
<Project>
|
||||
|
||||
<PropertyGroup>
|
||||
<ResolveReferencesDependsOn>
|
||||
ResolveCustomReferences;
|
||||
$(ResolveReferencesDependsOn);
|
||||
</ResolveReferencesDependsOn>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup>
|
||||
<!--
|
||||
Projects should only use the latest package references when:
|
||||
* preparing a new major or minor release (i.e. a non-servicing builds)
|
||||
* when a project is a test or sample project
|
||||
* when a package is releasing a new patch (we like to update external dependencies in patches when possible)
|
||||
-->
|
||||
<UseLatestPackageReferences Condition=" '$(UseLatestPackageReferences)' == '' AND '$(IsServicingBuild)' != 'true' ">true</UseLatestPackageReferences>
|
||||
<UseLatestPackageReferences Condition=" '$(UseLatestPackageReferences)' == '' AND '$(IsImplementationProject)' != 'true' ">true</UseLatestPackageReferences>
|
||||
<UseLatestPackageReferences Condition=" '$(UseLatestPackageReferences)' == '' AND '$(IsImplementationProject)' == 'true' AND ( '$(IsServicingBuild)' != 'true' OR '$(IsPackable)' == 'true' ) ">true</UseLatestPackageReferences>
|
||||
<UseLatestPackageReferences Condition=" '$(UseLatestPackageReferences)' == '' ">false</UseLatestPackageReferences>
|
||||
|
||||
<!--
|
||||
Projects should only use the project references instead of baseline package references when:
|
||||
* preparing a new major or minor release (i.e. a non-servicing builds)
|
||||
* when a project is a test or sample project
|
||||
We don't use project references between components in servicing builds between compontents to preserve the baseline as much as possible.
|
||||
-->
|
||||
<UseProjectReferences Condition=" '$(UseProjectReferences)' == '' AND '$(IsServicingBuild)' != 'true' ">true</UseProjectReferences>
|
||||
<UseProjectReferences Condition=" '$(UseProjectReferences)' == '' AND '$(IsImplementationProject)' != 'true' ">true</UseProjectReferences>
|
||||
<UseProjectReferences Condition=" '$(UseProjectReferences)' == '' ">false</UseProjectReferences>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<_ImplicitPackageReference Include="@(PackageReference->WithMetadataValue('IsImplicitlyDefined', 'true'))" />
|
||||
<_ExplicitPackageReference Include="@(PackageReference)" Exclude="@(_ImplicitPackageReference)" />
|
||||
<_ExplicitPackageReference Remove="Internal.AspNetCore.Sdk" />
|
||||
|
||||
<UnusedProjectReferenceProvider Include="@(ProjectReferenceProvider)" Exclude="@(Reference)" />
|
||||
|
||||
<!-- Order matters. Projects should be used when possible instead of packages. -->
|
||||
<_ProjectReferenceByAssemblyName Condition="'$(UseProjectReferences)' == 'true'"
|
||||
Include="@(ProjectReferenceProvider)"
|
||||
Exclude="@(UnusedProjectReferenceProvider)" />
|
||||
|
||||
<ProjectReference Include="@(_ProjectReferenceByAssemblyName->'%(ProjectPath)')" />
|
||||
|
||||
<Reference Remove="@(_ProjectReferenceByAssemblyName)" />
|
||||
</ItemGroup>
|
||||
|
||||
<Target Name="ResolveCustomReferences" BeforeTargets="CollectPackageReferences;ResolveAssemblyReferencesDesignTime;ResolveAssemblyReferences" Condition=" '$(TargetFramework)' != '' ">
|
||||
<ItemGroup>
|
||||
<UnusedBaselinePackageReference Include="@(BaselinePackageReference)" Exclude="@(Reference);@(_ProjectReferenceByAssemblyName)" />
|
||||
|
||||
<!--
|
||||
MSBuild does not provide a way to join on matching identities in a Condition,
|
||||
but you can do a cartesian product of two item groups and filter out mismatched id's in a second pass.
|
||||
-->
|
||||
<_LatestPackageReferenceWithVersion Include="@(Reference)" Condition=" '$(UseLatestPackageReferences)' == 'true' ">
|
||||
<Id>%(LatestPackageReference.Identity)</Id>
|
||||
<Version>%(LatestPackageReference.Version)</Version>
|
||||
</_LatestPackageReferenceWithVersion>
|
||||
<_LatestPackageReferenceWithVersion Remove="@(_LatestPackageReferenceWithVersion)" Condition="'%(Id)' != '%(Identity)' " />
|
||||
|
||||
<!-- Remove reference items that have been resolved to a LatestPackageReference item. -->
|
||||
<Reference Remove="@(_LatestPackageReferenceWithVersion)" />
|
||||
<PackageReference Include="@(_LatestPackageReferenceWithVersion)" IsImplicitlyDefined="true" />
|
||||
|
||||
<!-- Resolve references from BaselinePackageReference for servicing builds. -->
|
||||
<_BaselinePackageReferenceWithVersion Include="@(Reference)" Condition=" '$(IsServicingBuild)' == 'true' OR '$(UseLatestPackageReferences)' != 'true' ">
|
||||
<Id>%(BaselinePackageReference.Identity)</Id>
|
||||
<Version>%(BaselinePackageReference.Version)</Version>
|
||||
</_BaselinePackageReferenceWithVersion>
|
||||
|
||||
<_BaselinePackageReferenceWithVersion Remove="@(_BaselinePackageReferenceWithVersion)" Condition="'%(Id)' != '%(Identity)' " />
|
||||
|
||||
<!-- Remove reference items that have been resolved to a BaselinePackageReference item. -->
|
||||
<PackageReference Include="@(_BaselinePackageReferenceWithVersion)" IsImplicitlyDefined="true" />
|
||||
<Reference Remove="@(_BaselinePackageReferenceWithVersion)" />
|
||||
|
||||
<!-- For PrivateAssets=All references, like .Sources packages, fallback to LatestPackageReferences. -->
|
||||
<_PrivatePackageReferenceWithVersion Include="@(Reference->WithMetadataValue('PrivateAssets', 'All'))">
|
||||
<Id>%(LatestPackageReference.Identity)</Id>
|
||||
<Version>%(LatestPackageReference.Version)</Version>
|
||||
</_PrivatePackageReferenceWithVersion>
|
||||
|
||||
<_PrivatePackageReferenceWithVersion Remove="@(_PrivatePackageReferenceWithVersion)" Condition="'%(Id)' != '%(Identity)' " />
|
||||
|
||||
<!-- Remove reference items that have been resolved to a LatestPackageReference item. -->
|
||||
<PackageReference Include="@(_PrivatePackageReferenceWithVersion)" IsImplicitlyDefined="true" />
|
||||
<Reference Remove="@(_PrivatePackageReferenceWithVersion)" />
|
||||
|
||||
<!-- Free up memory for unnecessary items -->
|
||||
<_LatestPackageReferenceWithVersion Remove="@(_LatestPackageReferenceWithVersion)" />
|
||||
<_BaselinePackageReferenceWithVersion Remove="@(_BaselinePackageReferenceWithVersion)" />
|
||||
<_PrivatePackageReferenceWithVersion Remove="@(_PrivatePackageReferenceWithVersion)" />
|
||||
<_ImplicitPackageReference Remove="@(_ImplicitPackageReference)" />
|
||||
</ItemGroup>
|
||||
<!--
|
||||
<Error Condition="@(_ExplicitPackageReference->Count()) != 0"
|
||||
Text="PackageReference items are not allowed. Use <Reference> instead. " /> -->
|
||||
|
||||
<ItemGroup>
|
||||
<_ExplicitPackageReference Remove="@(_ExplicitPackageReference)" />
|
||||
</ItemGroup>
|
||||
|
||||
<Warning Condition="@(UnusedBaselinePackageReference->Count()) != 0"
|
||||
Text="Package references changed since the last release. This could be a breaking change. References removed:%0A - @(UnusedBaselinePackageReference, '%0A -')" />
|
||||
|
||||
<Error Condition="'$(TargetFrameworkIdentifier)' != '.NETFramework' AND '%(Reference.Identity)' != '' AND ! Exists('%(Reference.Identity)')"
|
||||
Code="MSB3245"
|
||||
Text="Could not resolve this reference. Could not locate the package or project for "%(Reference.Identity)"" />
|
||||
</Target>
|
||||
|
||||
<Target Name="GetReferencesProvided" Returns="@(ProvidesReference)">
|
||||
<ItemGroup>
|
||||
<_TargetFramework Remove="@(_TargetFramework)" />
|
||||
<_TargetFramework Include="$(TargetFramework)" Condition="'$(TargetFramework)' != '' "/>
|
||||
<_TargetFramework Include="$(TargetFrameworks)" Condition="'$(TargetFramework)' == '' "/>
|
||||
</ItemGroup>
|
||||
|
||||
<MSBuild Projects="$(MSBuildProjectFullPath)"
|
||||
Targets="_GetReferencesProvided"
|
||||
Properties="TargetFramework=%(_TargetFramework.Identity)">
|
||||
<Output TaskParameter="TargetOutputs" ItemName="ProvidesReference" />
|
||||
</MSBuild>
|
||||
</Target>
|
||||
|
||||
<Target Name="_GetReferencesProvided" Returns="@(ProvidesReference)">
|
||||
<ItemGroup Condition=" '$(IsImplementationProject)' == 'true' OR '$(IsProjectReferenceProvider)' == 'true' ">
|
||||
<ProvidesReference Include="$(AssemblyName)">
|
||||
<ProjectFileRelativePath>$([MSBuild]::MakeRelative($(RepositoryRoot), $(MSBuildProjectFullPath)))</ProjectFileRelativePath>
|
||||
</ProvidesReference>
|
||||
</ItemGroup>
|
||||
</Target>
|
||||
</Project>
|
||||
|
|
@ -332,4 +332,32 @@ This targets file should only be imported by .shfxproj files.
|
|||
</Target>
|
||||
|
||||
<Target Name="CreateManifestResourceNames" />
|
||||
|
||||
<Target Name="GetArtifactInfo" Returns="@(ArtifactInfo)">
|
||||
<PropertyGroup>
|
||||
<FullPackageOutputPath>$(PackageOutputPath)$(PackageId).$(PackageVersion).nupkg</FullPackageOutputPath>
|
||||
<SymbolsPackageOutputPath>$(PackageOutputPath)$(PackageId).$(PackageVersion).symbols.nupkg</SymbolsPackageOutputPath>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ArtifactInfo Include="$(FullPackageOutputPath)">
|
||||
<ArtifactType>NuGetPackage</ArtifactType>
|
||||
<PackageId>$(PackageId)</PackageId>
|
||||
<Version>$(PackageVersion)</Version>
|
||||
<RepositoryRoot>$(RepositoryRoot)</RepositoryRoot>
|
||||
<Certificate>$(PackageSigningCertName)</Certificate>
|
||||
<ShouldBeSigned>true</ShouldBeSigned>
|
||||
<IsContainer>true</IsContainer>
|
||||
</ArtifactInfo>
|
||||
<ArtifactInfo Include="$(SymbolsPackageOutputPath)" Condition="'$(IncludeSymbols)' != 'false'">
|
||||
<ArtifactType>NuGetSymbolsPackage</ArtifactType>
|
||||
<PackageId>$(PackageId)</PackageId>
|
||||
<Version>$(PackageVersion)</Version>
|
||||
<RepositoryRoot>$(RepositoryRoot)</RepositoryRoot>
|
||||
<Certificate>$(PackageSigningCertName)</Certificate>
|
||||
<ShouldBeSigned>true</ShouldBeSigned>
|
||||
<IsContainer>true</IsContainer>
|
||||
</ArtifactInfo>
|
||||
</ItemGroup>
|
||||
</Target>
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -0,0 +1,15 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<OutputType>Exe</OutputType>
|
||||
<TargetFramework>netcoreapp2.1</TargetFramework>
|
||||
<StartArguments>-o "$(MSBuildThisFileDirectory)../../Baseline.props"</StartArguments>
|
||||
<StartWorkingDirectory>$(MSBuildProjectDirectory)</StartWorkingDirectory>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="NuGet.Packaging" Version="4.8.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.CommandLineUtils" Version="1.1.0" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,138 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Net.Http;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using System.Xml;
|
||||
using System.Xml.Linq;
|
||||
using Microsoft.Extensions.CommandLineUtils;
|
||||
using NuGet.Packaging;
|
||||
using NuGet.Packaging.Core;
|
||||
|
||||
namespace PackageBaselineGenerator
|
||||
{
|
||||
/// <summary>
|
||||
/// This generates Baseline.props with information about the last RTM release.
|
||||
/// </summary>
|
||||
class Program : CommandLineApplication
|
||||
{
|
||||
static void Main(string[] args)
|
||||
{
|
||||
new Program().Execute(args);
|
||||
}
|
||||
|
||||
private readonly CommandOption _source;
|
||||
private readonly CommandOption _output;
|
||||
private readonly CommandOption _feedv3;
|
||||
|
||||
public Program()
|
||||
{
|
||||
_source = Option("-s|--source <SOURCE>", "The NuGet v2 source of the package to fetch", CommandOptionType.SingleValue);
|
||||
_output = Option("-o|--output <OUT>", "The generated file output path", CommandOptionType.SingleValue);
|
||||
_feedv3 = Option("--v3", "Sources is nuget v3", CommandOptionType.NoValue);
|
||||
|
||||
Invoke = () => Run().GetAwaiter().GetResult();
|
||||
}
|
||||
|
||||
private async Task<int> Run()
|
||||
{
|
||||
var source = _source.HasValue()
|
||||
? _source.Value()
|
||||
: "https://www.nuget.org/api/v2/package";
|
||||
|
||||
var packageCache = Environment.GetEnvironmentVariable("NUGET_PACKAGES") != null
|
||||
? Environment.GetEnvironmentVariable("NUGET_PACKAGES")
|
||||
: Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.UserProfile), ".nuget", "packages");
|
||||
|
||||
var tempDir = Path.Combine(Directory.GetCurrentDirectory(), "obj", "tmp");
|
||||
Directory.CreateDirectory(tempDir);
|
||||
|
||||
var input = XDocument.Load(Path.Combine(Directory.GetCurrentDirectory(), "baseline.xml"));
|
||||
|
||||
var output = _output.HasValue()
|
||||
? _output.Value()
|
||||
: Path.Combine(Directory.GetCurrentDirectory(), "Baseline.props");
|
||||
|
||||
var baselineVersion = input.Root.Attribute("Version").Value;
|
||||
|
||||
var doc = new XDocument(
|
||||
new XComment(" Auto generated. Do not edit manually, use eng/tools/BaselineGenerator/ to recreate. "),
|
||||
new XElement("Project",
|
||||
new XElement("PropertyGroup",
|
||||
new XElement("MSBuildAllProjects", "$(MSBuildAllProjects);$(MSBuildThisFileFullPath)"),
|
||||
new XElement("AspNetCoreBaselineVersion", baselineVersion))));
|
||||
|
||||
var client = new HttpClient();
|
||||
|
||||
foreach (var pkg in input.Root.Descendants("Package"))
|
||||
{
|
||||
var id = pkg.Attribute("Id").Value;
|
||||
var version = pkg.Attribute("Version").Value;
|
||||
var packageFileName = $"{id}.{version}.nupkg";
|
||||
var nupkgPath = Path.Combine(packageCache, id.ToLowerInvariant(), version, packageFileName);
|
||||
if (!File.Exists(nupkgPath))
|
||||
{
|
||||
nupkgPath = Path.Combine(tempDir, packageFileName);
|
||||
}
|
||||
|
||||
if (!File.Exists(nupkgPath))
|
||||
{
|
||||
var url = _feedv3.HasValue()
|
||||
? $"{source}/{id.ToLowerInvariant()}/{version}/{id.ToLowerInvariant()}.{version}.nupkg"
|
||||
: $"{source}/{id}/{version}";
|
||||
Console.WriteLine($"Downloading {url}");
|
||||
|
||||
var response = await client.GetStreamAsync(url);
|
||||
|
||||
using (var file = File.Create(nupkgPath))
|
||||
{
|
||||
await response.CopyToAsync(file);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
using (var reader = new PackageArchiveReader(nupkgPath))
|
||||
{
|
||||
var first = true;
|
||||
foreach (var group in reader.NuspecReader.GetDependencyGroups())
|
||||
{
|
||||
if (first)
|
||||
{
|
||||
first = false;
|
||||
doc.Root.Add(new XComment($" Package: {id}"));
|
||||
|
||||
var propertyGroup = new XElement("PropertyGroup",
|
||||
new XAttribute("Condition", $" '$(PackageId)' == '{id}' "),
|
||||
new XElement("BaselinePackageVersion", version));
|
||||
doc.Root.Add(propertyGroup);
|
||||
}
|
||||
|
||||
var itemGroup = new XElement("ItemGroup", new XAttribute("Condition", $" '$(PackageId)' == '{id}' AND '$(TargetFramework)' == '{group.TargetFramework.GetShortFolderName()}' "));
|
||||
doc.Root.Add(itemGroup);
|
||||
|
||||
foreach (var dependency in group.Packages)
|
||||
{
|
||||
itemGroup.Add(new XElement("BaselinePackageReference", new XAttribute("Include", dependency.Id), new XAttribute("Version", dependency.VersionRange.ToString())));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var settings = new XmlWriterSettings
|
||||
{
|
||||
OmitXmlDeclaration = true,
|
||||
Encoding = Encoding.UTF8,
|
||||
Indent = true,
|
||||
};
|
||||
using (var writer = XmlWriter.Create(output, settings))
|
||||
{
|
||||
doc.Save(writer);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,10 @@
|
|||
BaselineGenerator
|
||||
=================
|
||||
|
||||
This tool is used to generate an MSBuild file which sets the "baseline" against which servicing updates are built.
|
||||
|
||||
## Usage
|
||||
|
||||
1. Add to the [baseline.xml](./baseline.xml) a list of package ID's and their latest released versions. The source of this information can typically
|
||||
be found in the build.xml file generated during ProdCon builds. See https://github.com/dotnet/versions/blob/master/build-info/dotnet/product/cli/release/2.1.6/build.xml for example.
|
||||
2. Run `dotnet run` on this project.
|
||||
|
|
@ -0,0 +1,19 @@
|
|||
<Baseline Version="2.2.0">
|
||||
<Package Id="dotnet-dev-certs" Version="2.2.0" />
|
||||
<Package Id="dotnet-sql-cache" Version="2.2.0" />
|
||||
<Package Id="dotnet-user-secrets" Version="2.2.0" />
|
||||
<Package Id="dotnet-watch" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.Cryptography.Internal" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.Cryptography.KeyDerivation" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.DataProtection" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.DataProtection.Abstractions" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.DataProtection.AzureKeyVault" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.DataProtection.AzureStorage" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.DataProtection.EntityFrameworkCore" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.DataProtection.Extensions" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.DataProtection.StackExchangeRedis" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.DataProtection.SystemWeb" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.Html.Abstractions" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.JsonPatch" Version="2.2.0" />
|
||||
<Package Id="Microsoft.AspNetCore.WebSockets" Version="2.2.0" />
|
||||
</Baseline>
|
||||
|
|
@ -0,0 +1,3 @@
|
|||
<Project>
|
||||
<Import Project="..\..\build\sources.props" />
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,2 @@
|
|||
<Project>
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,34 @@
|
|||
|
||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||
# Visual Studio 15
|
||||
VisualStudioVersion = 15.0.26124.0
|
||||
MinimumVisualStudioVersion = 15.0.26124.0
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "BaselineGenerator", "BaselineGenerator\BaselineGenerator.csproj", "{CF76A947-3A72-4824-87E6-BF029D84218B}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Any CPU = Debug|Any CPU
|
||||
Debug|x64 = Debug|x64
|
||||
Debug|x86 = Debug|x86
|
||||
Release|Any CPU = Release|Any CPU
|
||||
Release|x64 = Release|x64
|
||||
Release|x86 = Release|x86
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{CF76A947-3A72-4824-87E6-BF029D84218B}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{CF76A947-3A72-4824-87E6-BF029D84218B}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{CF76A947-3A72-4824-87E6-BF029D84218B}.Debug|x64.ActiveCfg = Debug|Any CPU
|
||||
{CF76A947-3A72-4824-87E6-BF029D84218B}.Debug|x64.Build.0 = Debug|Any CPU
|
||||
{CF76A947-3A72-4824-87E6-BF029D84218B}.Debug|x86.ActiveCfg = Debug|Any CPU
|
||||
{CF76A947-3A72-4824-87E6-BF029D84218B}.Debug|x86.Build.0 = Debug|Any CPU
|
||||
{CF76A947-3A72-4824-87E6-BF029D84218B}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{CF76A947-3A72-4824-87E6-BF029D84218B}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{CF76A947-3A72-4824-87E6-BF029D84218B}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{CF76A947-3A72-4824-87E6-BF029D84218B}.Release|x64.Build.0 = Release|Any CPU
|
||||
{CF76A947-3A72-4824-87E6-BF029D84218B}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
{CF76A947-3A72-4824-87E6-BF029D84218B}.Release|x86.Build.0 = Release|Any CPU
|
||||
EndGlobalSection
|
||||
EndGlobal
|
||||
|
|
@ -3,6 +3,6 @@
|
|||
"version": "3.0.100-preview-009750"
|
||||
},
|
||||
"msbuild-sdks": {
|
||||
"Internal.AspNetCore.Sdk": "3.0.0-alpha1-20181114.4"
|
||||
"Internal.AspNetCore.Sdk": "3.0.0-build-20181114.5"
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,2 +1,2 @@
|
|||
version:3.0.0-alpha1-20181114.4
|
||||
commithash:576bd9858150e9aec1c3527dc68ebe9f69d55b5a
|
||||
version:3.0.0-build-20181114.5
|
||||
commithash:880e9a204d4ee4a18dfd83c9fb05a192a28bca60
|
||||
|
|
|
|||
|
|
@ -1 +0,0 @@
|
|||
Subproject commit a24b4ee4598b425d9e8b2f041be508c32eb41cf5
|
||||
|
|
@ -1 +0,0 @@
|
|||
Subproject commit 45b7e2ddb796f0cb909d8f04bc4b5a5cf13b5e46
|
||||
|
|
@ -1 +0,0 @@
|
|||
Subproject commit bf9fd0d10667e605d1df45f89e198be7f3bd1138
|
||||
|
|
@ -56,7 +56,6 @@ foreach ($package in $remoteDeps.SelectNodes('//Package')) {
|
|||
|
||||
if (-not $NoCommit) {
|
||||
$currentBranch = Invoke-Block { & git rev-parse --abbrev-ref HEAD }
|
||||
|
||||
$destinationBranch = "dotnetbot/UpdateDeps"
|
||||
Invoke-Block { & git checkout -tb $destinationBranch "origin/$GithubUpstreamBranch" }
|
||||
}
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ Microsoft.AspNetCore.DataProtection.IDataProtector</Description>
|
|||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.WebEncoders.Sources" PrivateAssets="All" Version="$(MicrosoftExtensionsWebEncodersSourcesPackageVersion)" />
|
||||
<Reference Include="Microsoft.Extensions.WebEncoders.Sources" PrivateAssets="All" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -5,8 +5,8 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\Cryptography.Internal\src\Microsoft.AspNetCore.Cryptography.Internal.csproj" />
|
||||
<ProjectReference Include="..\src\Microsoft.AspNetCore.DataProtection.Abstractions.csproj" />
|
||||
<Reference Include="Microsoft.AspNetCore.Cryptography.Internal" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.Abstractions" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -9,12 +9,9 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\DataProtection\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.IdentityModel.Clients.ActiveDirectory" Version="$(MicrosoftIdentityModelClientsActiveDirectoryPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Azure.KeyVault" Version="$(MicrosoftAzureKeyVaultPackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection" />
|
||||
<Reference Include="Microsoft.Azure.KeyVault" />
|
||||
<Reference Include="Microsoft.IdentityModel.Clients.ActiveDirectory" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -6,12 +6,9 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\DataProtection\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
<ProjectReference Include="..\src\Microsoft.AspNetCore.DataProtection.AzureKeyVault.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="$(MicrosoftExtensionsDependencyInjectionPackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.AzureKeyVault" />
|
||||
<Reference Include="Microsoft.Extensions.DependencyInjection" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -9,11 +9,8 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\DataProtection\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="WindowsAzure.Storage" Version="$(WindowsAzureStoragePackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection" />
|
||||
<Reference Include="WindowsAzure.Storage" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -6,12 +6,9 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\DataProtection\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
<ProjectReference Include="..\src\Microsoft.AspNetCore.DataProtection.AzureStorage.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="$(MicrosoftExtensionsDependencyInjectionPackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.AzureStorage" />
|
||||
<Reference Include="Microsoft.Extensions.DependencyInjection" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@
|
|||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\src\Microsoft.AspNetCore.Cryptography.Internal.csproj" />
|
||||
<Reference Include="Microsoft.AspNetCore.Cryptography.Internal" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\Cryptography.Internal\src\Microsoft.AspNetCore.Cryptography.Internal.csproj" />
|
||||
<Reference Include="Microsoft.AspNetCore.Cryptography.Internal" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -10,8 +10,8 @@
|
|||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\Cryptography.Internal\src\Microsoft.AspNetCore.Cryptography.Internal.csproj" />
|
||||
<ProjectReference Include="..\src\Microsoft.AspNetCore.Cryptography.KeyDerivation.csproj" />
|
||||
<Reference Include="Microsoft.AspNetCore.Cryptography.Internal" />
|
||||
<Reference Include="Microsoft.AspNetCore.Cryptography.KeyDerivation" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -14,18 +14,15 @@
|
|||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\Cryptography.Internal\src\Microsoft.AspNetCore.Cryptography.Internal.csproj" />
|
||||
<ProjectReference Include="..\..\Abstractions\src\Microsoft.AspNetCore.DataProtection.Abstractions.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.AspNetCore.Hosting.Abstractions" Version="$(MicrosoftAspNetCoreHostingAbstractionsPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyInjection.Abstractions" Version="$(MicrosoftExtensionsDependencyInjectionAbstractionsPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.Logging.Abstractions" Version="$(MicrosoftExtensionsLoggingAbstractionsPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.Options" Version="$(MicrosoftExtensionsOptionsPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Win32.Registry" Version="$(MicrosoftWin32RegistryPackageVersion)" />
|
||||
<PackageReference Include="System.Security.Cryptography.Xml" Version="$(SystemSecurityCryptographyXmlPackageVersion)" />
|
||||
<PackageReference Include="System.Security.Principal.Windows" Version="$(SystemSecurityPrincipalWindowsPackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.Cryptography.Internal" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.Abstractions" />
|
||||
<Reference Include="Microsoft.AspNetCore.Hosting.Abstractions" />
|
||||
<Reference Include="Microsoft.Extensions.DependencyInjection.Abstractions" />
|
||||
<Reference Include="Microsoft.Extensions.Logging.Abstractions" />
|
||||
<Reference Include="Microsoft.Extensions.Options" />
|
||||
<Reference Include="Microsoft.Win32.Registry" />
|
||||
<Reference Include="System.Security.Cryptography.Xml" />
|
||||
<Reference Include="System.Security.Principal.Windows" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -11,12 +11,12 @@
|
|||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
</ItemGroup>
|
||||
<!-- TODO replace all PackageReference with ProjectReference once aspnet/Hosting has merged to this repo -->
|
||||
<PackageReference Include="Microsoft.AspNetCore.Hosting" Version="2.1.1" />
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.AspNetCore.Hosting" Version="$(MicrosoftAspNetCoreHostingPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="$(MicrosoftExtensionsDependencyInjectionPackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.Cryptography.Internal" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection" />
|
||||
<Reference Include="Microsoft.Extensions.DependencyInjection" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -1,24 +0,0 @@
|
|||
<Project>
|
||||
|
||||
<PropertyGroup>
|
||||
<!-- Temporary until we can replace PackageRef with ProjectRef -->
|
||||
<SubFolderRepoBuild>true</SubFolderRepoBuild>
|
||||
</PropertyGroup>
|
||||
|
||||
<Import Project="$([MSBuild]::GetDirectoryNameOfFileAbove($(MSBuildThisFileDirectory)..\, Directory.Build.props))\Directory.Build.props" />
|
||||
|
||||
<Import Project="version.props" />
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Internal.AspNetCore.Sdk" PrivateAssets="All" Version="$(InternalAspNetCoreSdkPackageVersion)" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup Condition=" '$(IsTestProject)' == 'true' ">
|
||||
<PackageReference Include="Microsoft.AspNetCore.Testing" Version="$(MicrosoftAspNetCoreTestingPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="$(MicrosoftNETTestSdkPackageVersion)" />
|
||||
<PackageReference Include="Moq" Version="$(MoqPackageVersion)" />
|
||||
<PackageReference Include="xunit" Version="$(XunitPackageVersion)" />
|
||||
<PackageReference Include="xunit.runner.visualstudio" Version="$(XunitRunnerVisualStudioPackageVersion)" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
@ -9,15 +9,8 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\DataProtection\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.EntityFrameworkCore" Version="$(MicrosoftEntityFrameworkCorePackageVersion)" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<Folder Include="Properties\" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection" />
|
||||
<Reference Include="Microsoft.EntityFrameworkCore" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -5,11 +5,8 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.EntityFrameworkCore.InMemory" Version="$(MicrosoftEntityFrameworkCoreInMemoryPackageVersion)" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\src\Microsoft.AspNetCore.DataProtection.EntityFrameworkCore.csproj" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.EntityFrameworkCore" />
|
||||
<Reference Include="Microsoft.EntityFrameworkCore.InMemory" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -12,11 +12,8 @@
|
|||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\DataProtection\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="$(MicrosoftExtensionsDependencyInjectionPackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection" />
|
||||
<Reference Include="Microsoft.Extensions.DependencyInjection" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -10,8 +10,9 @@
|
|||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\Abstractions\src\Microsoft.AspNetCore.DataProtection.Abstractions.csproj" />
|
||||
<ProjectReference Include="..\src\Microsoft.AspNetCore.DataProtection.Extensions.csproj" />
|
||||
<Reference Include="Microsoft.AspNetCore.Cryptography.Internal" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.Abstractions" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.Extensions" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -9,11 +9,8 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\DataProtection\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="StackExchange.Redis" Version="$(StackExchangeRedisPackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection" />
|
||||
<Reference Include="StackExchange.Redis" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -11,14 +11,11 @@
|
|||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\Abstractions\src\Microsoft.AspNetCore.DataProtection.Abstractions.csproj" />
|
||||
<ProjectReference Include="..\src\Microsoft.AspNetCore.DataProtection.StackExchangeRedis.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="$(MicrosoftExtensionsConfigurationJsonPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration.EnvironmentVariables" Version="$(MicrosoftExtensionsConfigurationEnvironmentVariablesPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="$(MicrosoftExtensionsDependencyInjectionPackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.Abstractions" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.StackExchangeRedis" />
|
||||
<Reference Include="Microsoft.Extensions.Configuration.Json" />
|
||||
<Reference Include="Microsoft.Extensions.Configuration.EnvironmentVariables" />
|
||||
<Reference Include="Microsoft.Extensions.DependencyInjection" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -13,11 +13,8 @@
|
|||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\DataProtection\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="$(MicrosoftExtensionsDependencyInjectionPackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection" />
|
||||
<Reference Include="Microsoft.Extensions.DependencyInjection" />
|
||||
<Reference Include="System.Configuration" />
|
||||
<Reference Include="System.Web" />
|
||||
</ItemGroup>
|
||||
|
|
|
|||
|
|
@ -1,12 +0,0 @@
|
|||
<Project>
|
||||
<Import Project="..\..\..\build\dependencies.props" />
|
||||
<Import Project="..\..\..\build\runtimes.props" />
|
||||
<PropertyGroup>
|
||||
<!-- TODO: temporary while we reorganize source code and refactor dependency management -->
|
||||
<DisablePackageReferenceRestrictions>true</DisablePackageReferenceRestrictions>
|
||||
<OverridePackageOutputPath>false</OverridePackageOutputPath>
|
||||
<BuildSolutions>false</BuildSolutions>
|
||||
<DataProtectionRoot>$([MSBuild]::NormalizeDirectory('$(MSBuildThisFileDirectory)..\'))</DataProtectionRoot>
|
||||
<Projects>$(DataProtectionRoot)**\*.csproj</Projects>
|
||||
</PropertyGroup>
|
||||
</Project>
|
||||
|
|
@ -6,14 +6,11 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\DataProtection\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
<ProjectReference Include="..\..\AzureStorage\src\Microsoft.AspNetCore.DataProtection.AzureStorage.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="$(MicrosoftExtensionsDependencyInjectionPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.Logging" Version="$(MicrosoftExtensionsLoggingPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.Logging.Console" Version="$(MicrosoftExtensionsLoggingConsolePackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.AzureStorage" />
|
||||
<Reference Include="Microsoft.Extensions.DependencyInjection" />
|
||||
<Reference Include="Microsoft.Extensions.Logging" />
|
||||
<Reference Include="Microsoft.Extensions.Logging.Console" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -6,15 +6,12 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\AzureKeyVault\src\Microsoft.AspNetCore.DataProtection.AzureKeyVault.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration" Version="$(MicrosoftExtensionsConfigurationPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="$(MicrosoftExtensionsConfigurationJsonPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="$(MicrosoftExtensionsDependencyInjectionPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.Logging" Version="$(MicrosoftExtensionsLoggingPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.Logging.Console" Version="$(MicrosoftExtensionsLoggingConsolePackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.AzureKeyVault" />
|
||||
<Reference Include="Microsoft.Extensions.Configuration" />
|
||||
<Reference Include="Microsoft.Extensions.Configuration.Json" />
|
||||
<Reference Include="Microsoft.Extensions.DependencyInjection" />
|
||||
<Reference Include="Microsoft.Extensions.Logging" />
|
||||
<Reference Include="Microsoft.Extensions.Logging.Console" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -6,13 +6,10 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\DataProtection\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
<ProjectReference Include="..\..\Extensions\src\Microsoft.AspNetCore.DataProtection.Extensions.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.Logging" Version="$(MicrosoftExtensionsLoggingPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.Logging.Console" Version="$(MicrosoftExtensionsLoggingConsolePackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.Extensions" />
|
||||
<Reference Include="Microsoft.Extensions.Logging" />
|
||||
<Reference Include="Microsoft.Extensions.Logging.Console" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -6,8 +6,8 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\DataProtection\src\Microsoft.AspNetCore.DataProtection.csproj" />
|
||||
<ProjectReference Include="..\..\Extensions\src\Microsoft.AspNetCore.DataProtection.Extensions.csproj" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.Extensions" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\Extensions\src\Microsoft.AspNetCore.DataProtection.Extensions.csproj" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.Extensions" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -6,13 +6,10 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\StackExchangeRedis\src\Microsoft.AspNetCore.DataProtection.StackExchangeRedis.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.DependencyInjection" Version="$(MicrosoftExtensionsDependencyInjectionPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.Logging" Version="$(MicrosoftExtensionsLoggingPackageVersion)" />
|
||||
<PackageReference Include="Microsoft.Extensions.Logging.Console" Version="$(MicrosoftExtensionsLoggingConsolePackageVersion)" />
|
||||
<Reference Include="Microsoft.AspNetCore.DataProtection.StackExchangeRedis" />
|
||||
<Reference Include="Microsoft.Extensions.DependencyInjection" />
|
||||
<Reference Include="Microsoft.Extensions.Logging" />
|
||||
<Reference Include="Microsoft.Extensions.Logging.Console" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
|
|||
|
|
@ -1,10 +0,0 @@
|
|||
<Project>
|
||||
<PropertyGroup>
|
||||
<VersionPrefix>3.0.0</VersionPrefix>
|
||||
<VersionSuffix>alpha1</VersionSuffix>
|
||||
<PackageVersion Condition="'$(IsFinalBuild)' == 'true' AND '$(VersionSuffix)' == 'rtm' ">$(VersionPrefix)</PackageVersion>
|
||||
<PackageVersion Condition="'$(IsFinalBuild)' == 'true' AND '$(VersionSuffix)' != 'rtm' ">$(VersionPrefix)-$(VersionSuffix)-final</PackageVersion>
|
||||
<BuildNumber Condition="'$(BuildNumber)' == ''">t000</BuildNumber>
|
||||
<VersionSuffix Condition="'$(VersionSuffix)' != '' And '$(BuildNumber)' != ''">$(VersionSuffix)-$(BuildNumber)</VersionSuffix>
|
||||
</PropertyGroup>
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,49 @@
|
|||
using Microsoft.AspNetCore.JsonPatch.Internal;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Adapters
|
||||
{
|
||||
/// <summary>
|
||||
/// The default AdapterFactory to be used for resolving <see cref="IAdapter"/>.
|
||||
/// </summary>
|
||||
public class AdapterFactory : IAdapterFactory
|
||||
{
|
||||
/// <inheritdoc />
|
||||
public virtual IAdapter Create(object target, IContractResolver contractResolver)
|
||||
{
|
||||
if (target == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(target));
|
||||
}
|
||||
|
||||
if (contractResolver == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(contractResolver));
|
||||
}
|
||||
|
||||
var jsonContract = contractResolver.ResolveContract(target.GetType());
|
||||
|
||||
if (target is IList)
|
||||
{
|
||||
return new ListAdapter();
|
||||
}
|
||||
else if (jsonContract is JsonDictionaryContract jsonDictionaryContract)
|
||||
{
|
||||
var type = typeof(DictionaryAdapter<,>).MakeGenericType(jsonDictionaryContract.DictionaryKeyType, jsonDictionaryContract.DictionaryValueType);
|
||||
return (IAdapter)Activator.CreateInstance(type);
|
||||
}
|
||||
else if (jsonContract is JsonDynamicContract)
|
||||
{
|
||||
return new DynamicObjectAdapter();
|
||||
}
|
||||
else
|
||||
{
|
||||
return new PocoAdapter();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,22 @@
|
|||
using Microsoft.AspNetCore.JsonPatch.Internal;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Adapters
|
||||
{
|
||||
/// <summary>
|
||||
/// Defines the operations used for loading an <see cref="IAdapter"/> based on the current object and ContractResolver.
|
||||
/// </summary>
|
||||
public interface IAdapterFactory
|
||||
{
|
||||
/// <summary>
|
||||
/// Creates an <see cref="IAdapter"/> for the current object
|
||||
/// </summary>
|
||||
/// <param name="target">The target object</param>
|
||||
/// <param name="contractResolver">The current contract resolver</param>
|
||||
/// <returns>The needed <see cref="IAdapter"/></returns>
|
||||
IAdapter Create(object target, IContractResolver contractResolver);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,112 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using Microsoft.AspNetCore.JsonPatch.Operations;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Adapters
|
||||
{
|
||||
/// <summary>
|
||||
/// Defines the operations that can be performed on a JSON patch document.
|
||||
/// </summary>
|
||||
public interface IObjectAdapter
|
||||
{
|
||||
/// <summary>
|
||||
/// Using the "add" operation a new value is inserted into the root of the target
|
||||
/// document, into the target array at the specified valid index, or to a target object at
|
||||
/// the specified location.
|
||||
///
|
||||
/// When adding to arrays, the specified index MUST NOT be greater than the number of elements in the array.
|
||||
/// To append the value to the array, the index of "-" character is used (see [RFC6901]).
|
||||
///
|
||||
/// When adding to an object, if an object member does not already exist, a new member is added to the object at the
|
||||
/// specified location or if an object member does exist, that member's value is replaced.
|
||||
///
|
||||
/// The operation object MUST contain a "value" member whose content
|
||||
/// specifies the value to be added.
|
||||
///
|
||||
/// For example:
|
||||
///
|
||||
/// { "op": "add", "path": "/a/b/c", "value": [ "foo", "bar" ] }
|
||||
///
|
||||
/// See RFC 6902 https://tools.ietf.org/html/rfc6902#page-4
|
||||
/// </summary>
|
||||
/// <param name="operation">The add operation.</param>
|
||||
/// <param name="objectToApplyTo">Object to apply the operation to.</param>
|
||||
void Add(Operation operation, object objectToApplyTo);
|
||||
|
||||
/// <summary>
|
||||
/// Using the "copy" operation, a value is copied from a specified location to the
|
||||
/// target location.
|
||||
///
|
||||
/// The operation object MUST contain a "from" member, which references the location in the
|
||||
/// target document to copy the value from.
|
||||
///
|
||||
/// The "from" location MUST exist for the operation to be successful.
|
||||
///
|
||||
/// For example:
|
||||
///
|
||||
/// { "op": "copy", "from": "/a/b/c", "path": "/a/b/e" }
|
||||
///
|
||||
/// See RFC 6902 https://tools.ietf.org/html/rfc6902#page-7
|
||||
/// </summary>
|
||||
/// <param name="operation">The copy operation.</param>
|
||||
/// <param name="objectToApplyTo">Object to apply the operation to.</param>
|
||||
void Copy(Operation operation, object objectToApplyTo);
|
||||
|
||||
/// <summary>
|
||||
/// Using the "move" operation the value at a specified location is removed and
|
||||
/// added to the target location.
|
||||
///
|
||||
/// The operation object MUST contain a "from" member, which references the location in the
|
||||
/// target document to move the value from.
|
||||
///
|
||||
/// The "from" location MUST exist for the operation to be successful.
|
||||
///
|
||||
/// For example:
|
||||
///
|
||||
/// { "op": "move", "from": "/a/b/c", "path": "/a/b/d" }
|
||||
///
|
||||
/// A location cannot be moved into one of its children.
|
||||
///
|
||||
/// See RFC 6902 https://tools.ietf.org/html/rfc6902#page-6
|
||||
/// </summary>
|
||||
/// <param name="operation">The move operation.</param>
|
||||
/// <param name="objectToApplyTo">Object to apply the operation to.</param>
|
||||
void Move(Operation operation, object objectToApplyTo);
|
||||
|
||||
/// <summary>
|
||||
/// Using the "remove" operation the value at the target location is removed.
|
||||
///
|
||||
/// The target location MUST exist for the operation to be successful.
|
||||
///
|
||||
/// For example:
|
||||
///
|
||||
/// { "op": "remove", "path": "/a/b/c" }
|
||||
///
|
||||
/// If removing an element from an array, any elements above the
|
||||
/// specified index are shifted one position to the left.
|
||||
///
|
||||
/// See RFC 6902 https://tools.ietf.org/html/rfc6902#page-6
|
||||
/// </summary>
|
||||
/// <param name="operation">The remove operation.</param>
|
||||
/// <param name="objectToApplyTo">Object to apply the operation to.</param>
|
||||
void Remove(Operation operation, object objectToApplyTo);
|
||||
|
||||
/// <summary>
|
||||
/// Using the "replace" operation he value at the target location is replaced
|
||||
/// with a new value. The operation object MUST contain a "value" member
|
||||
/// which specifies the replacement value.
|
||||
///
|
||||
/// The target location MUST exist for the operation to be successful.
|
||||
///
|
||||
/// For example:
|
||||
///
|
||||
/// { "op": "replace", "path": "/a/b/c", "value": 42 }
|
||||
///
|
||||
/// See RFC 6902 https://tools.ietf.org/html/rfc6902#page-6
|
||||
/// </summary>
|
||||
/// <param name="operation">The replace operation.</param>
|
||||
/// <param name="objectToApplyTo">Object to apply the operation to.</param>
|
||||
void Replace(Operation operation, object objectToApplyTo);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,32 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using Microsoft.AspNetCore.JsonPatch.Operations;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Adapters
|
||||
{
|
||||
/// <summary>
|
||||
/// Defines the operations that can be performed on a JSON patch document, including "test".
|
||||
/// </summary>
|
||||
public interface IObjectAdapterWithTest : IObjectAdapter
|
||||
{
|
||||
/// <summary>
|
||||
/// Using the "test" operation a value at the target location is compared for
|
||||
/// equality to a specified value.
|
||||
///
|
||||
/// The operation object MUST contain a "value" member that specifies
|
||||
/// value to be compared to the target location's value.
|
||||
///
|
||||
/// The target location MUST be equal to the "value" value for the
|
||||
/// operation to be considered successful.
|
||||
///
|
||||
/// For example:
|
||||
/// { "op": "test", "path": "/a/b/c", "value": "foo" }
|
||||
///
|
||||
/// See RFC 6902 https://tools.ietf.org/html/rfc6902#page-7
|
||||
/// </summary>
|
||||
/// <param name="operation">The test operation.</param>
|
||||
/// <param name="objectToApplyTo">Object to apply the operation to.</param>
|
||||
void Test(Operation operation, object objectToApplyTo);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,348 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using Microsoft.AspNetCore.JsonPatch.Internal;
|
||||
using Microsoft.AspNetCore.JsonPatch.Operations;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Adapters
|
||||
{
|
||||
/// <inheritdoc />
|
||||
public class ObjectAdapter : IObjectAdapterWithTest
|
||||
{
|
||||
/// <summary>
|
||||
/// Initializes a new instance of <see cref="ObjectAdapter"/>.
|
||||
/// </summary>
|
||||
/// <param name="contractResolver">The <see cref="IContractResolver"/>.</param>
|
||||
/// <param name="logErrorAction">The <see cref="Action"/> for logging <see cref="JsonPatchError"/>.</param>
|
||||
public ObjectAdapter(
|
||||
IContractResolver contractResolver,
|
||||
Action<JsonPatchError> logErrorAction):
|
||||
this(contractResolver, logErrorAction, new AdapterFactory())
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of <see cref="ObjectAdapter"/>.
|
||||
/// </summary>
|
||||
/// <param name="contractResolver">The <see cref="IContractResolver"/>.</param>
|
||||
/// <param name="logErrorAction">The <see cref="Action"/> for logging <see cref="JsonPatchError"/>.</param>
|
||||
/// <param name="adapterFactory">The <see cref="IAdapterFactory"/> to use when creating adaptors.</param>
|
||||
public ObjectAdapter(
|
||||
IContractResolver contractResolver,
|
||||
Action<JsonPatchError> logErrorAction,
|
||||
IAdapterFactory adapterFactory)
|
||||
{
|
||||
ContractResolver = contractResolver ?? throw new ArgumentNullException(nameof(contractResolver));
|
||||
LogErrorAction = logErrorAction;
|
||||
AdapterFactory = adapterFactory ?? throw new ArgumentNullException(nameof(adapterFactory));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the <see cref="IContractResolver"/>.
|
||||
/// </summary>
|
||||
public IContractResolver ContractResolver { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the <see cref="IAdapterFactory"/>
|
||||
/// </summary>
|
||||
public IAdapterFactory AdapterFactory { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Action for logging <see cref="JsonPatchError"/>.
|
||||
/// </summary>
|
||||
public Action<JsonPatchError> LogErrorAction { get; }
|
||||
|
||||
public void Add(Operation operation, object objectToApplyTo)
|
||||
{
|
||||
if (operation == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(operation));
|
||||
}
|
||||
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
Add(operation.path, operation.value, objectToApplyTo, operation);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add is used by various operations (eg: add, copy, ...), yet through different operations;
|
||||
/// This method allows code reuse yet reporting the correct operation on error
|
||||
/// </summary>
|
||||
private void Add(
|
||||
string path,
|
||||
object value,
|
||||
object objectToApplyTo,
|
||||
Operation operation)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
if (operation == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(operation));
|
||||
}
|
||||
|
||||
var parsedPath = new ParsedPath(path);
|
||||
var visitor = new ObjectVisitor(parsedPath, ContractResolver, AdapterFactory);
|
||||
|
||||
var target = objectToApplyTo;
|
||||
if (!visitor.TryVisit(ref target, out var adapter, out var errorMessage))
|
||||
{
|
||||
var error = CreatePathNotFoundError(objectToApplyTo, path, operation, errorMessage);
|
||||
ErrorReporter(error);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!adapter.TryAdd(target, parsedPath.LastSegment, ContractResolver, value, out errorMessage))
|
||||
{
|
||||
var error = CreateOperationFailedError(objectToApplyTo, path, operation, errorMessage);
|
||||
ErrorReporter(error);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
public void Move(Operation operation, object objectToApplyTo)
|
||||
{
|
||||
if (operation == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(operation));
|
||||
}
|
||||
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
// Get value at 'from' location and add that value to the 'path' location
|
||||
if (TryGetValue(operation.from, objectToApplyTo, operation, out var propertyValue))
|
||||
{
|
||||
// remove that value
|
||||
Remove(operation.from, objectToApplyTo, operation);
|
||||
|
||||
// add that value to the path location
|
||||
Add(operation.path,
|
||||
propertyValue,
|
||||
objectToApplyTo,
|
||||
operation);
|
||||
}
|
||||
}
|
||||
|
||||
public void Remove(Operation operation, object objectToApplyTo)
|
||||
{
|
||||
if (operation == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(operation));
|
||||
}
|
||||
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
Remove(operation.path, objectToApplyTo, operation);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Remove is used by various operations (eg: remove, move, ...), yet through different operations;
|
||||
/// This method allows code reuse yet reporting the correct operation on error. The return value
|
||||
/// contains the type of the item that has been removed (and a bool possibly signifying an error)
|
||||
/// This can be used by other methods, like replace, to ensure that we can pass in the correctly
|
||||
/// typed value to whatever method follows.
|
||||
/// </summary>
|
||||
private void Remove(string path, object objectToApplyTo, Operation operationToReport)
|
||||
{
|
||||
var parsedPath = new ParsedPath(path);
|
||||
var visitor = new ObjectVisitor(parsedPath, ContractResolver, AdapterFactory);
|
||||
|
||||
var target = objectToApplyTo;
|
||||
if (!visitor.TryVisit(ref target, out var adapter, out var errorMessage))
|
||||
{
|
||||
var error = CreatePathNotFoundError(objectToApplyTo, path, operationToReport, errorMessage);
|
||||
ErrorReporter(error);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!adapter.TryRemove(target, parsedPath.LastSegment, ContractResolver, out errorMessage))
|
||||
{
|
||||
var error = CreateOperationFailedError(objectToApplyTo, path, operationToReport, errorMessage);
|
||||
ErrorReporter(error);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
public void Replace(Operation operation, object objectToApplyTo)
|
||||
{
|
||||
if (operation == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(operation));
|
||||
}
|
||||
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
var parsedPath = new ParsedPath(operation.path);
|
||||
var visitor = new ObjectVisitor(parsedPath, ContractResolver, AdapterFactory);
|
||||
|
||||
var target = objectToApplyTo;
|
||||
if (!visitor.TryVisit(ref target, out var adapter, out var errorMessage))
|
||||
{
|
||||
var error = CreatePathNotFoundError(objectToApplyTo, operation.path, operation, errorMessage);
|
||||
ErrorReporter(error);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!adapter.TryReplace(target, parsedPath.LastSegment, ContractResolver, operation.value, out errorMessage))
|
||||
{
|
||||
var error = CreateOperationFailedError(objectToApplyTo, operation.path, operation, errorMessage);
|
||||
ErrorReporter(error);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
public void Copy(Operation operation, object objectToApplyTo)
|
||||
{
|
||||
if (operation == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(operation));
|
||||
}
|
||||
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
// Get value at 'from' location and add that value to the 'path' location
|
||||
if (TryGetValue(operation.from, objectToApplyTo, operation, out var propertyValue))
|
||||
{
|
||||
// Create deep copy
|
||||
var copyResult = ConversionResultProvider.CopyTo(propertyValue, propertyValue?.GetType());
|
||||
if (copyResult.CanBeConverted)
|
||||
{
|
||||
Add(operation.path,
|
||||
copyResult.ConvertedInstance,
|
||||
objectToApplyTo,
|
||||
operation);
|
||||
}
|
||||
else
|
||||
{
|
||||
var error = CreateOperationFailedError(objectToApplyTo, operation.path, operation, Resources.FormatCannotCopyProperty(operation.from));
|
||||
ErrorReporter(error);
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void Test(Operation operation, object objectToApplyTo)
|
||||
{
|
||||
if (operation == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(operation));
|
||||
}
|
||||
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
var parsedPath = new ParsedPath(operation.path);
|
||||
var visitor = new ObjectVisitor(parsedPath, ContractResolver, AdapterFactory);
|
||||
|
||||
var target = objectToApplyTo;
|
||||
if (!visitor.TryVisit(ref target, out var adapter, out var errorMessage))
|
||||
{
|
||||
var error = CreatePathNotFoundError(objectToApplyTo, operation.path, operation, errorMessage);
|
||||
ErrorReporter(error);
|
||||
return;
|
||||
}
|
||||
|
||||
if (!adapter.TryTest(target, parsedPath.LastSegment, ContractResolver, operation.value, out errorMessage))
|
||||
{
|
||||
var error = CreateOperationFailedError(objectToApplyTo, operation.path, operation, errorMessage);
|
||||
ErrorReporter(error);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
private bool TryGetValue(
|
||||
string fromLocation,
|
||||
object objectToGetValueFrom,
|
||||
Operation operation,
|
||||
out object propertyValue)
|
||||
{
|
||||
if (fromLocation == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(fromLocation));
|
||||
}
|
||||
|
||||
if (objectToGetValueFrom == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToGetValueFrom));
|
||||
}
|
||||
|
||||
if (operation == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(operation));
|
||||
}
|
||||
|
||||
propertyValue = null;
|
||||
|
||||
var parsedPath = new ParsedPath(fromLocation);
|
||||
var visitor = new ObjectVisitor(parsedPath, ContractResolver, AdapterFactory);
|
||||
|
||||
var target = objectToGetValueFrom;
|
||||
if (!visitor.TryVisit(ref target, out var adapter, out var errorMessage))
|
||||
{
|
||||
var error = CreatePathNotFoundError(objectToGetValueFrom, fromLocation, operation, errorMessage);
|
||||
ErrorReporter(error);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!adapter.TryGet(target, parsedPath.LastSegment, ContractResolver, out propertyValue, out errorMessage))
|
||||
{
|
||||
var error = CreateOperationFailedError(objectToGetValueFrom, fromLocation, operation, errorMessage);
|
||||
ErrorReporter(error);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
private Action<JsonPatchError> ErrorReporter
|
||||
{
|
||||
get
|
||||
{
|
||||
return LogErrorAction ?? Internal.ErrorReporter.Default;
|
||||
}
|
||||
}
|
||||
|
||||
private JsonPatchError CreateOperationFailedError(object target, string path, Operation operation, string errorMessage)
|
||||
{
|
||||
return new JsonPatchError(
|
||||
target,
|
||||
operation,
|
||||
errorMessage ?? Resources.FormatCannotPerformOperation(operation.op, path));
|
||||
}
|
||||
|
||||
private JsonPatchError CreatePathNotFoundError(object target, string path, Operation operation, string errorMessage)
|
||||
{
|
||||
return new JsonPatchError(
|
||||
target,
|
||||
operation,
|
||||
errorMessage ?? Resources.FormatTargetLocationNotFound(operation.op, path));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,76 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Microsoft.AspNetCore.JsonPatch.Exceptions;
|
||||
using Microsoft.AspNetCore.JsonPatch.Operations;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Linq;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Converters
|
||||
{
|
||||
public class JsonPatchDocumentConverter : JsonConverter
|
||||
{
|
||||
public override bool CanConvert(Type objectType)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
public override object ReadJson(JsonReader reader, Type objectType, object existingValue,
|
||||
JsonSerializer serializer)
|
||||
{
|
||||
if (objectType != typeof(JsonPatchDocument))
|
||||
{
|
||||
throw new ArgumentException(Resources.FormatParameterMustMatchType("objectType", "JsonPatchDocument"), "objectType");
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
if (reader.TokenType == JsonToken.Null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
// load jObject
|
||||
var jObject = JArray.Load(reader);
|
||||
|
||||
// Create target object for Json => list of operations
|
||||
var targetOperations = new List<Operation>();
|
||||
|
||||
// Create a new reader for this jObject, and set all properties
|
||||
// to match the original reader.
|
||||
var jObjectReader = jObject.CreateReader();
|
||||
jObjectReader.Culture = reader.Culture;
|
||||
jObjectReader.DateParseHandling = reader.DateParseHandling;
|
||||
jObjectReader.DateTimeZoneHandling = reader.DateTimeZoneHandling;
|
||||
jObjectReader.FloatParseHandling = reader.FloatParseHandling;
|
||||
|
||||
// Populate the object properties
|
||||
serializer.Populate(jObjectReader, targetOperations);
|
||||
|
||||
// container target: the JsonPatchDocument.
|
||||
var container = new JsonPatchDocument(targetOperations, new DefaultContractResolver());
|
||||
|
||||
return container;
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
throw new JsonSerializationException(Resources.InvalidJsonPatchDocument, ex);
|
||||
}
|
||||
}
|
||||
|
||||
public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer)
|
||||
{
|
||||
if (value is IJsonPatchDocument)
|
||||
{
|
||||
var jsonPatchDoc = (IJsonPatchDocument)value;
|
||||
var lst = jsonPatchDoc.GetOperations();
|
||||
|
||||
// write out the operations, no envelope
|
||||
serializer.Serialize(writer, lst);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,64 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Reflection;
|
||||
using Microsoft.AspNetCore.JsonPatch.Operations;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Linq;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Converters
|
||||
{
|
||||
public class TypedJsonPatchDocumentConverter : JsonPatchDocumentConverter
|
||||
{
|
||||
public override object ReadJson(
|
||||
JsonReader reader,
|
||||
Type objectType,
|
||||
object existingValue,
|
||||
JsonSerializer serializer)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (reader.TokenType == JsonToken.Null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
var genericType = objectType.GetTypeInfo().GenericTypeArguments[0];
|
||||
|
||||
// load jObject
|
||||
var jObject = JArray.Load(reader);
|
||||
|
||||
// Create target object for Json => list of operations, typed to genericType
|
||||
var genericOperation = typeof(Operation<>);
|
||||
var concreteOperationType = genericOperation.MakeGenericType(genericType);
|
||||
|
||||
var genericList = typeof(List<>);
|
||||
var concreteList = genericList.MakeGenericType(concreteOperationType);
|
||||
|
||||
var targetOperations = Activator.CreateInstance(concreteList);
|
||||
|
||||
//Create a new reader for this jObject, and set all properties to match the original reader.
|
||||
var jObjectReader = jObject.CreateReader();
|
||||
jObjectReader.Culture = reader.Culture;
|
||||
jObjectReader.DateParseHandling = reader.DateParseHandling;
|
||||
jObjectReader.DateTimeZoneHandling = reader.DateTimeZoneHandling;
|
||||
jObjectReader.FloatParseHandling = reader.FloatParseHandling;
|
||||
|
||||
// Populate the object properties
|
||||
serializer.Populate(jObjectReader, targetOperations);
|
||||
|
||||
// container target: the typed JsonPatchDocument.
|
||||
var container = Activator.CreateInstance(objectType, targetOperations, new DefaultContractResolver());
|
||||
|
||||
return container;
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
throw new JsonSerializationException(Resources.InvalidJsonPatchDocument, ex);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,38 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using Microsoft.AspNetCore.JsonPatch.Operations;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Exceptions
|
||||
{
|
||||
public class JsonPatchException : Exception
|
||||
{
|
||||
public Operation FailedOperation { get; private set; }
|
||||
public object AffectedObject { get; private set; }
|
||||
|
||||
|
||||
public JsonPatchException()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
public JsonPatchException(JsonPatchError jsonPatchError, Exception innerException)
|
||||
: base(jsonPatchError.ErrorMessage, innerException)
|
||||
{
|
||||
FailedOperation = jsonPatchError.Operation;
|
||||
AffectedObject = jsonPatchError.AffectedObject;
|
||||
}
|
||||
|
||||
public JsonPatchException(JsonPatchError jsonPatchError)
|
||||
: this(jsonPatchError, null)
|
||||
{
|
||||
}
|
||||
|
||||
public JsonPatchException(string message, Exception innerException)
|
||||
: base (message, innerException)
|
||||
{
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,30 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Helpers
|
||||
{
|
||||
/// <summary>
|
||||
/// Return value for the helper method used by Copy/Move. Needed to ensure we can make a different
|
||||
/// decision in the calling method when the value is null because it cannot be fetched (HasError = true)
|
||||
/// versus when it actually is null (much like why RemovedPropertyTypeResult is used for returning
|
||||
/// type in the Remove operation).
|
||||
/// </summary>
|
||||
public class GetValueResult
|
||||
{
|
||||
public GetValueResult(object propertyValue, bool hasError)
|
||||
{
|
||||
PropertyValue = propertyValue;
|
||||
HasError = hasError;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The value of the property we're trying to get
|
||||
/// </summary>
|
||||
public object PropertyValue { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// HasError: true when an error occurred, the operation didn't complete succesfully
|
||||
/// </summary>
|
||||
public bool HasError { get; private set; }
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,43 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch
|
||||
{
|
||||
/// <summary>
|
||||
/// Metadata for JsonProperty.
|
||||
/// </summary>
|
||||
public class JsonPatchProperty
|
||||
{
|
||||
/// <summary>
|
||||
/// Initializes a new instance.
|
||||
/// </summary>
|
||||
public JsonPatchProperty(JsonProperty property, object parent)
|
||||
{
|
||||
if (property == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(property));
|
||||
}
|
||||
|
||||
if (parent == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(parent));
|
||||
}
|
||||
|
||||
Property = property;
|
||||
Parent = parent;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets JsonProperty.
|
||||
/// </summary>
|
||||
public JsonProperty Property { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets Parent.
|
||||
/// </summary>
|
||||
public object Parent { get; set; }
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,16 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using Microsoft.AspNetCore.JsonPatch.Operations;
|
||||
using System.Collections.Generic;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch
|
||||
{
|
||||
public interface IJsonPatchDocument
|
||||
{
|
||||
IContractResolver ContractResolver { get; set; }
|
||||
|
||||
IList<Operation> GetOperations();
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Internal
|
||||
{
|
||||
public class ConversionResult
|
||||
{
|
||||
public ConversionResult(bool canBeConverted, object convertedInstance)
|
||||
{
|
||||
CanBeConverted = canBeConverted;
|
||||
ConvertedInstance = convertedInstance;
|
||||
}
|
||||
|
||||
public bool CanBeConverted { get; }
|
||||
public object ConvertedInstance { get; }
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,75 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using System.Reflection;
|
||||
using Newtonsoft.Json;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Internal
|
||||
{
|
||||
public static class ConversionResultProvider
|
||||
{
|
||||
public static ConversionResult ConvertTo(object value, Type typeToConvertTo)
|
||||
{
|
||||
if (value == null)
|
||||
{
|
||||
return new ConversionResult(IsNullableType(typeToConvertTo), null);
|
||||
}
|
||||
else if (typeToConvertTo.IsAssignableFrom(value.GetType()))
|
||||
{
|
||||
// No need to convert
|
||||
return new ConversionResult(true, value);
|
||||
}
|
||||
else
|
||||
{
|
||||
try
|
||||
{
|
||||
var deserialized = JsonConvert.DeserializeObject(JsonConvert.SerializeObject(value), typeToConvertTo);
|
||||
return new ConversionResult(true, deserialized);
|
||||
}
|
||||
catch
|
||||
{
|
||||
return new ConversionResult(canBeConverted: false, convertedInstance: null);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static ConversionResult CopyTo(object value, Type typeToConvertTo)
|
||||
{
|
||||
var targetType = typeToConvertTo;
|
||||
if (value == null)
|
||||
{
|
||||
return new ConversionResult(canBeConverted: true, convertedInstance: null);
|
||||
}
|
||||
else if (typeToConvertTo.IsAssignableFrom(value.GetType()))
|
||||
{
|
||||
// Keep original type
|
||||
targetType = value.GetType();
|
||||
}
|
||||
try
|
||||
{
|
||||
var deserialized = JsonConvert.DeserializeObject(JsonConvert.SerializeObject(value), targetType);
|
||||
return new ConversionResult(true, deserialized);
|
||||
}
|
||||
catch
|
||||
{
|
||||
return new ConversionResult(canBeConverted: false, convertedInstance: null);
|
||||
}
|
||||
}
|
||||
|
||||
private static bool IsNullableType(Type type)
|
||||
{
|
||||
var typeInfo = type.GetTypeInfo();
|
||||
if (typeInfo.IsValueType)
|
||||
{
|
||||
// value types are only nullable if they are Nullable<T>
|
||||
return typeInfo.IsGenericType && type.GetGenericTypeDefinition() == typeof(Nullable<>);
|
||||
}
|
||||
else
|
||||
{
|
||||
// reference types are always nullable
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,245 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System.Collections.Generic;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Linq;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Internal
|
||||
{
|
||||
public class DictionaryAdapter<TKey, TValue> : IAdapter
|
||||
{
|
||||
public virtual bool TryAdd(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
var contract = (JsonDictionaryContract)contractResolver.ResolveContract(target.GetType());
|
||||
var key = contract.DictionaryKeyResolver(segment);
|
||||
var dictionary = (IDictionary<TKey, TValue>)target;
|
||||
|
||||
// As per JsonPatch spec, if a key already exists, adding should replace the existing value
|
||||
if (!TryConvertKey(key, out var convertedKey, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryConvertValue(value, out var convertedValue, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
dictionary[convertedKey] = convertedValue;
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryGet(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
var contract = (JsonDictionaryContract)contractResolver.ResolveContract(target.GetType());
|
||||
var key = contract.DictionaryKeyResolver(segment);
|
||||
var dictionary = (IDictionary<TKey, TValue>)target;
|
||||
|
||||
if (!TryConvertKey(key, out var convertedKey, out errorMessage))
|
||||
{
|
||||
value = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!dictionary.ContainsKey(convertedKey))
|
||||
{
|
||||
value = null;
|
||||
errorMessage = Resources.FormatTargetLocationAtPathSegmentNotFound(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
value = dictionary[convertedKey];
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryRemove(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out string errorMessage)
|
||||
{
|
||||
var contract = (JsonDictionaryContract)contractResolver.ResolveContract(target.GetType());
|
||||
var key = contract.DictionaryKeyResolver(segment);
|
||||
var dictionary = (IDictionary<TKey, TValue>)target;
|
||||
|
||||
if (!TryConvertKey(key, out var convertedKey, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
// As per JsonPatch spec, the target location must exist for remove to be successful
|
||||
if (!dictionary.ContainsKey(convertedKey))
|
||||
{
|
||||
errorMessage = Resources.FormatTargetLocationAtPathSegmentNotFound(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
dictionary.Remove(convertedKey);
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryReplace(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
var contract = (JsonDictionaryContract)contractResolver.ResolveContract(target.GetType());
|
||||
var key = contract.DictionaryKeyResolver(segment);
|
||||
var dictionary = (IDictionary<TKey, TValue>)target;
|
||||
|
||||
if (!TryConvertKey(key, out var convertedKey, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
// As per JsonPatch spec, the target location must exist for remove to be successful
|
||||
if (!dictionary.ContainsKey(convertedKey))
|
||||
{
|
||||
errorMessage = Resources.FormatTargetLocationAtPathSegmentNotFound(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryConvertValue(value, out var convertedValue, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
dictionary[convertedKey] = convertedValue;
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryTest(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
var contract = (JsonDictionaryContract)contractResolver.ResolveContract(target.GetType());
|
||||
var key = contract.DictionaryKeyResolver(segment);
|
||||
var dictionary = (IDictionary<TKey, TValue>)target;
|
||||
|
||||
if (!TryConvertKey(key, out var convertedKey, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
// As per JsonPatch spec, the target location must exist for test to be successful
|
||||
if (!dictionary.ContainsKey(convertedKey))
|
||||
{
|
||||
errorMessage = Resources.FormatTargetLocationAtPathSegmentNotFound(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryConvertValue(value, out var convertedValue, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
var currentValue = dictionary[convertedKey];
|
||||
|
||||
// The target segment does not have an assigned value to compare the test value with
|
||||
if (currentValue == null || string.IsNullOrEmpty(currentValue.ToString()))
|
||||
{
|
||||
errorMessage = Resources.FormatValueForTargetSegmentCannotBeNullOrEmpty(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!JToken.DeepEquals(JsonConvert.SerializeObject(currentValue), JsonConvert.SerializeObject(convertedValue)))
|
||||
{
|
||||
errorMessage = Resources.FormatValueNotEqualToTestValue(currentValue, value, segment);
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
public virtual bool TryTraverse(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out object nextTarget,
|
||||
out string errorMessage)
|
||||
{
|
||||
var contract = (JsonDictionaryContract)contractResolver.ResolveContract(target.GetType());
|
||||
var key = contract.DictionaryKeyResolver(segment);
|
||||
var dictionary = (IDictionary<TKey, TValue>)target;
|
||||
|
||||
if (!TryConvertKey(key, out var convertedKey, out errorMessage))
|
||||
{
|
||||
nextTarget = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (dictionary.ContainsKey(convertedKey))
|
||||
{
|
||||
nextTarget = dictionary[convertedKey];
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
nextTarget = null;
|
||||
errorMessage = null;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
protected virtual bool TryConvertKey(string key, out TKey convertedKey, out string errorMessage)
|
||||
{
|
||||
var conversionResult = ConversionResultProvider.ConvertTo(key, typeof(TKey));
|
||||
if (conversionResult.CanBeConverted)
|
||||
{
|
||||
errorMessage = null;
|
||||
convertedKey = (TKey)conversionResult.ConvertedInstance;
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
errorMessage = Resources.FormatInvalidPathSegment(key);
|
||||
convertedKey = default(TKey);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
protected virtual bool TryConvertValue(object value, out TValue convertedValue, out string errorMessage)
|
||||
{
|
||||
var conversionResult = ConversionResultProvider.ConvertTo(value, typeof(TValue));
|
||||
if (conversionResult.CanBeConverted)
|
||||
{
|
||||
errorMessage = null;
|
||||
convertedValue = (TValue)conversionResult.ConvertedInstance;
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
errorMessage = Resources.FormatInvalidValueForProperty(value);
|
||||
convertedValue = default(TValue);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,248 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Reflection;
|
||||
using System.Runtime.CompilerServices;
|
||||
using Microsoft.CSharp.RuntimeBinder;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Linq;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
using CSharpBinder = Microsoft.CSharp.RuntimeBinder;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Internal
|
||||
{
|
||||
public class DynamicObjectAdapter : IAdapter
|
||||
{
|
||||
public virtual bool TryAdd(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (!TrySetDynamicObjectProperty(target, contractResolver, segment, value, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryGet(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (!TryGetDynamicObjectProperty(target, contractResolver, segment, out value, out errorMessage))
|
||||
{
|
||||
value = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryRemove(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (!TryGetDynamicObjectProperty(target, contractResolver, segment, out var property, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
// Setting the value to "null" will use the default value in case of value types, and
|
||||
// null in case of reference types
|
||||
object value = null;
|
||||
if (property.GetType().GetTypeInfo().IsValueType
|
||||
&& Nullable.GetUnderlyingType(property.GetType()) == null)
|
||||
{
|
||||
value = Activator.CreateInstance(property.GetType());
|
||||
}
|
||||
|
||||
if (!TrySetDynamicObjectProperty(target, contractResolver, segment, value, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
public virtual bool TryReplace(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (!TryGetDynamicObjectProperty(target, contractResolver, segment, out var property, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryConvertValue(value, property.GetType(), out var convertedValue))
|
||||
{
|
||||
errorMessage = Resources.FormatInvalidValueForProperty(value);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryRemove(target, segment, contractResolver, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TrySetDynamicObjectProperty(target, contractResolver, segment, convertedValue, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryTest(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (!TryGetDynamicObjectProperty(target, contractResolver, segment, out var property, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryConvertValue(value, property.GetType(), out var convertedValue))
|
||||
{
|
||||
errorMessage = Resources.FormatInvalidValueForProperty(value);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!JToken.DeepEquals(JsonConvert.SerializeObject(property), JsonConvert.SerializeObject(convertedValue)))
|
||||
{
|
||||
errorMessage = Resources.FormatValueNotEqualToTestValue(property, value, segment);
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
public virtual bool TryTraverse(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out object nextTarget,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (!TryGetDynamicObjectProperty(target, contractResolver, segment, out var property, out errorMessage))
|
||||
{
|
||||
nextTarget = null;
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
nextTarget = property;
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
protected virtual bool TryGetDynamicObjectProperty(
|
||||
object target,
|
||||
IContractResolver contractResolver,
|
||||
string segment,
|
||||
out object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
var jsonDynamicContract = (JsonDynamicContract)contractResolver.ResolveContract(target.GetType());
|
||||
|
||||
var propertyName = jsonDynamicContract.PropertyNameResolver(segment);
|
||||
|
||||
var binder = CSharpBinder.Binder.GetMember(
|
||||
CSharpBinderFlags.None,
|
||||
propertyName,
|
||||
target.GetType(),
|
||||
new List<CSharpArgumentInfo>
|
||||
{
|
||||
CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null)
|
||||
});
|
||||
|
||||
var callsite = CallSite<Func<CallSite, object, object>>.Create(binder);
|
||||
|
||||
try
|
||||
{
|
||||
value = callsite.Target(callsite, target);
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
catch (RuntimeBinderException)
|
||||
{
|
||||
value = null;
|
||||
errorMessage = Resources.FormatTargetLocationAtPathSegmentNotFound(segment);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
protected virtual bool TrySetDynamicObjectProperty(
|
||||
object target,
|
||||
IContractResolver contractResolver,
|
||||
string segment,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
var jsonDynamicContract = (JsonDynamicContract)contractResolver.ResolveContract(target.GetType());
|
||||
|
||||
var propertyName = jsonDynamicContract.PropertyNameResolver(segment);
|
||||
|
||||
var binder = CSharpBinder.Binder.SetMember(
|
||||
CSharpBinderFlags.None,
|
||||
propertyName,
|
||||
target.GetType(),
|
||||
new List<CSharpArgumentInfo>
|
||||
{
|
||||
CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null),
|
||||
CSharpArgumentInfo.Create(CSharpArgumentInfoFlags.None, null)
|
||||
});
|
||||
|
||||
var callsite = CallSite<Func<CallSite, object, object, object>>.Create(binder);
|
||||
|
||||
try
|
||||
{
|
||||
callsite.Target(callsite, target, value);
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
catch (RuntimeBinderException)
|
||||
{
|
||||
errorMessage = Resources.FormatTargetLocationAtPathSegmentNotFound(segment);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
protected virtual bool TryConvertValue(object value, Type propertyType, out object convertedValue)
|
||||
{
|
||||
var conversionResult = ConversionResultProvider.ConvertTo(value, propertyType);
|
||||
if (!conversionResult.CanBeConverted)
|
||||
{
|
||||
convertedValue = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
convertedValue = conversionResult.ConvertedInstance;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,16 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using Microsoft.AspNetCore.JsonPatch.Exceptions;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Internal
|
||||
{
|
||||
internal static class ErrorReporter
|
||||
{
|
||||
public static readonly Action<JsonPatchError> Default = (error) =>
|
||||
{
|
||||
throw new JsonPatchException(error);
|
||||
};
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,51 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Internal
|
||||
{
|
||||
public interface IAdapter
|
||||
{
|
||||
bool TryTraverse(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out object nextTarget,
|
||||
out string errorMessage);
|
||||
|
||||
bool TryAdd(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage);
|
||||
|
||||
bool TryRemove(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out string errorMessage);
|
||||
|
||||
bool TryGet(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out object value,
|
||||
out string errorMessage);
|
||||
|
||||
bool TryReplace(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage);
|
||||
|
||||
bool TryTest(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,349 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.Collections.Generic;
|
||||
using Microsoft.Extensions.Internal;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Linq;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Internal
|
||||
{
|
||||
public class ListAdapter : IAdapter
|
||||
{
|
||||
public virtual bool TryAdd(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
var list = (IList)target;
|
||||
|
||||
if (!TryGetListTypeArgument(list, out var typeArgument, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryGetPositionInfo(list, segment, OperationType.Add, out var positionInfo, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryConvertValue(value, typeArgument, segment, out var convertedValue, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (positionInfo.Type == PositionType.EndOfList)
|
||||
{
|
||||
list.Add(convertedValue);
|
||||
}
|
||||
else
|
||||
{
|
||||
list.Insert(positionInfo.Index, convertedValue);
|
||||
}
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryGet(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
var list = (IList)target;
|
||||
|
||||
if (!TryGetListTypeArgument(list, out var typeArgument, out errorMessage))
|
||||
{
|
||||
value = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryGetPositionInfo(list, segment, OperationType.Get, out var positionInfo, out errorMessage))
|
||||
{
|
||||
value = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (positionInfo.Type == PositionType.EndOfList)
|
||||
{
|
||||
value = list[list.Count - 1];
|
||||
}
|
||||
else
|
||||
{
|
||||
value = list[positionInfo.Index];
|
||||
}
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryRemove(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out string errorMessage)
|
||||
{
|
||||
var list = (IList)target;
|
||||
|
||||
if (!TryGetListTypeArgument(list, out var typeArgument, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryGetPositionInfo(list, segment, OperationType.Remove, out var positionInfo, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (positionInfo.Type == PositionType.EndOfList)
|
||||
{
|
||||
list.RemoveAt(list.Count - 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
list.RemoveAt(positionInfo.Index);
|
||||
}
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryReplace(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
var list = (IList)target;
|
||||
|
||||
if (!TryGetListTypeArgument(list, out var typeArgument, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryGetPositionInfo(list, segment, OperationType.Replace, out var positionInfo, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryConvertValue(value, typeArgument, segment, out var convertedValue, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (positionInfo.Type == PositionType.EndOfList)
|
||||
{
|
||||
list[list.Count - 1] = convertedValue;
|
||||
}
|
||||
else
|
||||
{
|
||||
list[positionInfo.Index] = convertedValue;
|
||||
}
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryTest(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
var list = (IList)target;
|
||||
|
||||
if (!TryGetListTypeArgument(list, out var typeArgument, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryGetPositionInfo(list, segment, OperationType.Replace, out var positionInfo, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryConvertValue(value, typeArgument, segment, out var convertedValue, out errorMessage))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
var currentValue = list[positionInfo.Index];
|
||||
if (!JToken.DeepEquals(JsonConvert.SerializeObject(currentValue), JsonConvert.SerializeObject(convertedValue)))
|
||||
{
|
||||
errorMessage = Resources.FormatValueAtListPositionNotEqualToTestValue(currentValue, value, positionInfo.Index);
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
public virtual bool TryTraverse(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
var list = target as IList;
|
||||
if (list == null)
|
||||
{
|
||||
value = null;
|
||||
errorMessage = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
var index = -1;
|
||||
if (!int.TryParse(segment, out index))
|
||||
{
|
||||
value = null;
|
||||
errorMessage = Resources.FormatInvalidIndexValue(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (index < 0 || index >= list.Count)
|
||||
{
|
||||
value = null;
|
||||
errorMessage = Resources.FormatIndexOutOfBounds(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
value = list[index];
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
protected virtual bool TryConvertValue(
|
||||
object originalValue,
|
||||
Type listTypeArgument,
|
||||
string segment,
|
||||
out object convertedValue,
|
||||
out string errorMessage)
|
||||
{
|
||||
var conversionResult = ConversionResultProvider.ConvertTo(originalValue, listTypeArgument);
|
||||
if (!conversionResult.CanBeConverted)
|
||||
{
|
||||
convertedValue = null;
|
||||
errorMessage = Resources.FormatInvalidValueForProperty(originalValue);
|
||||
return false;
|
||||
}
|
||||
|
||||
convertedValue = conversionResult.ConvertedInstance;
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
protected virtual bool TryGetListTypeArgument(IList list, out Type listTypeArgument, out string errorMessage)
|
||||
{
|
||||
// Arrays are not supported as they have fixed size and operations like Add, Insert do not make sense
|
||||
var listType = list.GetType();
|
||||
if (listType.IsArray)
|
||||
{
|
||||
errorMessage = Resources.FormatPatchNotSupportedForArrays(listType.FullName);
|
||||
listTypeArgument = null;
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
var genericList = ClosedGenericMatcher.ExtractGenericInterface(listType, typeof(IList<>));
|
||||
if (genericList == null)
|
||||
{
|
||||
errorMessage = Resources.FormatPatchNotSupportedForNonGenericLists(listType.FullName);
|
||||
listTypeArgument = null;
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
listTypeArgument = genericList.GenericTypeArguments[0];
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected virtual bool TryGetPositionInfo(
|
||||
IList list,
|
||||
string segment,
|
||||
OperationType operationType,
|
||||
out PositionInfo positionInfo,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (segment == "-")
|
||||
{
|
||||
positionInfo = new PositionInfo(PositionType.EndOfList, -1);
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
var position = -1;
|
||||
if (int.TryParse(segment, out position))
|
||||
{
|
||||
if (position >= 0 && position < list.Count)
|
||||
{
|
||||
positionInfo = new PositionInfo(PositionType.Index, position);
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
// As per JSON Patch spec, for Add operation the index value representing the number of elements is valid,
|
||||
// where as for other operations like Remove, Replace, Move and Copy the target index MUST exist.
|
||||
else if (position == list.Count && operationType == OperationType.Add)
|
||||
{
|
||||
positionInfo = new PositionInfo(PositionType.EndOfList, -1);
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
positionInfo = new PositionInfo(PositionType.OutOfBounds, position);
|
||||
errorMessage = Resources.FormatIndexOutOfBounds(segment);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
positionInfo = new PositionInfo(PositionType.Invalid, -1);
|
||||
errorMessage = Resources.FormatInvalidIndexValue(segment);
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
protected struct PositionInfo
|
||||
{
|
||||
public PositionInfo(PositionType type, int index)
|
||||
{
|
||||
Type = type;
|
||||
Index = index;
|
||||
}
|
||||
|
||||
public PositionType Type { get; }
|
||||
public int Index { get; }
|
||||
}
|
||||
|
||||
protected enum PositionType
|
||||
{
|
||||
Index, // valid index
|
||||
EndOfList, // '-'
|
||||
Invalid, // Ex: not an integer
|
||||
OutOfBounds
|
||||
}
|
||||
|
||||
protected enum OperationType
|
||||
{
|
||||
Add,
|
||||
Remove,
|
||||
Get,
|
||||
Replace
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,79 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using Microsoft.AspNetCore.JsonPatch.Adapters;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Internal
|
||||
{
|
||||
public class ObjectVisitor
|
||||
{
|
||||
private readonly IAdapterFactory _adapterFactory;
|
||||
private readonly IContractResolver _contractResolver;
|
||||
private readonly ParsedPath _path;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of <see cref="ObjectVisitor"/>.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the JsonPatch operation</param>
|
||||
/// <param name="contractResolver">The <see cref="IContractResolver"/>.</param>
|
||||
public ObjectVisitor(ParsedPath path, IContractResolver contractResolver)
|
||||
:this(path, contractResolver, new AdapterFactory())
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of <see cref="ObjectVisitor"/>.
|
||||
/// </summary>
|
||||
/// <param name="path">The path of the JsonPatch operation</param>
|
||||
/// <param name="contractResolver">The <see cref="IContractResolver"/>.</param>
|
||||
/// <param name="adapterFactory">The <see cref="IAdapterFactory"/> to use when creating adaptors.</param>
|
||||
public ObjectVisitor(ParsedPath path, IContractResolver contractResolver, IAdapterFactory adapterFactory)
|
||||
{
|
||||
_path = path;
|
||||
_contractResolver = contractResolver ?? throw new ArgumentNullException(nameof(contractResolver));
|
||||
_adapterFactory = adapterFactory ?? throw new ArgumentNullException(nameof(adapterFactory));
|
||||
}
|
||||
|
||||
public bool TryVisit(ref object target, out IAdapter adapter, out string errorMessage)
|
||||
{
|
||||
if (target == null)
|
||||
{
|
||||
adapter = null;
|
||||
errorMessage = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
adapter = SelectAdapter(target);
|
||||
|
||||
// Traverse until the penultimate segment to get the target object and adapter
|
||||
for (var i = 0; i < _path.Segments.Count - 1; i++)
|
||||
{
|
||||
if (!adapter.TryTraverse(target, _path.Segments[i], _contractResolver, out var next, out errorMessage))
|
||||
{
|
||||
adapter = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
// If we hit a null on an interior segment then we need to stop traversing.
|
||||
if (next == null)
|
||||
{
|
||||
adapter = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
target = next;
|
||||
adapter = SelectAdapter(target);
|
||||
}
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
private IAdapter SelectAdapter(object targetObject)
|
||||
{
|
||||
return _adapterFactory.Create(targetObject, _contractResolver);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,92 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using Microsoft.AspNetCore.JsonPatch.Exceptions;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Internal
|
||||
{
|
||||
public struct ParsedPath
|
||||
{
|
||||
private static readonly string[] Empty = null;
|
||||
|
||||
private readonly string[] _segments;
|
||||
|
||||
public ParsedPath(string path)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
_segments = ParsePath(path);
|
||||
}
|
||||
|
||||
public string LastSegment
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_segments == null || _segments.Length == 0)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
return _segments[_segments.Length - 1];
|
||||
}
|
||||
}
|
||||
|
||||
public IReadOnlyList<string> Segments => _segments ?? Empty;
|
||||
|
||||
private static string[] ParsePath(string path)
|
||||
{
|
||||
var strings = new List<string>();
|
||||
var sb = new StringBuilder(path.Length);
|
||||
|
||||
for (var i = 0; i < path.Length; i++)
|
||||
{
|
||||
if (path[i] == '/')
|
||||
{
|
||||
if (sb.Length > 0)
|
||||
{
|
||||
strings.Add(sb.ToString());
|
||||
sb.Length = 0;
|
||||
}
|
||||
}
|
||||
else if (path[i] == '~')
|
||||
{
|
||||
++i;
|
||||
if (i >= path.Length)
|
||||
{
|
||||
throw new JsonPatchException(Resources.FormatInvalidValueForPath(path), null);
|
||||
}
|
||||
|
||||
if (path[i] == '0')
|
||||
{
|
||||
sb.Append('~');
|
||||
}
|
||||
else if (path[i] == '1')
|
||||
{
|
||||
sb.Append('/');
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new JsonPatchException(Resources.FormatInvalidValueForPath(path), null);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
sb.Append(path[i]);
|
||||
}
|
||||
}
|
||||
|
||||
if (sb.Length > 0)
|
||||
{
|
||||
strings.Add(sb.ToString());
|
||||
}
|
||||
|
||||
return strings.ToArray();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,32 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using Microsoft.AspNetCore.JsonPatch.Exceptions;
|
||||
using System;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Internal
|
||||
{
|
||||
internal static class PathHelpers
|
||||
{
|
||||
internal static string ValidateAndNormalizePath(string path)
|
||||
{
|
||||
// check for most common path errors on create. This is not
|
||||
// absolutely necessary, but it allows us to already catch mistakes
|
||||
// on creation of the patch document rather than on execute.
|
||||
|
||||
if (path.Contains("//"))
|
||||
{
|
||||
throw new JsonPatchException(Resources.FormatInvalidValueForPath(path), null);
|
||||
}
|
||||
|
||||
if (!path.StartsWith("/", StringComparison.Ordinal))
|
||||
{
|
||||
return "/" + path;
|
||||
}
|
||||
else
|
||||
{
|
||||
return path;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,236 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using System.Linq;
|
||||
using System.Reflection;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Linq;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Internal
|
||||
{
|
||||
public class PocoAdapter : IAdapter
|
||||
{
|
||||
public virtual bool TryAdd(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (!TryGetJsonProperty(target, contractResolver, segment, out var jsonProperty))
|
||||
{
|
||||
errorMessage = Resources.FormatTargetLocationAtPathSegmentNotFound(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!jsonProperty.Writable)
|
||||
{
|
||||
errorMessage = Resources.FormatCannotUpdateProperty(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryConvertValue(value, jsonProperty.PropertyType, out var convertedValue))
|
||||
{
|
||||
errorMessage = Resources.FormatInvalidValueForProperty(value);
|
||||
return false;
|
||||
}
|
||||
|
||||
jsonProperty.ValueProvider.SetValue(target, convertedValue);
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryGet(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (!TryGetJsonProperty(target, contractResolver, segment, out var jsonProperty))
|
||||
{
|
||||
errorMessage = Resources.FormatTargetLocationAtPathSegmentNotFound(segment);
|
||||
value = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!jsonProperty.Readable)
|
||||
{
|
||||
errorMessage = Resources.FormatCannotReadProperty(segment);
|
||||
value = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
value = jsonProperty.ValueProvider.GetValue(target);
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryRemove(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (!TryGetJsonProperty(target, contractResolver, segment, out var jsonProperty))
|
||||
{
|
||||
errorMessage = Resources.FormatTargetLocationAtPathSegmentNotFound(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!jsonProperty.Writable)
|
||||
{
|
||||
errorMessage = Resources.FormatCannotUpdateProperty(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
// Setting the value to "null" will use the default value in case of value types, and
|
||||
// null in case of reference types
|
||||
object value = null;
|
||||
if (jsonProperty.PropertyType.GetTypeInfo().IsValueType
|
||||
&& Nullable.GetUnderlyingType(jsonProperty.PropertyType) == null)
|
||||
{
|
||||
value = Activator.CreateInstance(jsonProperty.PropertyType);
|
||||
}
|
||||
|
||||
jsonProperty.ValueProvider.SetValue(target, value);
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryReplace(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver
|
||||
contractResolver,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (!TryGetJsonProperty(target, contractResolver, segment, out var jsonProperty))
|
||||
{
|
||||
errorMessage = Resources.FormatTargetLocationAtPathSegmentNotFound(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!jsonProperty.Writable)
|
||||
{
|
||||
errorMessage = Resources.FormatCannotUpdateProperty(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryConvertValue(value, jsonProperty.PropertyType, out var convertedValue))
|
||||
{
|
||||
errorMessage = Resources.FormatInvalidValueForProperty(value);
|
||||
return false;
|
||||
}
|
||||
|
||||
jsonProperty.ValueProvider.SetValue(target, convertedValue);
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryTest(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver
|
||||
contractResolver,
|
||||
object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (!TryGetJsonProperty(target, contractResolver, segment, out var jsonProperty))
|
||||
{
|
||||
errorMessage = Resources.FormatTargetLocationAtPathSegmentNotFound(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!jsonProperty.Readable)
|
||||
{
|
||||
errorMessage = Resources.FormatCannotReadProperty(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!TryConvertValue(value, jsonProperty.PropertyType, out var convertedValue))
|
||||
{
|
||||
errorMessage = Resources.FormatInvalidValueForProperty(value);
|
||||
return false;
|
||||
}
|
||||
|
||||
var currentValue = jsonProperty.ValueProvider.GetValue(target);
|
||||
if (!JToken.DeepEquals(JsonConvert.SerializeObject(currentValue), JsonConvert.SerializeObject(convertedValue)))
|
||||
{
|
||||
errorMessage = Resources.FormatValueNotEqualToTestValue(currentValue, value, segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
public virtual bool TryTraverse(
|
||||
object target,
|
||||
string segment,
|
||||
IContractResolver contractResolver,
|
||||
out object value,
|
||||
out string errorMessage)
|
||||
{
|
||||
if (target == null)
|
||||
{
|
||||
value = null;
|
||||
errorMessage = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (TryGetJsonProperty(target, contractResolver, segment, out var jsonProperty))
|
||||
{
|
||||
value = jsonProperty.ValueProvider.GetValue(target);
|
||||
errorMessage = null;
|
||||
return true;
|
||||
}
|
||||
|
||||
value = null;
|
||||
errorMessage = Resources.FormatTargetLocationAtPathSegmentNotFound(segment);
|
||||
return false;
|
||||
}
|
||||
|
||||
protected virtual bool TryGetJsonProperty(
|
||||
object target,
|
||||
IContractResolver contractResolver,
|
||||
string segment,
|
||||
out JsonProperty jsonProperty)
|
||||
{
|
||||
if (contractResolver.ResolveContract(target.GetType()) is JsonObjectContract jsonObjectContract)
|
||||
{
|
||||
var pocoProperty = jsonObjectContract
|
||||
.Properties
|
||||
.FirstOrDefault(p => string.Equals(p.PropertyName, segment, StringComparison.OrdinalIgnoreCase));
|
||||
|
||||
if (pocoProperty != null)
|
||||
{
|
||||
jsonProperty = pocoProperty;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
jsonProperty = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
protected virtual bool TryConvertValue(object value, Type propertyType, out object convertedValue)
|
||||
{
|
||||
var conversionResult = ConversionResultProvider.ConvertTo(value, propertyType);
|
||||
if (!conversionResult.CanBeConverted)
|
||||
{
|
||||
convertedValue = null;
|
||||
return false;
|
||||
}
|
||||
|
||||
convertedValue = conversionResult.ConvertedInstance;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,271 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Microsoft.AspNetCore.JsonPatch.Adapters;
|
||||
using Microsoft.AspNetCore.JsonPatch.Converters;
|
||||
using Microsoft.AspNetCore.JsonPatch.Exceptions;
|
||||
using Microsoft.AspNetCore.JsonPatch.Internal;
|
||||
using Microsoft.AspNetCore.JsonPatch.Operations;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch
|
||||
{
|
||||
// Implementation details: the purpose of this type of patch document is to allow creation of such
|
||||
// documents for cases where there's no class/DTO to work on. Typical use case: backend not built in
|
||||
// .NET or architecture doesn't contain a shared DTO layer.
|
||||
[JsonConverter(typeof(JsonPatchDocumentConverter))]
|
||||
public class JsonPatchDocument : IJsonPatchDocument
|
||||
{
|
||||
public List<Operation> Operations { get; private set; }
|
||||
|
||||
[JsonIgnore]
|
||||
public IContractResolver ContractResolver { get; set; }
|
||||
|
||||
public JsonPatchDocument()
|
||||
{
|
||||
Operations = new List<Operation>();
|
||||
ContractResolver = new DefaultContractResolver();
|
||||
}
|
||||
|
||||
public JsonPatchDocument(List<Operation> operations, IContractResolver contractResolver)
|
||||
{
|
||||
if (operations == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(operations));
|
||||
}
|
||||
|
||||
if (contractResolver == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(contractResolver));
|
||||
}
|
||||
|
||||
Operations = operations;
|
||||
ContractResolver = contractResolver;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add operation. Will result in, for example,
|
||||
/// { "op": "add", "path": "/a/b/c", "value": [ "foo", "bar" ] }
|
||||
/// </summary>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="value">value</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument Add(string path, object value)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation("add", PathHelpers.ValidateAndNormalizePath(path), null, value));
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Remove value at target location. Will result in, for example,
|
||||
/// { "op": "remove", "path": "/a/b/c" }
|
||||
/// </summary>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument Remove(string path)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation("remove", PathHelpers.ValidateAndNormalizePath(path), null, null));
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Replace value. Will result in, for example,
|
||||
/// { "op": "replace", "path": "/a/b/c", "value": 42 }
|
||||
/// </summary>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="value">value</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument Replace(string path, object value)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation("replace", PathHelpers.ValidateAndNormalizePath(path), null, value));
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Test value. Will result in, for example,
|
||||
/// { "op": "test", "path": "/a/b/c", "value": 42 }
|
||||
/// </summary>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="value">value</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument Test(string path, object value)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation("test", PathHelpers.ValidateAndNormalizePath(path), null, value));
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Removes value at specified location and add it to the target location. Will result in, for example:
|
||||
/// { "op": "move", "from": "/a/b/c", "path": "/a/b/d" }
|
||||
/// </summary>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument Move(string from, string path)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation("move", PathHelpers.ValidateAndNormalizePath(path), PathHelpers.ValidateAndNormalizePath(from)));
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Copy the value at specified location to the target location. Will result in, for example:
|
||||
/// { "op": "copy", "from": "/a/b/c", "path": "/a/b/e" }
|
||||
/// </summary>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument Copy(string from, string path)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation("copy", PathHelpers.ValidateAndNormalizePath(path), PathHelpers.ValidateAndNormalizePath(from)));
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Apply this JsonPatchDocument
|
||||
/// </summary>
|
||||
/// <param name="objectToApplyTo">Object to apply the JsonPatchDocument to</param>
|
||||
public void ApplyTo(object objectToApplyTo)
|
||||
{
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
ApplyTo(objectToApplyTo, new ObjectAdapter(ContractResolver, null, new AdapterFactory()));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Apply this JsonPatchDocument
|
||||
/// </summary>
|
||||
/// <param name="objectToApplyTo">Object to apply the JsonPatchDocument to</param>
|
||||
/// <param name="logErrorAction">Action to log errors</param>
|
||||
public void ApplyTo(object objectToApplyTo, Action<JsonPatchError> logErrorAction)
|
||||
{
|
||||
ApplyTo(objectToApplyTo, new ObjectAdapter(ContractResolver, logErrorAction, new AdapterFactory()), logErrorAction);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Apply this JsonPatchDocument
|
||||
/// </summary>
|
||||
/// <param name="objectToApplyTo">Object to apply the JsonPatchDocument to</param>
|
||||
/// <param name="adapter">IObjectAdapter instance to use when applying</param>
|
||||
/// <param name="logErrorAction">Action to log errors</param>
|
||||
public void ApplyTo(object objectToApplyTo, IObjectAdapter adapter, Action<JsonPatchError> logErrorAction)
|
||||
{
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
if (adapter == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(adapter));
|
||||
}
|
||||
|
||||
foreach (var op in Operations)
|
||||
{
|
||||
try
|
||||
{
|
||||
op.Apply(objectToApplyTo, adapter);
|
||||
}
|
||||
catch (JsonPatchException jsonPatchException)
|
||||
{
|
||||
var errorReporter = logErrorAction ?? ErrorReporter.Default;
|
||||
errorReporter(new JsonPatchError(objectToApplyTo, op, jsonPatchException.Message));
|
||||
|
||||
// As per JSON Patch spec if an operation results in error, further operations should not be executed.
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Apply this JsonPatchDocument
|
||||
/// </summary>
|
||||
/// <param name="objectToApplyTo">Object to apply the JsonPatchDocument to</param>
|
||||
/// <param name="adapter">IObjectAdapter instance to use when applying</param>
|
||||
public void ApplyTo(object objectToApplyTo, IObjectAdapter adapter)
|
||||
{
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
if (adapter == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(adapter));
|
||||
}
|
||||
|
||||
// apply each operation in order
|
||||
foreach (var op in Operations)
|
||||
{
|
||||
op.Apply(objectToApplyTo, adapter);
|
||||
}
|
||||
}
|
||||
|
||||
IList<Operation> IJsonPatchDocument.GetOperations()
|
||||
{
|
||||
var allOps = new List<Operation>();
|
||||
|
||||
if (Operations != null)
|
||||
{
|
||||
foreach (var op in Operations)
|
||||
{
|
||||
var untypedOp = new Operation();
|
||||
|
||||
untypedOp.op = op.op;
|
||||
untypedOp.value = op.value;
|
||||
untypedOp.path = op.path;
|
||||
untypedOp.from = op.from;
|
||||
|
||||
allOps.Add(untypedOp);
|
||||
}
|
||||
}
|
||||
|
||||
return allOps;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,884 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using System.Linq;
|
||||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using System.Linq.Expressions;
|
||||
using Microsoft.AspNetCore.JsonPatch.Adapters;
|
||||
using Microsoft.AspNetCore.JsonPatch.Converters;
|
||||
using Microsoft.AspNetCore.JsonPatch.Exceptions;
|
||||
using Microsoft.AspNetCore.JsonPatch.Internal;
|
||||
using Microsoft.AspNetCore.JsonPatch.Operations;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Serialization;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch
|
||||
{
|
||||
// Implementation details: the purpose of this type of patch document is to ensure we can do type-checking
|
||||
// when producing a JsonPatchDocument. However, we cannot send this "typed" over the wire, as that would require
|
||||
// including type data in the JsonPatchDocument serialized as JSON (to allow for correct deserialization) - that's
|
||||
// not according to RFC 6902, and would thus break cross-platform compatibility.
|
||||
[JsonConverter(typeof(TypedJsonPatchDocumentConverter))]
|
||||
public class JsonPatchDocument<TModel> : IJsonPatchDocument where TModel : class
|
||||
{
|
||||
public List<Operation<TModel>> Operations { get; private set; }
|
||||
|
||||
[JsonIgnore]
|
||||
public IContractResolver ContractResolver { get; set; }
|
||||
|
||||
public JsonPatchDocument()
|
||||
{
|
||||
Operations = new List<Operation<TModel>>();
|
||||
ContractResolver = new DefaultContractResolver();
|
||||
}
|
||||
|
||||
// Create from list of operations
|
||||
public JsonPatchDocument(List<Operation<TModel>> operations, IContractResolver contractResolver)
|
||||
{
|
||||
Operations = operations ?? throw new ArgumentNullException(nameof(operations));
|
||||
ContractResolver = contractResolver ?? throw new ArgumentNullException(nameof(contractResolver));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add operation. Will result in, for example,
|
||||
/// { "op": "add", "path": "/a/b/c", "value": [ "foo", "bar" ] }
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp">value type</typeparam>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="value">value</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Add<TProp>(Expression<Func<TModel, TProp>> path, TProp value)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"add",
|
||||
GetPath(path, null),
|
||||
from: null,
|
||||
value: value));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add value to list at given position
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp">value type</typeparam>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="value">value</param>
|
||||
/// <param name="position">position</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Add<TProp>(
|
||||
Expression<Func<TModel, IList<TProp>>> path,
|
||||
TProp value,
|
||||
int position)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"add",
|
||||
GetPath(path, position.ToString()),
|
||||
from: null,
|
||||
value: value));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Add value to the end of the list
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp">value type</typeparam>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="value">value</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Add<TProp>(Expression<Func<TModel, IList<TProp>>> path, TProp value)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"add",
|
||||
GetPath(path, "-"),
|
||||
from: null,
|
||||
value: value));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Remove value at target location. Will result in, for example,
|
||||
/// { "op": "remove", "path": "/a/b/c" }
|
||||
/// </summary>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Remove<TProp>(Expression<Func<TModel, TProp>> path)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>("remove", GetPath(path, null), from: null));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Remove value from list at given position
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp">value type</typeparam>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="position">position</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Remove<TProp>(Expression<Func<TModel, IList<TProp>>> path, int position)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"remove",
|
||||
GetPath(path, position.ToString()),
|
||||
from: null));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Remove value from end of list
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp">value type</typeparam>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Remove<TProp>(Expression<Func<TModel, IList<TProp>>> path)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"remove",
|
||||
GetPath(path, "-"),
|
||||
from: null));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Replace value. Will result in, for example,
|
||||
/// { "op": "replace", "path": "/a/b/c", "value": 42 }
|
||||
/// </summary>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="value">value</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Replace<TProp>(Expression<Func<TModel, TProp>> path, TProp value)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"replace",
|
||||
GetPath(path, null),
|
||||
from: null,
|
||||
value: value));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Replace value in a list at given position
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp">value type</typeparam>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="value">value</param>
|
||||
/// <param name="position">position</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Replace<TProp>(Expression<Func<TModel, IList<TProp>>> path,
|
||||
TProp value, int position)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"replace",
|
||||
GetPath(path, position.ToString()),
|
||||
from: null,
|
||||
value: value));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Replace value at end of a list
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp">value type</typeparam>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="value">value</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Replace<TProp>(Expression<Func<TModel, IList<TProp>>> path, TProp value)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"replace",
|
||||
GetPath(path, "-"),
|
||||
from: null,
|
||||
value: value));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Test value. Will result in, for example,
|
||||
/// { "op": "test", "path": "/a/b/c", "value": 42 }
|
||||
/// </summary>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="value">value</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Test<TProp>(Expression<Func<TModel, TProp>> path, TProp value)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"test",
|
||||
GetPath(path, null),
|
||||
from: null,
|
||||
value: value));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Test value in a list at given position
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp">value type</typeparam>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="value">value</param>
|
||||
/// <param name="position">position</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Test<TProp>(Expression<Func<TModel, IList<TProp>>> path,
|
||||
TProp value, int position)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"test",
|
||||
GetPath(path, position.ToString()),
|
||||
from: null,
|
||||
value: value));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Test value at end of a list
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp">value type</typeparam>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="value">value</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Test<TProp>(Expression<Func<TModel, IList<TProp>>> path, TProp value)
|
||||
{
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"test",
|
||||
GetPath(path, "-"),
|
||||
from: null,
|
||||
value: value));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Removes value at specified location and add it to the target location. Will result in, for example:
|
||||
/// { "op": "move", "from": "/a/b/c", "path": "/a/b/d" }
|
||||
/// </summary>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Move<TProp>(
|
||||
Expression<Func<TModel, TProp>> from,
|
||||
Expression<Func<TModel, TProp>> path)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"move",
|
||||
GetPath(path, null),
|
||||
GetPath(from, null)));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Move from a position in a list to a new location
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp"></typeparam>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="positionFrom">position</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Move<TProp>(
|
||||
Expression<Func<TModel, IList<TProp>>> from,
|
||||
int positionFrom,
|
||||
Expression<Func<TModel, TProp>> path)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"move",
|
||||
GetPath(path, null),
|
||||
GetPath(from, positionFrom.ToString())));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Move from a property to a location in a list
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp"></typeparam>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="positionTo">position</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Move<TProp>(
|
||||
Expression<Func<TModel, TProp>> from,
|
||||
Expression<Func<TModel, IList<TProp>>> path,
|
||||
int positionTo)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"move",
|
||||
GetPath(path, positionTo.ToString()),
|
||||
GetPath(from, null)));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Move from a position in a list to another location in a list
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp"></typeparam>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="positionFrom">position (source)</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="positionTo">position (target)</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Move<TProp>(
|
||||
Expression<Func<TModel, IList<TProp>>> from,
|
||||
int positionFrom,
|
||||
Expression<Func<TModel, IList<TProp>>> path,
|
||||
int positionTo)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"move",
|
||||
GetPath(path, positionTo.ToString()),
|
||||
GetPath(from, positionFrom.ToString())));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Move from a position in a list to the end of another list
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp"></typeparam>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="positionFrom">position</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Move<TProp>(
|
||||
Expression<Func<TModel, IList<TProp>>> from,
|
||||
int positionFrom,
|
||||
Expression<Func<TModel, IList<TProp>>> path)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"move",
|
||||
GetPath(path, "-"),
|
||||
GetPath(from, positionFrom.ToString())));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Move to the end of a list
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp"></typeparam>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Move<TProp>(
|
||||
Expression<Func<TModel, TProp>> from,
|
||||
Expression<Func<TModel, IList<TProp>>> path)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"move",
|
||||
GetPath(path, "-"),
|
||||
GetPath(from, null)));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Copy the value at specified location to the target location. Will result in, for example:
|
||||
/// { "op": "copy", "from": "/a/b/c", "path": "/a/b/e" }
|
||||
/// </summary>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Copy<TProp>(
|
||||
Expression<Func<TModel, TProp>> from,
|
||||
Expression<Func<TModel, TProp>> path)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"copy",
|
||||
GetPath(path, null),
|
||||
GetPath(from, null)));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Copy from a position in a list to a new location
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp"></typeparam>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="positionFrom">position</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Copy<TProp>(
|
||||
Expression<Func<TModel, IList<TProp>>> from,
|
||||
int positionFrom,
|
||||
Expression<Func<TModel, TProp>> path)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"copy",
|
||||
GetPath(path, null),
|
||||
GetPath(from, positionFrom.ToString())));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Copy from a property to a location in a list
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp"></typeparam>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="positionTo">position</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Copy<TProp>(
|
||||
Expression<Func<TModel, TProp>> from,
|
||||
Expression<Func<TModel, IList<TProp>>> path,
|
||||
int positionTo)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"copy",
|
||||
GetPath(path, positionTo.ToString()),
|
||||
GetPath(from, null)));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Copy from a position in a list to a new location in a list
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp"></typeparam>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="positionFrom">position (source)</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <param name="positionTo">position (target)</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Copy<TProp>(
|
||||
Expression<Func<TModel, IList<TProp>>> from,
|
||||
int positionFrom,
|
||||
Expression<Func<TModel, IList<TProp>>> path,
|
||||
int positionTo)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"copy",
|
||||
GetPath(path, positionTo.ToString()),
|
||||
GetPath(from, positionFrom.ToString())));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Copy from a position in a list to the end of another list
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp"></typeparam>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="positionFrom">position</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Copy<TProp>(
|
||||
Expression<Func<TModel, IList<TProp>>> from,
|
||||
int positionFrom,
|
||||
Expression<Func<TModel, IList<TProp>>> path)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"copy",
|
||||
GetPath(path, "-"),
|
||||
GetPath(from, positionFrom.ToString())));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Copy to the end of a list
|
||||
/// </summary>
|
||||
/// <typeparam name="TProp"></typeparam>
|
||||
/// <param name="from">source location</param>
|
||||
/// <param name="path">target location</param>
|
||||
/// <returns></returns>
|
||||
public JsonPatchDocument<TModel> Copy<TProp>(
|
||||
Expression<Func<TModel, TProp>> from,
|
||||
Expression<Func<TModel, IList<TProp>>> path)
|
||||
{
|
||||
if (from == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(from));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
Operations.Add(new Operation<TModel>(
|
||||
"copy",
|
||||
GetPath(path, "-"),
|
||||
GetPath(from, null)));
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Apply this JsonPatchDocument
|
||||
/// </summary>
|
||||
/// <param name="objectToApplyTo">Object to apply the JsonPatchDocument to</param>
|
||||
public void ApplyTo(TModel objectToApplyTo)
|
||||
{
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
ApplyTo(objectToApplyTo, new ObjectAdapter(ContractResolver, null, new AdapterFactory()));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Apply this JsonPatchDocument
|
||||
/// </summary>
|
||||
/// <param name="objectToApplyTo">Object to apply the JsonPatchDocument to</param>
|
||||
/// <param name="logErrorAction">Action to log errors</param>
|
||||
public void ApplyTo(TModel objectToApplyTo, Action<JsonPatchError> logErrorAction)
|
||||
{
|
||||
ApplyTo(objectToApplyTo, new ObjectAdapter(ContractResolver, logErrorAction, new AdapterFactory()), logErrorAction);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Apply this JsonPatchDocument
|
||||
/// </summary>
|
||||
/// <param name="objectToApplyTo">Object to apply the JsonPatchDocument to</param>
|
||||
/// <param name="adapter">IObjectAdapter instance to use when applying</param>
|
||||
/// <param name="logErrorAction">Action to log errors</param>
|
||||
public void ApplyTo(TModel objectToApplyTo, IObjectAdapter adapter, Action<JsonPatchError> logErrorAction)
|
||||
{
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
if (adapter == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(adapter));
|
||||
}
|
||||
|
||||
foreach (var op in Operations)
|
||||
{
|
||||
try
|
||||
{
|
||||
op.Apply(objectToApplyTo, adapter);
|
||||
}
|
||||
catch (JsonPatchException jsonPatchException)
|
||||
{
|
||||
var errorReporter = logErrorAction ?? ErrorReporter.Default;
|
||||
errorReporter(new JsonPatchError(objectToApplyTo, op, jsonPatchException.Message));
|
||||
|
||||
// As per JSON Patch spec if an operation results in error, further operations should not be executed.
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Apply this JsonPatchDocument
|
||||
/// </summary>
|
||||
/// <param name="objectToApplyTo">Object to apply the JsonPatchDocument to</param>
|
||||
/// <param name="adapter">IObjectAdapter instance to use when applying</param>
|
||||
public void ApplyTo(TModel objectToApplyTo, IObjectAdapter adapter)
|
||||
{
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
if (adapter == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(adapter));
|
||||
}
|
||||
|
||||
// apply each operation in order
|
||||
foreach (var op in Operations)
|
||||
{
|
||||
op.Apply(objectToApplyTo, adapter);
|
||||
}
|
||||
}
|
||||
|
||||
IList<Operation> IJsonPatchDocument.GetOperations()
|
||||
{
|
||||
var allOps = new List<Operation>();
|
||||
|
||||
if (Operations != null)
|
||||
{
|
||||
foreach (var op in Operations)
|
||||
{
|
||||
var untypedOp = new Operation
|
||||
{
|
||||
op = op.op,
|
||||
value = op.value,
|
||||
path = op.path,
|
||||
from = op.from
|
||||
};
|
||||
|
||||
allOps.Add(untypedOp);
|
||||
}
|
||||
}
|
||||
|
||||
return allOps;
|
||||
}
|
||||
|
||||
// Internal for testing
|
||||
internal string GetPath<TProp>(Expression<Func<TModel, TProp>> expr, string position)
|
||||
{
|
||||
var segments = GetPathSegments(expr.Body);
|
||||
var path = String.Join("/", segments);
|
||||
if (position != null)
|
||||
{
|
||||
path += "/" + position;
|
||||
if (segments.Count == 0)
|
||||
{
|
||||
return path;
|
||||
}
|
||||
}
|
||||
|
||||
return "/" + path;
|
||||
}
|
||||
|
||||
private List<string> GetPathSegments(Expression expr)
|
||||
{
|
||||
var listOfSegments = new List<string>();
|
||||
switch (expr.NodeType)
|
||||
{
|
||||
case ExpressionType.ArrayIndex:
|
||||
var binaryExpression = (BinaryExpression)expr;
|
||||
listOfSegments.AddRange(GetPathSegments(binaryExpression.Left));
|
||||
listOfSegments.Add(binaryExpression.Right.ToString());
|
||||
return listOfSegments;
|
||||
|
||||
case ExpressionType.Call:
|
||||
var methodCallExpression = (MethodCallExpression)expr;
|
||||
listOfSegments.AddRange(GetPathSegments(methodCallExpression.Object));
|
||||
listOfSegments.Add(EvaluateExpression(methodCallExpression.Arguments[0]));
|
||||
return listOfSegments;
|
||||
|
||||
case ExpressionType.Convert:
|
||||
listOfSegments.AddRange(GetPathSegments(((UnaryExpression)expr).Operand));
|
||||
return listOfSegments;
|
||||
|
||||
case ExpressionType.MemberAccess:
|
||||
var memberExpression = expr as MemberExpression;
|
||||
listOfSegments.AddRange(GetPathSegments(memberExpression.Expression));
|
||||
// Get property name, respecting JsonProperty attribute
|
||||
listOfSegments.Add(GetPropertyNameFromMemberExpression(memberExpression));
|
||||
return listOfSegments;
|
||||
|
||||
case ExpressionType.Parameter:
|
||||
// Fits "x => x" (the whole document which is "" as JSON pointer)
|
||||
return listOfSegments;
|
||||
|
||||
default:
|
||||
throw new InvalidOperationException(Resources.FormatExpressionTypeNotSupported(expr));
|
||||
}
|
||||
}
|
||||
|
||||
private string GetPropertyNameFromMemberExpression(MemberExpression memberExpression)
|
||||
{
|
||||
var jsonObjectContract = ContractResolver.ResolveContract(memberExpression.Expression.Type) as JsonObjectContract;
|
||||
if (jsonObjectContract != null)
|
||||
{
|
||||
return jsonObjectContract.Properties
|
||||
.First(jsonProperty => jsonProperty.UnderlyingName == memberExpression.Member.Name)
|
||||
.PropertyName;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
private static bool ContinueWithSubPath(ExpressionType expressionType)
|
||||
{
|
||||
return (expressionType == ExpressionType.ArrayIndex
|
||||
|| expressionType == ExpressionType.Call
|
||||
|| expressionType == ExpressionType.Convert
|
||||
|| expressionType == ExpressionType.MemberAccess);
|
||||
|
||||
}
|
||||
|
||||
// Evaluates the value of the key or index which may be an int or a string,
|
||||
// or some other expression type.
|
||||
// The expression is converted to a delegate and the result of executing the delegate is returned as a string.
|
||||
private static string EvaluateExpression(Expression expression)
|
||||
{
|
||||
var converted = Expression.Convert(expression, typeof(object));
|
||||
var fakeParameter = Expression.Parameter(typeof(object), null);
|
||||
var lambda = Expression.Lambda<Func<object, object>>(converted, fakeParameter);
|
||||
var func = lambda.Compile();
|
||||
|
||||
return Convert.ToString(func(null), CultureInfo.InvariantCulture);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,50 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using Microsoft.AspNetCore.JsonPatch.Operations;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch
|
||||
{
|
||||
/// <summary>
|
||||
/// Captures error message and the related entity and the operation that caused it.
|
||||
/// </summary>
|
||||
public class JsonPatchError
|
||||
{
|
||||
/// <summary>
|
||||
/// Initializes a new instance of <see cref="JsonPatchError"/>.
|
||||
/// </summary>
|
||||
/// <param name="affectedObject">The object that is affected by the error.</param>
|
||||
/// <param name="operation">The <see cref="Operation"/> that caused the error.</param>
|
||||
/// <param name="errorMessage">The error message.</param>
|
||||
public JsonPatchError(
|
||||
object affectedObject,
|
||||
Operation operation,
|
||||
string errorMessage)
|
||||
{
|
||||
if (errorMessage == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(errorMessage));
|
||||
}
|
||||
|
||||
AffectedObject = affectedObject;
|
||||
Operation = operation;
|
||||
ErrorMessage = errorMessage;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the object that is affected by the error.
|
||||
/// </summary>
|
||||
public object AffectedObject { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the <see cref="Operation"/> that caused the error.
|
||||
/// </summary>
|
||||
public Operation Operation { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the error message.
|
||||
/// </summary>
|
||||
public string ErrorMessage { get; }
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,17 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<Description>ASP.NET Core support for JSON PATCH.</Description>
|
||||
<TargetFramework>netstandard2.0</TargetFramework>
|
||||
<NoWarn>$(NoWarn);CS1591</NoWarn>
|
||||
<GenerateDocumentationFile>true</GenerateDocumentationFile>
|
||||
<PackageTags>aspnetcore;json;jsonpatch</PackageTags>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<Reference Include="Microsoft.CSharp" />
|
||||
<Reference Include="Newtonsoft.Json" />
|
||||
<Reference Include="Microsoft.Extensions.ClosedGenericMatcher.Sources" PrivateAssets="All" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,82 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using Microsoft.AspNetCore.JsonPatch.Adapters;
|
||||
using Newtonsoft.Json;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Operations
|
||||
{
|
||||
public class Operation : OperationBase
|
||||
{
|
||||
[JsonProperty("value")]
|
||||
public object value { get; set; }
|
||||
|
||||
public Operation()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
public Operation(string op, string path, string from, object value)
|
||||
: base(op, path, from)
|
||||
{
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
public Operation(string op, string path, string from)
|
||||
: base(op, path, from)
|
||||
{
|
||||
}
|
||||
|
||||
public void Apply(object objectToApplyTo, IObjectAdapter adapter)
|
||||
{
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
if (adapter == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(adapter));
|
||||
}
|
||||
|
||||
switch (OperationType)
|
||||
{
|
||||
case OperationType.Add:
|
||||
adapter.Add(this, objectToApplyTo);
|
||||
break;
|
||||
case OperationType.Remove:
|
||||
adapter.Remove(this, objectToApplyTo);
|
||||
break;
|
||||
case OperationType.Replace:
|
||||
adapter.Replace(this, objectToApplyTo);
|
||||
break;
|
||||
case OperationType.Move:
|
||||
adapter.Move(this, objectToApplyTo);
|
||||
break;
|
||||
case OperationType.Copy:
|
||||
adapter.Copy(this, objectToApplyTo);
|
||||
break;
|
||||
case OperationType.Test:
|
||||
if (adapter is IObjectAdapterWithTest adapterWithTest)
|
||||
{
|
||||
adapterWithTest.Test(this, objectToApplyTo);
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new NotSupportedException(Resources.TestOperationNotSupported);
|
||||
}
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
public bool ShouldSerializevalue()
|
||||
{
|
||||
return (OperationType == OperationType.Add
|
||||
|| OperationType == OperationType.Replace
|
||||
|| OperationType == OperationType.Test);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,76 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using Newtonsoft.Json;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Operations
|
||||
{
|
||||
public class OperationBase
|
||||
{
|
||||
private string _op;
|
||||
private OperationType _operationType;
|
||||
|
||||
[JsonIgnore]
|
||||
public OperationType OperationType
|
||||
{
|
||||
get
|
||||
{
|
||||
return _operationType;
|
||||
}
|
||||
}
|
||||
|
||||
[JsonProperty("path")]
|
||||
public string path { get; set; }
|
||||
|
||||
[JsonProperty("op")]
|
||||
public string op
|
||||
{
|
||||
get
|
||||
{
|
||||
return _op;
|
||||
}
|
||||
set
|
||||
{
|
||||
OperationType result;
|
||||
if (!Enum.TryParse(value, ignoreCase: true, result: out result))
|
||||
{
|
||||
result = OperationType.Invalid;
|
||||
}
|
||||
_operationType = result;
|
||||
_op = value;
|
||||
}
|
||||
}
|
||||
|
||||
[JsonProperty("from")]
|
||||
public string from { get; set; }
|
||||
|
||||
public OperationBase()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
public OperationBase(string op, string path, string from)
|
||||
{
|
||||
if (op == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(op));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
this.op = op;
|
||||
this.path = path;
|
||||
this.from = from;
|
||||
}
|
||||
|
||||
public bool ShouldSerializefrom()
|
||||
{
|
||||
return (OperationType == OperationType.Move
|
||||
|| OperationType == OperationType.Copy);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,94 @@
|
|||
// Copyright (c) .NET Foundation. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using Microsoft.AspNetCore.JsonPatch.Adapters;
|
||||
using Microsoft.AspNetCore.JsonPatch.Exceptions;
|
||||
|
||||
namespace Microsoft.AspNetCore.JsonPatch.Operations
|
||||
{
|
||||
public class Operation<TModel> : Operation where TModel : class
|
||||
{
|
||||
public Operation()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
public Operation(string op, string path, string from, object value)
|
||||
: base(op, path, from)
|
||||
{
|
||||
if (op == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(op));
|
||||
}
|
||||
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
public Operation(string op, string path, string from)
|
||||
: base(op, path, from)
|
||||
{
|
||||
if (op == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(op));
|
||||
}
|
||||
if (path == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(path));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void Apply(TModel objectToApplyTo, IObjectAdapter adapter)
|
||||
{
|
||||
if (objectToApplyTo == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(objectToApplyTo));
|
||||
}
|
||||
|
||||
if (adapter == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(adapter));
|
||||
}
|
||||
|
||||
switch (OperationType)
|
||||
{
|
||||
case OperationType.Add:
|
||||
adapter.Add(this, objectToApplyTo);
|
||||
break;
|
||||
case OperationType.Remove:
|
||||
adapter.Remove(this, objectToApplyTo);
|
||||
break;
|
||||
case OperationType.Replace:
|
||||
adapter.Replace(this, objectToApplyTo);
|
||||
break;
|
||||
case OperationType.Move:
|
||||
adapter.Move(this, objectToApplyTo);
|
||||
break;
|
||||
case OperationType.Copy:
|
||||
adapter.Copy(this, objectToApplyTo);
|
||||
break;
|
||||
case OperationType.Test:
|
||||
if (adapter is IObjectAdapterWithTest adapterWithTest)
|
||||
{
|
||||
adapterWithTest.Test(this, objectToApplyTo);
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new JsonPatchException(new JsonPatchError(objectToApplyTo, this, Resources.TestOperationNotSupported));
|
||||
}
|
||||
case OperationType.Invalid:
|
||||
throw new JsonPatchException(
|
||||
Resources.FormatInvalidJsonPatchOperation(op), innerException: null);
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue