diff --git a/.github/actions/setup-dotnets/action.yml b/.github/actions/setup-dotnets/action.yml index 442005972..b936b5f22 100644 --- a/.github/actions/setup-dotnets/action.yml +++ b/.github/actions/setup-dotnets/action.yml @@ -11,6 +11,12 @@ runs: using: "composite" steps: + - name: Setup .NET 10 (if needed) + if: ${{ contains(inputs.target_framework, '10.0') }} + uses: actions/setup-dotnet@v4 + with: + dotnet-version: '10.0.x' + - name: Setup .NET 9 (if needed) if: ${{ contains(inputs.target_framework, '9.0') }} uses: actions/setup-dotnet@v4 diff --git a/.github/workflows/auto-databaseless-tests.yml b/.github/workflows/auto-databaseless-tests.yml index 86bb73a78..af3302dc8 100644 --- a/.github/workflows/auto-databaseless-tests.yml +++ b/.github/workflows/auto-databaseless-tests.yml @@ -4,8 +4,8 @@ run-name: Core tests triggered by '${{ github.event_name }}'. Run No ${{ github. on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # extensions - 'Extensions/Xtensive.Orm.Logging.log4net/**' @@ -32,7 +32,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # extensions - 'Extensions/Xtensive.Orm.Logging.log4net/**' @@ -59,7 +59,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # extensions - 'Extensions/Xtensive.Orm.Logging.log4net/**' @@ -99,7 +99,7 @@ jobs: name: Core Tests strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] + net: [ 'net8.0', 'net10.0' ] # For security reasons we allow test runs either for pushes from the team or for pull-requests after their changes were seen and approved by someone # # push filter - to cover pushes from the team to main branch of major version @@ -110,13 +110,13 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) + && !startsWith(github.head_ref, 'master-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-independant-tests.yml@7.2 + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-independant-tests.yml@master with: build_config: Release target_framework: ${{ matrix.net }} diff --git a/.github/workflows/auto-firebird3-tests.yml b/.github/workflows/auto-firebird3-tests.yml index 69fae0dd9..35e06226e 100644 --- a/.github/workflows/auto-firebird3-tests.yml +++ b/.github/workflows/auto-firebird3-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on Firebird 3 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/firebird/do-firebird-3_0' @@ -50,7 +50,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/firebird/do-firebird-3_0' @@ -95,7 +95,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/firebird/do-firebird-3_0' @@ -164,12 +164,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: firebird30 build_config: Release diff --git a/.github/workflows/auto-firebird4-tests.yml b/.github/workflows/auto-firebird4-tests.yml index 02841c424..19e7b269c 100644 --- a/.github/workflows/auto-firebird4-tests.yml +++ b/.github/workflows/auto-firebird4-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on Firebird 4 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/firebird/do-firebird-4_0' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/firebird/do-firebird-4_0' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/firebird/do-firebird-4_0' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: firebird40 build_config: Release diff --git a/.github/workflows/auto-firebird5-tests.yml b/.github/workflows/auto-firebird5-tests.yml index 4b297c275..f22c785e4 100644 --- a/.github/workflows/auto-firebird5-tests.yml +++ b/.github/workflows/auto-firebird5-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on Firebird 5 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/firebird/do-firebird-5_0' @@ -50,7 +50,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/firebird/do-firebird-5_0' @@ -95,7 +95,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/firebird/do-firebird-5_0' @@ -164,12 +164,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: firebird50 build_config: Release diff --git a/.github/workflows/auto-mssql2017-tests.yml b/.github/workflows/auto-mssql2017-tests.yml index 4a8c850cb..45164db0a 100644 --- a/.github/workflows/auto-mssql2017-tests.yml +++ b/.github/workflows/auto-mssql2017-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MS SQL Server 2017 tests triggered by '${{ github.event_name on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/mssql/do-mssql-2017' @@ -38,7 +38,7 @@ on: - 'TestFileForBuildServerTests.txt' pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mssql/do-mssql-2017' @@ -72,7 +72,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mssql/do-mssql-2017' @@ -130,12 +130,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mssql2017 build_config: Release diff --git a/.github/workflows/auto-mssql2019-tests.yml b/.github/workflows/auto-mssql2019-tests.yml index fb4bb7a2d..c7770ba84 100644 --- a/.github/workflows/auto-mssql2019-tests.yml +++ b/.github/workflows/auto-mssql2019-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MS SQL Server 2019 tests triggered by '${{ github.event_name on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/mssql/do-mssql-2019' @@ -47,7 +47,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mssql/do-mssql-2019' @@ -89,7 +89,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mssql/do-mssql-2019' @@ -144,7 +144,7 @@ jobs: name: Tests on MS SQL Server 2019 strategy: matrix: - net: [ 'net6.0', 'net8.0' ] # only LTS + net: [ 'net8.0', 'net10.0' ] # only LTS # For security reasons we allow test runs either for pushes from the team or for pull-requests after their changes were seen and approved by someone # # push filter - to cover pushes from the team to main branch of major version @@ -155,12 +155,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mssql2019 build_config: Release diff --git a/.github/workflows/auto-mssql2022-tests.yml b/.github/workflows/auto-mssql2022-tests.yml index d4fede997..40afa6769 100644 --- a/.github/workflows/auto-mssql2022-tests.yml +++ b/.github/workflows/auto-mssql2022-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MS SQL Server 2022 tests triggered by '${{ github.event_name on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/mssql/do-mssql-2022' @@ -38,7 +38,7 @@ on: - 'TestFileForBuildServerTests.txt' pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mssql/do-mssql-2022' @@ -72,7 +72,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mssql/do-mssql-2022' @@ -130,12 +130,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mssql2022 build_config: Release diff --git a/.github/workflows/auto-mysql57-tests.yml b/.github/workflows/auto-mysql57-tests.yml index b02e74a2c..68a4106d5 100644 --- a/.github/workflows/auto-mysql57-tests.yml +++ b/.github/workflows/auto-mysql57-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MySQL 5.7 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: - 'Containers/mysql/do-mysql-5_7' - 'Containers/mysql/**.sh' @@ -49,7 +49,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: - 'Containers/mysql/do-mysql-5_7' - 'Containers/mysql/**.sh' @@ -93,7 +93,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: - 'Containers/mysql/do-mysql-5_7' - 'Containers/mysql/**.sh' @@ -150,7 +150,7 @@ jobs: name: Tests on MySQL 5.7 strategy: matrix: - net: [ 'net6.0', 'net8.0' ] # only LTS + net: [ 'net8.0', 'net10.0' ] # only LTS # For security reasons we allow test runs either for pushes from the team or for pull-requests after their changes were seen and approved by someone # # push filter - to cover pushes from the team to main branch of major version @@ -161,12 +161,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql57 build_config: Release diff --git a/.github/workflows/auto-mysql80-tests.yml b/.github/workflows/auto-mysql80-tests.yml index d62284c02..8a1df4ded 100644 --- a/.github/workflows/auto-mysql80-tests.yml +++ b/.github/workflows/auto-mysql80-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MySQL 8.0 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/mysql/do-mysql-8_0' @@ -50,7 +50,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-8_0' @@ -95,7 +95,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-8_0' @@ -153,7 +153,7 @@ jobs: name: Tests on MySQL 8.0 strategy: matrix: - net: [ 'net6.0', 'net8.0' ] # only LTS + net: [ 'net8.0', 'net10.0' ] # only LTS # For security reasons we allow test runs either for pushes from the team or for pull-requests after their changes were seen and approved by someone # # push filter - to cover pushes from the team to main branch of major version @@ -164,12 +164,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql80 build_config: Release diff --git a/.github/workflows/auto-mysql81-tests.yml b/.github/workflows/auto-mysql81-tests.yml index 244ae507c..1c189e8d2 100644 --- a/.github/workflows/auto-mysql81-tests.yml +++ b/.github/workflows/auto-mysql81-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MySQL 8.1 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/mysql/do-mysql-8_1' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-8_1' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-8_1' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql81 build_config: Release diff --git a/.github/workflows/auto-mysql82-tests.yml b/.github/workflows/auto-mysql82-tests.yml index 99723c07d..26d9e97cd 100644 --- a/.github/workflows/auto-mysql82-tests.yml +++ b/.github/workflows/auto-mysql82-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MySQL 8.2 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/mysql/do-mysql-8_2' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-8_2' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-8_2' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql82 build_config: Release diff --git a/.github/workflows/auto-mysql83-tests.yml b/.github/workflows/auto-mysql83-tests.yml index b594b20b3..e27f72678 100644 --- a/.github/workflows/auto-mysql83-tests.yml +++ b/.github/workflows/auto-mysql83-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MySQL 8.3 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/mysql/do-mysql-8_3' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-8_3' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-8_3' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql83 build_config: Release diff --git a/.github/workflows/auto-mysql84-tests.yml b/.github/workflows/auto-mysql84-tests.yml index 11a2c10ed..4ec131529 100644 --- a/.github/workflows/auto-mysql84-tests.yml +++ b/.github/workflows/auto-mysql84-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MySQL 8.4 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/mysql/do-mysql-8_4' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-8_4' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-8_4' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql84 build_config: Release diff --git a/.github/workflows/auto-mysql90-tests.yml b/.github/workflows/auto-mysql90-tests.yml index 1b3a68f27..d3c19079f 100644 --- a/.github/workflows/auto-mysql90-tests.yml +++ b/.github/workflows/auto-mysql90-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MySQL 9.0 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/mysql/do-mysql-9_0' @@ -50,7 +50,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-9_0' @@ -95,7 +95,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-9_0' @@ -153,7 +153,7 @@ jobs: name: Tests on MySQL 9.0 strategy: matrix: - net: [ 'net6.0', 'net8.0' ] # only LTS + net: [ 'net8.0', 'net10.0' ] # only LTS # For security reasons we allow test runs either for pushes from the team or for pull-requests after their changes were seen and approved by someone # # push filter - to cover pushes from the team to main branch of major version @@ -164,12 +164,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql90 build_config: Release diff --git a/.github/workflows/auto-mysql91-tests.yml b/.github/workflows/auto-mysql91-tests.yml index edf0263ae..96e4d3bbc 100644 --- a/.github/workflows/auto-mysql91-tests.yml +++ b/.github/workflows/auto-mysql91-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MySQL 9.1 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/mysql/do-mysql-9_1' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-9_1' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-9_1' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql91 build_config: Release diff --git a/.github/workflows/auto-mysql92-tests.yml b/.github/workflows/auto-mysql92-tests.yml index f0998dbee..366616f75 100644 --- a/.github/workflows/auto-mysql92-tests.yml +++ b/.github/workflows/auto-mysql92-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MySQL 9.2 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/mysql/do-mysql-9_2' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-9_2' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-9_2' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql92 build_config: Release diff --git a/.github/workflows/auto-mysql93-tests.yml b/.github/workflows/auto-mysql93-tests.yml index 940b3798d..1ca934e79 100644 --- a/.github/workflows/auto-mysql93-tests.yml +++ b/.github/workflows/auto-mysql93-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on MySQL 9.3 tests triggered by '${{ github.event_name }}'. Run on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/mysql/do-mysql-9_3' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-9_3' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/mysql/do-mysql-9_3' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql93 build_config: Release diff --git a/.github/workflows/auto-pgsql110-tests.yml b/.github/workflows/auto-pgsql110-tests.yml index fbf8f3a76..7d139f15b 100644 --- a/.github/workflows/auto-pgsql110-tests.yml +++ b/.github/workflows/auto-pgsql110-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on PostgreSQL 11.0 tests triggered by '${{ github.event_name }}' on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/postgres/do-postgres-11' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-11' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-11' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql110 build_config: Release diff --git a/.github/workflows/auto-pgsql120-tests.yml b/.github/workflows/auto-pgsql120-tests.yml index 56c22fe5c..88eeebc02 100644 --- a/.github/workflows/auto-pgsql120-tests.yml +++ b/.github/workflows/auto-pgsql120-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on PostgreSQL 12.0 tests triggered by '${{ github.event_name }}' on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/postgres/do-postgres-12' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-12' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-12' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql120 build_config: Release diff --git a/.github/workflows/auto-pgsql130-tests.yml b/.github/workflows/auto-pgsql130-tests.yml index c2d9ce307..ad6934f86 100644 --- a/.github/workflows/auto-pgsql130-tests.yml +++ b/.github/workflows/auto-pgsql130-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on PostgreSQL 13.0 tests triggered by '${{ github.event_name }}' on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/postgres/do-postgres-13' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-13' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-13' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql130 build_config: Release diff --git a/.github/workflows/auto-pgsql140-tests.yml b/.github/workflows/auto-pgsql140-tests.yml index e236b14b8..2caeadc9b 100644 --- a/.github/workflows/auto-pgsql140-tests.yml +++ b/.github/workflows/auto-pgsql140-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on PostgreSQL 14.0 tests triggered by '${{ github.event_name }}' on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/postgres/do-postgres-14' @@ -47,7 +47,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-14' @@ -89,7 +89,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-14' @@ -144,7 +144,7 @@ jobs: name: Tests on PostgreSQL 14.0 strategy: matrix: - net: [ 'net6.0', 'net8.0' ] # only LTS + net: [ 'net8.0', 'net10.0' ] # only LTS # For security reasons we allow test runs either for pushes from the team or for pull-requests after their changes were seen and approved by someone # # push filter - to cover pushes from the team to main branch of major version @@ -155,12 +155,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql140 build_config: Release diff --git a/.github/workflows/auto-pgsql150-tests.yml b/.github/workflows/auto-pgsql150-tests.yml index c9c21b936..55959a4a9 100644 --- a/.github/workflows/auto-pgsql150-tests.yml +++ b/.github/workflows/auto-pgsql150-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on PostgreSQL 15.0 tests triggered by '${{ github.event_name }}' on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/postgres/do-postgres-15' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-15' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-15' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql150 build_config: Release diff --git a/.github/workflows/auto-pgsql160-tests.yml b/.github/workflows/auto-pgsql160-tests.yml index 2959e1636..08bf938da 100644 --- a/.github/workflows/auto-pgsql160-tests.yml +++ b/.github/workflows/auto-pgsql160-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on PostgreSQL 16.0 tests triggered by '${{ github.event_name }}' on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/postgres/do-postgres-16' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-16' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-16' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql160 build_config: Release diff --git a/.github/workflows/auto-pgsql170-tests.yml b/.github/workflows/auto-pgsql170-tests.yml index 7f70ab682..df7f75466 100644 --- a/.github/workflows/auto-pgsql170-tests.yml +++ b/.github/workflows/auto-pgsql170-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on PostgreSQL 17.0 tests triggered by '${{ github.event_name }}' on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/postgres/do-postgres-17' @@ -50,7 +50,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-17' @@ -95,7 +95,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-17' @@ -153,7 +153,7 @@ jobs: name: Tests on PostgreSQL 17.0 strategy: matrix: - net: [ 'net6.0', 'net8.0' ] # only LTS + net: [ 'net8.0', 'net10.0' ] # only LTS # For security reasons we allow test runs either for pushes from the team or for pull-requests after their changes were seen and approved by someone # # push filter - to cover pushes from the team to main branch of major version @@ -164,12 +164,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql170 build_config: Release diff --git a/.github/workflows/auto-pgsql180-tests.yml b/.github/workflows/auto-pgsql180-tests.yml index 25fbaed0b..089938a4a 100644 --- a/.github/workflows/auto-pgsql180-tests.yml +++ b/.github/workflows/auto-pgsql180-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on PostgreSQL 18.0 tests triggered by '${{ github.event_name }}' on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # containers - 'Containers/postgres/do-postgres-18' @@ -39,7 +39,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-18' @@ -73,7 +73,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # containers - 'Containers/postgres/do-postgres-18' @@ -131,12 +131,12 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + && !startsWith(github.head_ref, 'master-')) + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql180 build_config: Release diff --git a/.github/workflows/auto-sqlite3-tests.yml b/.github/workflows/auto-sqlite3-tests.yml index 35c0c8622..eae392e04 100644 --- a/.github/workflows/auto-sqlite3-tests.yml +++ b/.github/workflows/auto-sqlite3-tests.yml @@ -4,8 +4,8 @@ run-name: Tests on SQLite 3 tests triggered by '${{ github.event_name }}'. Run N on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths: # extensions code only - 'Extensions/**' @@ -46,7 +46,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths: # extensions code only - 'Extensions/**' @@ -87,7 +87,7 @@ on: pull_request_review: branches: - - '7.2' + - 'master' paths: # extensions code only - 'Extensions/**' @@ -142,7 +142,7 @@ jobs: name: Tests on SQLite 3 strategy: matrix: - net: [ 'net6.0', 'net8.0' ] # only LTS + net: [ 'net8.0', 'net10.0' ] # only LTS # For security reasons we allow test runs either for pushes from the team or for pull-requests after their changes were seen and approved by someone # # push filter - to cover pushes from the team to main branch of major version @@ -153,13 +153,13 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request_review' && github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name - && startsWith(github.event.pull_request.base.ref, '7.2') + && startsWith(github.event.pull_request.base.ref, 'master') && github.event.review.state == 'approved') || (github.event_name == 'pull_request' && github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name - && !startsWith(github.head_ref, '7.2-')) + && !startsWith(github.head_ref, 'master-')) - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: sqlite3 build_config: Release diff --git a/.github/workflows/autobuild-on-push-and-pr.yml b/.github/workflows/autobuild-on-push-and-pr.yml index 32b2b77fd..0007163c9 100644 --- a/.github/workflows/autobuild-on-push-and-pr.yml +++ b/.github/workflows/autobuild-on-push-and-pr.yml @@ -4,8 +4,8 @@ run-name: Auto-build run on '${{ github.event_name }}'. Build ${{ github.run_num on: push: branches: - - '7.2' - - '7.2-*' + - 'master' + - 'master-*' paths-ignore: - '.github/**' - 'ChangeLog/**' @@ -21,7 +21,7 @@ on: pull_request: branches: - - '7.2' + - 'master' paths-ignore: - '.github/**' - 'ChangeLog/**' @@ -59,7 +59,7 @@ jobs: github.event_name == 'push' || (github.event_name == 'pull_request' && (github.event.pull_request.head.repo.full_name != github.event.pull_request.base.repo.full_name || - (github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name && !startsWith(github.head_ref, '7.2-')))) + (github.event.pull_request.head.repo.full_name == github.event.pull_request.base.repo.full_name && !startsWith(github.head_ref, 'master-')))) steps: - name: Checkout repo diff --git a/.github/workflows/dispatched-firebird-tests.yml b/.github/workflows/dispatched-firebird-tests.yml index 9855039b0..b5df78699 100644 --- a/.github/workflows/dispatched-firebird-tests.yml +++ b/.github/workflows/dispatched-firebird-tests.yml @@ -45,8 +45,8 @@ jobs: if: ${{ inputs.firebird30 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: firebird30 build_config: Release @@ -65,8 +65,8 @@ jobs: if: ${{ inputs.firebird40 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: firebird40 build_config: Release @@ -85,8 +85,8 @@ jobs: if: ${{ inputs.firebird50 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: firebird50 build_config: Release diff --git a/.github/workflows/dispatched-mssql-tests.yml b/.github/workflows/dispatched-mssql-tests.yml index 4f038e7ed..e6dfe586d 100644 --- a/.github/workflows/dispatched-mssql-tests.yml +++ b/.github/workflows/dispatched-mssql-tests.yml @@ -45,8 +45,8 @@ jobs: if: ${{ inputs.mssql2017 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mssql2017 build_config: Release @@ -65,8 +65,8 @@ jobs: if: ${{ inputs.mssql2019 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mssql2019 build_config: Release @@ -85,8 +85,8 @@ jobs: if: ${{ inputs.mssql2022 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mssql2022 build_config: Release diff --git a/.github/workflows/dispatched-mysql5-tests.yml b/.github/workflows/dispatched-mysql5-tests.yml index 74caee8a9..7671204ed 100644 --- a/.github/workflows/dispatched-mysql5-tests.yml +++ b/.github/workflows/dispatched-mysql5-tests.yml @@ -13,16 +13,6 @@ on: type: boolean default: false required: true - mysql55: - description: 'MySQL 5.5' - type: boolean - default: false - required: true - mysql56: - description: 'MySQL 5.6' - type: boolean - default: true - required: true mysql57: description: 'MySQL 5.7' type: boolean @@ -40,53 +30,13 @@ permissions: checks: write jobs: - test_on_mysql55: - name: Tests on MySQL 5.5 - if: ${{ inputs.mysql55 }} - strategy: - matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 - with: - storage: mysql55 - build_config: Release - target_framework: ${{ matrix.net }} - specific_sha: ${{ inputs.specific_sha }} - show_all_fails: ${{ fromJSON(inputs.show_all_fails) }} - test_output_verbosity: minimal - test_run_timeout: 20 - run_main: true - run_sql: true - run_extensions: true - publish_raw_results: true - - test_on_mysql56: - name: Tests on MySQL 5.6 - if: ${{ inputs.mysql56 }} - strategy: - matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 - with: - storage: mysql56 - build_config: Release - target_framework: ${{ matrix.net }} - specific_sha: ${{ inputs.specific_sha }} - show_all_fails: ${{ fromJSON(inputs.show_all_fails) }} - test_output_verbosity: minimal - test_run_timeout: 30 - run_main: true - run_sql: true - run_extensions: true - publish_raw_results: true - test_on_mysql57: name: Tests on MySQL 5.7 if: ${{ inputs.mysql57 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql57 build_config: Release diff --git a/.github/workflows/dispatched-mysql8-tests.yml b/.github/workflows/dispatched-mysql8-tests.yml index 57c3da32e..7d91d434d 100644 --- a/.github/workflows/dispatched-mysql8-tests.yml +++ b/.github/workflows/dispatched-mysql8-tests.yml @@ -55,8 +55,8 @@ jobs: if: ${{ inputs.mysql80 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql80 build_config: Release @@ -75,8 +75,8 @@ jobs: if: ${{ inputs.mysql81 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql81 build_config: Release @@ -95,8 +95,8 @@ jobs: if: ${{ inputs.mysql82 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql82 build_config: Release @@ -115,8 +115,8 @@ jobs: if: ${{ inputs.mysql83 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql83 build_config: Release @@ -135,8 +135,8 @@ jobs: if: ${{ inputs.mysql84 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql84 build_config: Release diff --git a/.github/workflows/dispatched-mysql9-tests.yml b/.github/workflows/dispatched-mysql9-tests.yml index 5b0e50f9f..608cf2f9a 100644 --- a/.github/workflows/dispatched-mysql9-tests.yml +++ b/.github/workflows/dispatched-mysql9-tests.yml @@ -50,8 +50,8 @@ jobs: if: ${{ inputs.mysql90 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql90 build_config: Release @@ -70,8 +70,8 @@ jobs: if: ${{ inputs.mysql91 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql91 build_config: Release @@ -90,8 +90,8 @@ jobs: if: ${{ inputs.mysql92 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql92 build_config: Release @@ -110,8 +110,8 @@ jobs: if: ${{ inputs.mysql93 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: mysql93 build_config: Release diff --git a/.github/workflows/dispatched-pgsql10-tests.yml b/.github/workflows/dispatched-pgsql10-tests.yml index 0521e6205..eb970dc91 100644 --- a/.github/workflows/dispatched-pgsql10-tests.yml +++ b/.github/workflows/dispatched-pgsql10-tests.yml @@ -14,12 +14,6 @@ on: default: false required: true # EOL - moved to addtional versions - #pgsql100: - # description: 'PostgreSQL 10' - # type: boolean - # default: false - # required: true - # EOL - moved to addtional versions #pgsql110: # description: 'PostgreSQL 11' # type: boolean @@ -84,33 +78,13 @@ permissions: checks: write jobs: - test_on_pgsql100: - name: Tests on PostgreSQL 10 - if: ${{ contains(inputs.additional_versions, 'pgsql100') }} - strategy: - matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 - with: - storage: pgsql100 - build_config: Release - target_framework: ${{ matrix.net }} - specific_sha: ${{ inputs.specific_sha }} - show_all_fails: ${{ fromJSON(inputs.show_all_fails) }} - test_output_verbosity: minimal - test_run_timeout: 30 - run_main: true - run_sql: true - run_extensions: true - publish_raw_results: true - test_on_pgsql110: name: Tests on PostgreSQL 11 if: ${{ contains(inputs.additional_versions, 'pgsql110') }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql110 build_config: Release @@ -129,8 +103,8 @@ jobs: if: ${{ contains(inputs.additional_versions, 'pgsql120') }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql120 build_config: Release @@ -150,8 +124,8 @@ jobs: strategy: fail-fast: false matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql130 build_config: Release @@ -170,8 +144,8 @@ jobs: if: ${{ inputs.pgsql140 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql140 build_config: Release @@ -190,8 +164,8 @@ jobs: if: ${{ inputs.pgsql150 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql150 build_config: Release @@ -210,8 +184,8 @@ jobs: if: ${{ inputs.pgsql160 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql160 build_config: Release @@ -230,8 +204,8 @@ jobs: if: ${{ inputs.pgsql170 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql170 build_config: Release @@ -250,8 +224,8 @@ jobs: if: ${{ inputs.pgsql180 }} strategy: matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + net: [ 'net8.0', 'net10.0' ] + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: pgsql180 build_config: Release @@ -270,8 +244,8 @@ jobs: # if: ${{ inputs.pgsql190 }} # strategy: # matrix: - # net: [ 'net6.0', 'net7.0', 'net8.0' ] - # uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + # net: [ 'net8.0', 'net10.0' ] + # uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master # with: # storage: pgsql190 # build_config: Release diff --git a/.github/workflows/dispatched-pgsql9-tests.yml b/.github/workflows/dispatched-pgsql9-tests.yml deleted file mode 100644 index 3dd169712..000000000 --- a/.github/workflows/dispatched-pgsql9-tests.yml +++ /dev/null @@ -1,118 +0,0 @@ -name: 🛠🐘 PostgreSQL 9.x tests -run-name: Run database tests on PostgreSQL on dispatch. Run No ${{ github.run_number }}. -on: - workflow_dispatch: - inputs: - specific_sha: - description: 'Commit SHA to checkout' - required: false - default: '' - type: string - show_all_fails: - description: 'No mute tests' - type: boolean - default: false - required: true - pgsql91: - description: 'PostgreSQL 9.1' - type: boolean - default: false - required: true - pgsql92: - description: 'PostgreSQL 9.2' - type: boolean - default: false - required: true - pgsql96: - description: 'PostgreSQL 9.6' - type: boolean - default: true - required: true - -# new commits with the same key will cancel previously run workflows -concurrency: - group: ${{ github.workflow }}-${{ github.ref }} - cancel-in-progress: true - -permissions: - contents: read - actions: read - checks: write - -jobs: - # requires special docker registry because the image is based on schema 1, which is depricated - #test_on_pgsql90: - # name: Tests on PostgreSQL 9.0 - # if: ${{ inputs.pgsql90 }} - # uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 - # with: - # storage: pgsql90 - # build_config: Release - # target_frameworks: net6.0 - # specific_sha: ${{ inputs.specific_sha }} - # test_output_verbosity: minimal - # test_run_timeout: 70 - # run_main: true - # run_sql: true - # run_extensions: true - # publish_raw_results: false - - test_on_pgsql91: - name: Tests on PostgreSQL 9.1 - if: ${{ inputs.pgsql91 }} - strategy: - matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 - with: - storage: pgsql91 - build_config: Release - target_framework: ${{ matrix.net }} - specific_sha: ${{ inputs.specific_sha }} - show_all_fails: ${{ fromJSON(inputs.show_all_fails) }} - test_output_verbosity: minimal - test_run_timeout: 30 - run_main: true - run_sql: true - run_extensions: true - publish_raw_results: true - - test_on_pgsql92: - name: Tests on PostgreSQL 9.2 - if: ${{ inputs.pgsql92 }} - strategy: - matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 - with: - storage: pgsql92 - build_config: Release - target_framework: ${{ matrix.net }} - specific_sha: ${{ inputs.specific_sha }} - show_all_fails: ${{ fromJSON(inputs.show_all_fails) }} - test_output_verbosity: minimal - test_run_timeout: 30 - run_main: true - run_sql: true - run_extensions: true - publish_raw_results: true - - test_on_pgsql96: - name: Tests on PostgreSQL 9.6 - if: ${{ inputs.pgsql96 }} - strategy: - matrix: - net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 - with: - storage: pgsql96 - build_config: Release - target_framework: ${{ matrix.net }} - specific_sha: ${{ inputs.specific_sha }} - show_all_fails: ${{ fromJSON(inputs.show_all_fails) }} - test_output_verbosity: minimal - test_run_timeout: 30 - run_main: true - run_sql: true - run_extensions: true - publish_raw_results: true diff --git a/.github/workflows/dispatched-sqlite-tests.yml b/.github/workflows/dispatched-sqlite-tests.yml index c0a0df839..6feeb8395 100644 --- a/.github/workflows/dispatched-sqlite-tests.yml +++ b/.github/workflows/dispatched-sqlite-tests.yml @@ -36,7 +36,7 @@ jobs: strategy: matrix: net: [ 'net6.0', 'net7.0', 'net8.0' ] - uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@7.2 + uses: DataObjects-NET/dataobjects-net/.github/workflows/reusable-storage-dependant-tests.yml@master with: storage: sqlite3 build_config: Release diff --git a/ChangeLog/7.2.1-Z_Final.txt b/ChangeLog/7.2.1-Z_Final.txt new file mode 100644 index 000000000..bfa4e69ad --- /dev/null +++ b/ChangeLog/7.2.1-Z_Final.txt @@ -0,0 +1,10 @@ +[main] Added Query.SingleAsync()/SingleOrDefaultAsync and QueryEndpoint.SingleAsync()/SingleOrDefaultAsync methods +[main] Addressed issue of not disposing IAsyncEnumerator which caused query being open +[main] Addressed issue of overwriting exception on attempt to rollback the transaction of Domain upgrade if commit operation failed +[main] LeftJoin extension marked as Obsolete to prepare movement to .NET 10, LeftJoinEx provided as substitution +[main] IPriorityQueue interface became Obsolete +[main] EnumerableUtils.One() marked as Obsolete +[main] Performance and memory usage improvements +[main] Fixed certain issues connected with SerializableExpressions deserialization +[postgresql] Update Npgsql to 9.0.4 +[weaver] Updated Mono.Cecil package to v0.11.6, which resolves certain issues of unsynced pdb files diff --git a/ChangeLog/7.2.1-dev.txt b/ChangeLog/7.2.1-dev.txt deleted file mode 100644 index eea024a7b..000000000 --- a/ChangeLog/7.2.1-dev.txt +++ /dev/null @@ -1 +0,0 @@ -[main] Added Query.SingleAsync()/SingleOrDefaultAsync and QueryEndpoint.SingleAsync()/SingleOrDefaultAsync methods \ No newline at end of file diff --git a/Extensions/Xtensive.Orm.Security/Cryptography/MD5HashingService.cs b/Extensions/Xtensive.Orm.Security/Cryptography/MD5HashingService.cs index ff29af7e8..26d8766d8 100644 --- a/Extensions/Xtensive.Orm.Security/Cryptography/MD5HashingService.cs +++ b/Extensions/Xtensive.Orm.Security/Cryptography/MD5HashingService.cs @@ -17,10 +17,7 @@ namespace Xtensive.Orm.Security.Cryptography public class MD5HashingService : GenericHashingService { /// -#pragma warning disable SYSLIB0021 // Type or member is obsolete - // direct creation is more efficient than MD5.Create() - protected override HashAlgorithm GetHashAlgorithm() => new MD5CryptoServiceProvider(); -#pragma warning restore SYSLIB0021 // Type or member is obsolete + protected override HashAlgorithm GetHashAlgorithm() => MD5.Create(); /// protected override int HashSizeInBytes => MD5.HashSizeInBytes; diff --git a/Extensions/Xtensive.Orm.Security/Cryptography/SHA1HashingService.cs b/Extensions/Xtensive.Orm.Security/Cryptography/SHA1HashingService.cs index 7a7488fec..70bedcb2a 100644 --- a/Extensions/Xtensive.Orm.Security/Cryptography/SHA1HashingService.cs +++ b/Extensions/Xtensive.Orm.Security/Cryptography/SHA1HashingService.cs @@ -16,13 +16,10 @@ namespace Xtensive.Orm.Security.Cryptography public class SHA1HashingService : GenericHashingService { /// -#pragma warning disable SYSLIB0021 // Type or member is obsolete - // direct creation is more efficient than SHA1.Create() - protected override HashAlgorithm GetHashAlgorithm() => new SHA1Managed(); -#pragma warning restore SYSLIB0021 // Type or member is obsolete - - /// - protected override int HashSizeInBytes => SHA1.HashSizeInBytes; + protected override int HashSizeInBytes => 20; + + /// + protected override HashAlgorithm GetHashAlgorithm() => SHA1.Create(); /// /// Initializes a new instance of the class. diff --git a/Extensions/Xtensive.Orm.Security/Cryptography/SHA256HashingService.cs b/Extensions/Xtensive.Orm.Security/Cryptography/SHA256HashingService.cs index 12af5aa14..ced4034d6 100644 --- a/Extensions/Xtensive.Orm.Security/Cryptography/SHA256HashingService.cs +++ b/Extensions/Xtensive.Orm.Security/Cryptography/SHA256HashingService.cs @@ -16,10 +16,7 @@ namespace Xtensive.Orm.Security.Cryptography public class SHA256HashingService : GenericHashingService { /// -#pragma warning disable SYSLIB0021 // Type or member is obsolete - // direct creation is more efficient than SHA256.Create() - protected override HashAlgorithm GetHashAlgorithm() => new SHA256Managed(); -#pragma warning restore SYSLIB0021 // Type or member is obsolete + protected override HashAlgorithm GetHashAlgorithm() => SHA256.Create(); /// protected override int HashSizeInBytes => SHA256.HashSizeInBytes; diff --git a/Extensions/Xtensive.Orm.Security/Cryptography/SHA384HashingService.cs b/Extensions/Xtensive.Orm.Security/Cryptography/SHA384HashingService.cs index cde63ebb6..83aceb110 100644 --- a/Extensions/Xtensive.Orm.Security/Cryptography/SHA384HashingService.cs +++ b/Extensions/Xtensive.Orm.Security/Cryptography/SHA384HashingService.cs @@ -16,10 +16,7 @@ namespace Xtensive.Orm.Security.Cryptography public class SHA384HashingService : GenericHashingService { /// -#pragma warning disable SYSLIB0021 // Type or member is obsolete - // direct creation is more efficient than SHA384.Create() - protected override HashAlgorithm GetHashAlgorithm() => new SHA384Managed(); -#pragma warning restore SYSLIB0021 // Type or member is obsolete + protected override HashAlgorithm GetHashAlgorithm() => SHA384.Create(); /// protected override int HashSizeInBytes => SHA384.HashSizeInBytes; diff --git a/Extensions/Xtensive.Orm.Security/Cryptography/SHA512HashingService.cs b/Extensions/Xtensive.Orm.Security/Cryptography/SHA512HashingService.cs index d67b05c44..0ef1be03d 100644 --- a/Extensions/Xtensive.Orm.Security/Cryptography/SHA512HashingService.cs +++ b/Extensions/Xtensive.Orm.Security/Cryptography/SHA512HashingService.cs @@ -16,10 +16,7 @@ namespace Xtensive.Orm.Security.Cryptography public class SHA512HashingService : GenericHashingService { /// -#pragma warning disable SYSLIB0021 // Type or member is obsolete - // direct creation is more efficient than SHA512.Create() - protected override HashAlgorithm GetHashAlgorithm() => new SHA512Managed(); -#pragma warning restore SYSLIB0021 // Type or member is obsolete + protected override HashAlgorithm GetHashAlgorithm() => SHA512.Create(); /// protected override int HashSizeInBytes => SHA512.HashSizeInBytes; diff --git a/Extensions/Xtensive.Orm.Security/ImpersonationContext.cs b/Extensions/Xtensive.Orm.Security/ImpersonationContext.cs index 6e44b33f1..3101fd7f2 100644 --- a/Extensions/Xtensive.Orm.Security/ImpersonationContext.cs +++ b/Extensions/Xtensive.Orm.Security/ImpersonationContext.cs @@ -1,4 +1,4 @@ -using System; +using System; using Xtensive.Core; namespace Xtensive.Orm.Security diff --git a/Orm/Xtensive.Orm.PostgreSql/Sql.Drivers.PostgreSql/v11_0/Extractor.cs b/Orm/Xtensive.Orm.PostgreSql/Sql.Drivers.PostgreSql/v11_0/Extractor.cs index 0169acf70..cce8cbbeb 100644 --- a/Orm/Xtensive.Orm.PostgreSql/Sql.Drivers.PostgreSql/v11_0/Extractor.cs +++ b/Orm/Xtensive.Orm.PostgreSql/Sql.Drivers.PostgreSql/v11_0/Extractor.cs @@ -624,7 +624,7 @@ protected virtual ISqlCompileUnit BuildExtractSchemaContentsQuery(ExtractionCont var relationsTable = PgClass; var tablespacesTable = PgTablespace; - var join = relationsTable.LeftOuterJoin(tablespacesTable, + var join = relationsTable.LeftJoinEx(tablespacesTable, tablespacesTable["oid"] == relationsTable["reltablespace"]); var select = SqlDml.Select(join); select.Where = relationsTable["relowner"] == context.CurrentUserIdentifier @@ -735,7 +735,7 @@ protected virtual ISqlCompileUnit BuildExtractTableAndViewColumnsQuery(Extractio var typesTable = PgType; var select = SqlDml.Select(columnsTable - .LeftOuterJoin(defaultValuesTable, + .LeftJoinEx(defaultValuesTable, columnsTable["attrelid"] == defaultValuesTable["adrelid"] && columnsTable["attnum"] == defaultValuesTable["adnum"]) .InnerJoin(typesTable, typesTable["oid"] == columnsTable["atttypid"])); @@ -889,7 +889,7 @@ protected virtual ISqlCompileUnit BuildExtractTableIndexesQuery(ExtractionContex //not automatically created indexes of our tables var select = SqlDml.Select(indexTable .InnerJoin(relationsTable, relationsTable["oid"] == indexTable["indexrelid"]) - .LeftOuterJoin(tableSpacesTable, tableSpacesTable["oid"] == relationsTable["reltablespace"])); + .LeftJoinEx(tableSpacesTable, tableSpacesTable["oid"] == relationsTable["reltablespace"])); select.Where = SqlDml.In(indexTable["indrelid"], CreateOidRow(tableMap.Keys)) && !SqlDml.Exists(subSelect); select.Columns.Add(indexTable["indrelid"]); select.Columns.Add(indexTable["indexrelid"]); diff --git a/Orm/Xtensive.Orm.PostgreSql/Sql.Drivers.PostgreSql/v12_0/Extractor.cs b/Orm/Xtensive.Orm.PostgreSql/Sql.Drivers.PostgreSql/v12_0/Extractor.cs index a22674cb0..c02cbb256 100644 --- a/Orm/Xtensive.Orm.PostgreSql/Sql.Drivers.PostgreSql/v12_0/Extractor.cs +++ b/Orm/Xtensive.Orm.PostgreSql/Sql.Drivers.PostgreSql/v12_0/Extractor.cs @@ -33,7 +33,7 @@ protected override ISqlCompileUnit BuildExtractTableAndViewColumnsQuery(Extracti var typesTable = PgType; var select = SqlDml.Select(columnsTable - .LeftOuterJoin(defaultValuesTable, + .LeftJoinEx(defaultValuesTable, columnsTable["attrelid"] == defaultValuesTable["adrelid"] && columnsTable["attnum"] == defaultValuesTable["adnum"]) .InnerJoin(typesTable, typesTable["oid"] == columnsTable["atttypid"])); @@ -103,7 +103,7 @@ protected override ISqlCompileUnit BuildExtractTableIndexesQuery(ExtractionConte //not automatically created indexes of our tables var select = SqlDml.Select(indexTable .InnerJoin(relationsTable, relationsTable["oid"] == indexTable["indexrelid"]) - .LeftOuterJoin(tableSpacesTable, tableSpacesTable["oid"] == relationsTable["reltablespace"])); + .LeftJoinEx(tableSpacesTable, tableSpacesTable["oid"] == relationsTable["reltablespace"])); select.Where = SqlDml.In(indexTable["indrelid"], CreateOidRow(tableMap.Keys)) && !SqlDml.Exists(subSelect); select.Columns.Add(indexTable["indrelid"]); select.Columns.Add(indexTable["indexrelid"]); diff --git a/Orm/Xtensive.Orm.SqlServer/Sql.Drivers.SqlServer/v13/Extractor.cs b/Orm/Xtensive.Orm.SqlServer/Sql.Drivers.SqlServer/v13/Extractor.cs index 9f5b4e5f3..e03c41382 100644 --- a/Orm/Xtensive.Orm.SqlServer/Sql.Drivers.SqlServer/v13/Extractor.cs +++ b/Orm/Xtensive.Orm.SqlServer/Sql.Drivers.SqlServer/v13/Extractor.cs @@ -96,7 +96,7 @@ public override async Task ExtractSchemesAsync( string catalogName, string[] schemaNames, CancellationToken token = default) { var context = CreateContext(catalogName, schemaNames); - await ExtractCatalogContentsAsync(context, token).ConfigureAwait(false); + await ExtractCatalogContentsAsync(context, token).ConfigureAwaitFalse(); return context.Catalog; } @@ -115,15 +115,15 @@ protected virtual void ExtractCatalogContents(ExtractionContext context) protected virtual async Task ExtractCatalogContentsAsync(ExtractionContext context, CancellationToken token) { - await ExtractSchemasAsync(context, token).ConfigureAwait(false); + await ExtractSchemasAsync(context, token).ConfigureAwaitFalse(); RegisterReplacements(context); - await ExtractTypesAsync(context, token).ConfigureAwait(false); - await ExtractTablesAndViewsAsync(context, token).ConfigureAwait(false); - await ExtractColumnsAsync(context, token).ConfigureAwait(false); - await ExtractIndexesAsync(context, token).ConfigureAwait(false); - await ExtractForeignKeysAsync(context, token).ConfigureAwait(false); - await ExtractFulltextIndexesAsync(context, token).ConfigureAwait(false); - await ExtractSequencesAsync(context, token).ConfigureAwait(false); + await ExtractTypesAsync(context, token).ConfigureAwaitFalse(); + await ExtractTablesAndViewsAsync(context, token).ConfigureAwaitFalse(); + await ExtractColumnsAsync(context, token).ConfigureAwaitFalse(); + await ExtractIndexesAsync(context, token).ConfigureAwaitFalse(); + await ExtractForeignKeysAsync(context, token).ConfigureAwaitFalse(); + await ExtractFulltextIndexesAsync(context, token).ConfigureAwaitFalse(); + await ExtractSequencesAsync(context, token).ConfigureAwaitFalse(); } protected virtual void RegisterReplacements(ExtractionContext context) @@ -162,10 +162,10 @@ private async Task ExtractSchemasAsync(ExtractionContext context, CancellationTo var query = BuildExtractSchemasQuery(context); var cmd = Connection.CreateCommand(query); - await using (cmd.ConfigureAwait(false)) { - var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwait(false); - await using (reader.ConfigureAwait(false)) { - while (await reader.ReadAsync(token).ConfigureAwait(false)) { + await using (cmd.ConfigureAwaitFalse()) { + var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwaitFalse(); + await using (reader.ConfigureAwaitFalse()) { + while (await reader.ReadAsync(token).ConfigureAwaitFalse()) { ReadSchemaData(reader, context); } } @@ -215,10 +215,10 @@ private async Task ExtractTypesAsync(ExtractionContext context, CancellationToke var query = BuildExtractTypesQuery(context); var command = Connection.CreateCommand(query); - await using (command.ConfigureAwait(false)) { - var reader = await command.ExecuteReaderAsync(token).ConfigureAwait(false); - await using (reader.ConfigureAwait(false)) { - while (await reader.ReadAsync(token).ConfigureAwait(false)) { + await using (command.ConfigureAwaitFalse()) { + var reader = await command.ExecuteReaderAsync(token).ConfigureAwaitFalse(); + await using (reader.ConfigureAwaitFalse()) { + while (await reader.ReadAsync(token).ConfigureAwaitFalse()) { ReadTypeData(reader, context); } } @@ -285,10 +285,10 @@ private async Task ExtractTablesAndViewsAsync(ExtractionContext context, Cancell var query = BuildExtractTablesAndViewsQuery(context); var cmd = Connection.CreateCommand(query); - await using (cmd.ConfigureAwait(false)) { - var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwait(false); - await using (reader.ConfigureAwait(false)) { - while (await reader.ReadAsync(token).ConfigureAwait(false)) { + await using (cmd.ConfigureAwaitFalse()) { + var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwaitFalse(); + await using (reader.ConfigureAwaitFalse()) { + while (await reader.ReadAsync(token).ConfigureAwaitFalse()) { ReadTableOrViewData(reader, context); } } @@ -371,10 +371,10 @@ private async Task ExtractColumnsAsync(ExtractionContext context, CancellationTo var currentTableId = 0; var cmd = Connection.CreateCommand(query); ColumnResolver columnResolver = null; - await using (cmd.ConfigureAwait(false)) { - var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwait(false); - await using (reader.ConfigureAwait(false)) { - while (await reader.ReadAsync(token).ConfigureAwait(false)) { + await using (cmd.ConfigureAwaitFalse()) { + var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwaitFalse(); + await using (reader.ConfigureAwaitFalse()) { + while (await reader.ReadAsync(token).ConfigureAwaitFalse()) { ReadColumnData(context, reader, ref currentTableId, ref columnResolver); } } @@ -383,10 +383,10 @@ private async Task ExtractColumnsAsync(ExtractionContext context, CancellationTo query = BuildExtractIdentityColumnsQuery(context); cmd = Connection.CreateCommand(query); - await using (cmd.ConfigureAwait(false)) { - var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwait(false); - await using (reader.ConfigureAwait(false)) { - while (await reader.ReadAsync(token).ConfigureAwait(false)) { + await using (cmd.ConfigureAwaitFalse()) { + var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwaitFalse(); + await using (reader.ConfigureAwaitFalse()) { + while (await reader.ReadAsync(token).ConfigureAwaitFalse()) { ReadIdentityColumnData(reader, context); } } @@ -625,10 +625,10 @@ private async Task ExtractIndexesAsync(ExtractionContext context, CancellationTo PrimaryKey primaryKey = null; UniqueConstraint uniqueConstraint = null; var cmd = Connection.CreateCommand(query); - await using (cmd.ConfigureAwait(false)) { - var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwait(false); - await using (reader.ConfigureAwait(false)) { - while (await reader.ReadAsync(token).ConfigureAwait(false)) { + await using (cmd.ConfigureAwaitFalse()) { + var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwaitFalse(); + await using (reader.ConfigureAwaitFalse()) { + while (await reader.ReadAsync(token).ConfigureAwaitFalse()) { ReadIndexColumnData(reader, context, ref tableId, spatialIndexType, ref primaryKey, ref uniqueConstraint, ref index, ref table); } @@ -736,10 +736,10 @@ private async Task ExtractForeignKeysAsync(ExtractionContext context, Cancellati ColumnResolver referencedTable = null; ForeignKey foreignKey = null; var cmd = Connection.CreateCommand(query); - await using (cmd.ConfigureAwait(false)) { - var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwait(false); - await using (reader.ConfigureAwait(false)) { - while (await reader.ReadAsync(token).ConfigureAwait(false)) { + await using (cmd.ConfigureAwaitFalse()) { + var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwaitFalse(); + await using (reader.ConfigureAwaitFalse()) { + while (await reader.ReadAsync(token).ConfigureAwaitFalse()) { ReadForeignKeyColumnData(reader, context, ref tableId, ref foreignKey, ref referencingTable, ref referencedTable); } } @@ -812,10 +812,10 @@ protected virtual async Task ExtractFulltextIndexesAsync(ExtractionContext conte ColumnResolver table = null; FullTextIndex index = null; var cmd = Connection.CreateCommand(query); - await using (cmd.ConfigureAwait(false)) { - var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwait(false); - await using (reader.ConfigureAwait(false)) { - while (await reader.ReadAsync(token).ConfigureAwait(false)) { + await using (cmd.ConfigureAwaitFalse()) { + var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwaitFalse(); + await using (reader.ConfigureAwaitFalse()) { + while (await reader.ReadAsync(token).ConfigureAwaitFalse()) { ReadFullTextIndexColumnData(reader, context, ref currentTableId, ref table, ref index); } } @@ -999,10 +999,10 @@ private async Task ExtractSequencesAsync(ExtractionContext context, Cancellation var query = BuildExtractSequencesQuery(context); var cmd = Connection.CreateCommand(query); - await using (cmd.ConfigureAwait(false)) { - var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwait(false); - await using (reader.ConfigureAwait(false)) { - while (await reader.ReadAsync(token).ConfigureAwait(false)) { + await using (cmd.ConfigureAwaitFalse()) { + var reader = await cmd.ExecuteReaderAsync(token).ConfigureAwaitFalse(); + await using (reader.ConfigureAwaitFalse()) { + while (await reader.ReadAsync(token).ConfigureAwaitFalse()) { ReadSequenceData(reader, context); } } diff --git a/Orm/Xtensive.Orm.Sqlite/Sql.Drivers.Sqlite/ProviderInitializer.cs b/Orm/Xtensive.Orm.Sqlite/Sql.Drivers.Sqlite/ProviderInitializer.cs index b7a6aca3a..467eefbe8 100644 --- a/Orm/Xtensive.Orm.Sqlite/Sql.Drivers.Sqlite/ProviderInitializer.cs +++ b/Orm/Xtensive.Orm.Sqlite/Sql.Drivers.Sqlite/ProviderInitializer.cs @@ -53,9 +53,7 @@ private static Stream GetLibraryStream() private static string GetLibraryHash() { -#pragma warning disable SYSLIB0021 // Type or member is obsolete - // direct creation is more efficient than SHA1.Create() - using (var hashProvider = new System.Security.Cryptography.SHA1Managed()) { + using (var hashProvider = SHA1.Create()) { //hashProvider.Initialize(); ReadOnlySpan hashRaw; using (var stream = GetLibraryStream()) { @@ -63,7 +61,6 @@ private static string GetLibraryHash() } return new StringBuilder().AppendHexArray(hashRaw[..8]).ToString(); } -#pragma warning restore SYSLIB0021 // Type or member is obsolete } private static string GetLibraryFileName(string nativeLibraryCacheFolder, string moduleHash) diff --git a/Orm/Xtensive.Orm.Tests.Core/Collections/CollectionUtilsTest.cs b/Orm/Xtensive.Orm.Tests.Core/Collections/CollectionUtilsTest.cs index e888bba33..e747e40cd 100644 --- a/Orm/Xtensive.Orm.Tests.Core/Collections/CollectionUtilsTest.cs +++ b/Orm/Xtensive.Orm.Tests.Core/Collections/CollectionUtilsTest.cs @@ -16,6 +16,7 @@ namespace Xtensive.Orm.Tests.Core.Collections public class CollectionUtilsTest { [Test] + [Obsolete] public void RangeToArrayTest() { Assert.That(CollectionUtils.RangeToArray(1, 10).SequenceEqual(Enumerable.Range(1, 10))); @@ -24,6 +25,7 @@ public void RangeToArrayTest() } [Test] + [Obsolete] public void RangeToListTest() { Assert.That(CollectionUtils.RangeToList(1, 10).SequenceEqual(Enumerable.Range(1, 10).Select(i => (ColNum)i))); diff --git a/Orm/Xtensive.Orm.Tests.Core/Tuples/DummyTuple.cs b/Orm/Xtensive.Orm.Tests.Core/Tuples/DummyTuple.cs index a82e35f3f..bab6533ee 100644 --- a/Orm/Xtensive.Orm.Tests.Core/Tuples/DummyTuple.cs +++ b/Orm/Xtensive.Orm.Tests.Core/Tuples/DummyTuple.cs @@ -14,7 +14,7 @@ namespace Xtensive.Orm.Tests.Core.Tuples { public class DummyTuple: Xtensive.Tuples.Tuple { - private TupleDescriptor descriptor; + private readonly TupleDescriptor descriptor; private BitArray available; private object[] values; @@ -81,7 +81,7 @@ public override void SetValue(int fieldIndex, object fieldValue) public DummyTuple(TupleDescriptor descriptor) { - ArgumentNullException.ThrowIfNull(descriptor); + ArgumentValidator.EnsureArgumentIsNotDefault(descriptor, nameof(descriptor)); this.descriptor = descriptor; values = new object[descriptor.Count]; available = new BitArray(new bool[descriptor.Count]); diff --git a/Orm/Xtensive.Orm.Tests.Framework/Orm.config b/Orm/Xtensive.Orm.Tests.Framework/Orm.config index 12434b9b8..2fd979363 100644 --- a/Orm/Xtensive.Orm.Tests.Framework/Orm.config +++ b/Orm/Xtensive.Orm.Tests.Framework/Orm.config @@ -23,24 +23,6 @@ - - - - - - - - - - - - @@ -81,12 +63,6 @@ - - - - @@ -122,9 +98,6 @@ - - @@ -159,28 +132,11 @@ + - - - - - - - - - - - - @@ -221,12 +177,6 @@ - - - - @@ -262,9 +212,6 @@ - - diff --git a/Orm/Xtensive.Orm.Tests.Sql/SqlServer/MSSQLTests.cs b/Orm/Xtensive.Orm.Tests.Sql/SqlServer/MSSQLTests.cs index 66c4c36ec..b21ffdd1e 100644 --- a/Orm/Xtensive.Orm.Tests.Sql/SqlServer/MSSQLTests.cs +++ b/Orm/Xtensive.Orm.Tests.Sql/SqlServer/MSSQLTests.cs @@ -2562,7 +2562,7 @@ public void Test115() var p = SqlDml.TableRef(Catalog.Schemas["Production"].Tables["Product"], "p"); var pr = SqlDml.TableRef(Catalog.Schemas["Production"].Tables["ProductReview"], "pr"); - var select = SqlDml.Select(p.LeftOuterJoin(pr, p["ProductID"]==pr["ProductID"])); + var select = SqlDml.Select(p.LeftJoinEx(pr, p["ProductID"]==pr["ProductID"])); select.Columns.AddRange(p["Name"], pr["ProductReviewID"]); Assert.That(CompareExecuteDataReader(nativeSql, select), Is.True); diff --git a/Orm/Xtensive.Orm.Tests/Issues/IssueGithub0114_QueryRootReuseCauseNoRefJoin.cs b/Orm/Xtensive.Orm.Tests/Issues/IssueGithub0114_QueryRootReuseCauseNoRefJoin.cs index 7a2509434..fcb47e498 100644 --- a/Orm/Xtensive.Orm.Tests/Issues/IssueGithub0114_QueryRootReuseCauseNoRefJoin.cs +++ b/Orm/Xtensive.Orm.Tests/Issues/IssueGithub0114_QueryRootReuseCauseNoRefJoin.cs @@ -2389,7 +2389,7 @@ public void LeftJoinQueryReuse() .Select(promo => new { promo, notifications = session.Query.All() - .LeftOuterJoin(session.Query.All(), n => n.TriggeredBy.Id, u => u.Id, (n, u) => new { n, u }) + .LeftJoinEx(session.Query.All(), n => n.TriggeredBy.Id, u => u.Id, (n, u) => new { n, u }) }) .Select(anon => new { contacted = anon.notifications.Select(c => c.n.Recipient.User.Id) @@ -2401,9 +2401,9 @@ public void LeftJoinQueryReuse() .Select(promo => new { promo }) .Select(anon => new { contacted = session.Query.All() - .LeftOuterJoin(session.Query.All(), n => n.TriggeredBy.Id, u => u.Id, (n, u) => new { n, u }).Select(c => c.n.Recipient.User.Id) + .LeftJoinEx(session.Query.All(), n => n.TriggeredBy.Id, u => u.Id, (n, u) => new { n, u }).Select(c => c.n.Recipient.User.Id) .Concat(session.Query.All() - .LeftOuterJoin(session.Query.All(), n => n.TriggeredBy.Id, u => u.Id, (n, u) => new { n, u }).Select(c => c.n.Recipient.User.Id)), + .LeftJoinEx(session.Query.All(), n => n.TriggeredBy.Id, u => u.Id, (n, u) => new { n, u }).Select(c => c.n.Recipient.User.Id)), promo = anon.promo }).ToArray(); diff --git a/Orm/Xtensive.Orm.Tests/Issues/IssueGithub0171_ReadDateTimeOffsetFromPackedTuple.cs b/Orm/Xtensive.Orm.Tests/Issues/IssueGithub0171_ReadDateTimeOffsetFromPackedTuple.cs index ca963bba5..67f97769e 100644 --- a/Orm/Xtensive.Orm.Tests/Issues/IssueGithub0171_ReadDateTimeOffsetFromPackedTuple.cs +++ b/Orm/Xtensive.Orm.Tests/Issues/IssueGithub0171_ReadDateTimeOffsetFromPackedTuple.cs @@ -78,7 +78,7 @@ public void DateTimeOffsetCase() var loadWithCargo = new CargoLoad(session, cargo); var query = session.Query.All() - .LeftOuterJoin(session.Query.All(), + .LeftJoinEx(session.Query.All(), cl => cl.Cargo, c => c, (cl, c) => new { CargoLoad = cl, Cargo = c }) @@ -102,7 +102,7 @@ public void DateTimeCase() var loadWithCargo = new CargoLoad(session, cargo); var query = session.Query.All() - .LeftOuterJoin(session.Query.All(), + .LeftJoinEx(session.Query.All(), cl => cl.Cargo, c => c, (cl, c) => new { CargoLoad = cl, Cargo = c }) diff --git a/Orm/Xtensive.Orm.Tests/Issues/IssueJira0553_IncorrectLeftJoinOnNotNullEntityField.cs b/Orm/Xtensive.Orm.Tests/Issues/IssueJira0553_IncorrectLeftJoinOnNotNullEntityField.cs index 10e05e255..c01a8114f 100644 --- a/Orm/Xtensive.Orm.Tests/Issues/IssueJira0553_IncorrectLeftJoinOnNotNullEntityField.cs +++ b/Orm/Xtensive.Orm.Tests/Issues/IssueJira0553_IncorrectLeftJoinOnNotNullEntityField.cs @@ -136,7 +136,7 @@ public void BadWorkTest() using (var session = Domain.OpenSession()) using (var t = session.OpenTransaction()) { var badResult = session.Query.All() - .LeftOuterJoin( + .LeftJoinEx( session.Query.All(), e => e.Id, ewc => ewc.Id, @@ -155,7 +155,7 @@ public void GoodWorkTest() using (var session = Domain.OpenSession()) using (var transaction = session.OpenTransaction()) { var goodResult = session.Query.All() - .LeftOuterJoin( + .LeftJoinEx( session.Query.All(), e => e.Id, ewc => ewc.Id, @@ -173,7 +173,7 @@ public void WorkaroundTest() using (var session = Domain.OpenSession()) using (var transaction = session.OpenTransaction()) { var wordaround = session.Query.All() - .LeftOuterJoin( + .LeftJoinEx( session.Query.All(), e => e.Id, ewc => ewc.Id, @@ -181,7 +181,7 @@ public void WorkaroundTest() e.Id, CarId = ewc.Car.Id }) - .LeftOuterJoin( + .LeftJoinEx( session.Query.All(), e => e.CarId, c => c.Id, diff --git a/Orm/Xtensive.Orm.Tests/Issues/IssueJira0584_IncorrectMappingOfColumnInQuery.cs b/Orm/Xtensive.Orm.Tests/Issues/IssueJira0584_IncorrectMappingOfColumnInQuery.cs index 409077418..272fdf6f0 100644 --- a/Orm/Xtensive.Orm.Tests/Issues/IssueJira0584_IncorrectMappingOfColumnInQuery.cs +++ b/Orm/Xtensive.Orm.Tests/Issues/IssueJira0584_IncorrectMappingOfColumnInQuery.cs @@ -526,8 +526,8 @@ public void IncludeProviderOptimizationTest01() var usefulColumns = masterCredit.Union(masterDebit); var readyForFilterQuery = from joinResult in usefulColumns - .LeftOuterJoin(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) - .LeftOuterJoin(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) + .LeftJoinEx(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) + .LeftJoinEx(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) let item = joinResult.pp select new CustomPosting() { Id = item.Id, @@ -609,8 +609,8 @@ public void IncludeProviderOptimizationTest02() var usefulColumns = masterCredit.Union(masterDebit); var readyForFilterQuery = from joinResult in usefulColumns - .LeftOuterJoin(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) - .LeftOuterJoin(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) + .LeftJoinEx(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) + .LeftJoinEx(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) let item = joinResult.pp select new CustomPosting { Id = item.Id, @@ -692,8 +692,8 @@ public void IncludeProviderOptimizationTest03() var usefulColumns = masterCredit.Union(masterDebit); var readyForFilterQuery = from joinResult in usefulColumns - .LeftOuterJoin(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) - .LeftOuterJoin(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) + .LeftJoinEx(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) + .LeftJoinEx(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) let item = joinResult.pp select new CustomPosting { Id = item.Id, @@ -776,8 +776,8 @@ public void IncludeProviderOptimizationTest04() var usefulColumns = masterCredit.Union(masterDebit); var readyForFilterQuery = from joinResult in usefulColumns - .LeftOuterJoin(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) - .LeftOuterJoin(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) + .LeftJoinEx(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) + .LeftJoinEx(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) let item = joinResult.pp select new CustomPosting { Id = item.Id, @@ -859,8 +859,8 @@ public void IncludeProviderOptimizationTest05() var usefulColumns = masterCredit.Union(masterDebit); var readyForFilterQuery = from joinResult in usefulColumns - .LeftOuterJoin(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) - .LeftOuterJoin(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) + .LeftJoinEx(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) + .LeftJoinEx(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) let item = joinResult.pp select new CustomPosting { Id = item.Id, @@ -1029,7 +1029,7 @@ public void JoinAsSourceOfSetOperation() var result = from r in preResult.Join(tp.Distinct(), a => a.MasterAccount, a => a.Account, (a, pm) => new {pp = a, pm}) - .LeftOuterJoin(Query.All(), a => a.pm.FinToolKind, a => a.Id, (a, b) => new {pp = a.pp, pm = a.pm, fk = b}) + .LeftJoinEx(Query.All(), a => a.pm.FinToolKind, a => a.Id, (a, b) => new {pp = a.pp, pm = a.pm, fk = b}) let q = r.pp select new { diff --git a/Orm/Xtensive.Orm.Tests/Issues/IssueJira0586_AnonymousTypeComparisonBug.cs b/Orm/Xtensive.Orm.Tests/Issues/IssueJira0586_AnonymousTypeComparisonBug.cs index 2ea6b5a0e..8080bfd0a 100644 --- a/Orm/Xtensive.Orm.Tests/Issues/IssueJira0586_AnonymousTypeComparisonBug.cs +++ b/Orm/Xtensive.Orm.Tests/Issues/IssueJira0586_AnonymousTypeComparisonBug.cs @@ -108,7 +108,7 @@ public void MainTest() var masterCredit = Query.All(); - var join = from r in masterCredit.LeftOuterJoin( + var join = from r in masterCredit.LeftJoinEx( tableParts, a => a.CreditAccount.Id, a => a.Account.Id, diff --git a/Orm/Xtensive.Orm.Tests/Issues/IssueJira0617_IncorrectRemoveOfRedundantColumns.cs b/Orm/Xtensive.Orm.Tests/Issues/IssueJira0617_IncorrectRemoveOfRedundantColumns.cs index 2c2eaf62a..a2b9c6687 100644 --- a/Orm/Xtensive.Orm.Tests/Issues/IssueJira0617_IncorrectRemoveOfRedundantColumns.cs +++ b/Orm/Xtensive.Orm.Tests/Issues/IssueJira0617_IncorrectRemoveOfRedundantColumns.cs @@ -68,8 +68,8 @@ public void Test01() var usefulColumns = masterCredit.Union(masterDebit); var readyForFilterQuery = from joinResult in usefulColumns - .LeftOuterJoin(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) - .LeftOuterJoin(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) + .LeftJoinEx(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) + .LeftJoinEx(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) let item = joinResult.pp select new CustomPosting() { Id = item.Id, @@ -149,8 +149,8 @@ public void Test02() var usefulColumns = masterCredit.Union(masterDebit); var readyForFilterQuery = from joinResult in usefulColumns - .LeftOuterJoin(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) - .LeftOuterJoin(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) + .LeftJoinEx(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) + .LeftJoinEx(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) let item = joinResult.pp select new CustomPosting { Id = item.Id, @@ -230,8 +230,8 @@ public void Test03() var usefulColumns = masterCredit.Union(masterDebit); var readyForFilterQuery = from joinResult in usefulColumns - .LeftOuterJoin(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) - .LeftOuterJoin(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) + .LeftJoinEx(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) + .LeftJoinEx(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) let item = joinResult.pp select new CustomPosting { Id = item.Id, @@ -312,8 +312,8 @@ public void Test04() var usefulColumns = masterCredit.Union(masterDebit); var readyForFilterQuery = from joinResult in usefulColumns - .LeftOuterJoin(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) - .LeftOuterJoin(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) + .LeftJoinEx(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) + .LeftJoinEx(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) let item = joinResult.pp select new CustomPosting { Id = item.Id, @@ -393,8 +393,8 @@ public void Test05() var usefulColumns = masterCredit.Union(masterDebit); var readyForFilterQuery = from joinResult in usefulColumns - .LeftOuterJoin(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) - .LeftOuterJoin(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) + .LeftJoinEx(priceCalculation, a => a.SlaveAccount, a => a.Account, (pp, ps) => new {pp, ps}) + .LeftJoinEx(priceCalculation, a => a.pp.MasterAccount, a => a.Account, (a, pm) => new {a.pp, a.ps, pm}) let item = joinResult.pp select new CustomPosting { Id = item.Id, @@ -562,7 +562,7 @@ public void Test08() var result = from r in preResult.Join(tp.Distinct(), a => a.MasterAccount, a => a.Account, (a, pm) => new {pp = a, pm}) - .LeftOuterJoin(Query.All(), a => a.pm.FinToolKind, a => a.Id, (a, b) => new {pp = a.pp, pm = a.pm, fk = b}) + .LeftJoinEx(Query.All(), a => a.pm.FinToolKind, a => a.Id, (a, b) => new {pp = a.pp, pm = a.pm, fk = b}) let q = r.pp select new { diff --git a/Orm/Xtensive.Orm.Tests/Issues/IssueJira0803_ReuseOfJoiningExpressionCausesWrongTranslation.cs b/Orm/Xtensive.Orm.Tests/Issues/IssueJira0803_ReuseOfJoiningExpressionCausesWrongTranslation.cs index 8e4e1bebe..57d5c648a 100644 --- a/Orm/Xtensive.Orm.Tests/Issues/IssueJira0803_ReuseOfJoiningExpressionCausesWrongTranslation.cs +++ b/Orm/Xtensive.Orm.Tests/Issues/IssueJira0803_ReuseOfJoiningExpressionCausesWrongTranslation.cs @@ -66,7 +66,7 @@ public void LeftJoinOneVariableUsage() using (var tx = session.OpenTransaction()) { var leftJoinWithExpression = session.Query.All() - .LeftOuterJoin(session.Query.All().Where(it => it.Description == null), + .LeftJoinEx(session.Query.All().Where(it => it.Description == null), o => o.Id, key, (o, i) => o) @@ -78,7 +78,7 @@ public void LeftJoinOneVariableUsage() Assert.That(leftJoinWithExpression.Count, Is.EqualTo(3)); leftJoinWithExpression = session.Query.All() - .LeftOuterJoin(session.Query.All().Where(it => it.Description == null), + .LeftJoinEx(session.Query.All().Where(it => it.Description == null), key, i => i.Id, (o, i) => o) @@ -101,7 +101,7 @@ public void LeftJoinTwoVariableUsage() var ex = Assert.Throws(() => _ = session.Query.All() - .LeftOuterJoin(session.Query.All().Where(it => it.Description == null), + .LeftJoinEx(session.Query.All().Where(it => it.Description == null), key, key, (o, i) => o) diff --git a/Orm/Xtensive.Orm.Tests/Linq/CustomExpressionCompilers.cs b/Orm/Xtensive.Orm.Tests/Linq/CustomExpressionCompilers.cs index 48e8dc4c6..e1ee52b5d 100644 --- a/Orm/Xtensive.Orm.Tests/Linq/CustomExpressionCompilers.cs +++ b/Orm/Xtensive.Orm.Tests/Linq/CustomExpressionCompilers.cs @@ -142,10 +142,11 @@ public void MainTest() var expected1 = session.Query.All().AsEnumerable().OrderBy(p => p.Id).Select(p => p.Fullname).ToList(); Assert.That(expected1.Count, Is.GreaterThan(0)); var fullNames1 = session.Query.All().OrderBy(p => p.Id).Select(p => p.Fullname).ToList(); - Assert.That(expected1, Is.EqualTo(fullNames1)); + Assert.That(expected1.SequenceEqual(fullNames1), Is.True); + var expected2 = session.Query.All().AsEnumerable().OrderBy(p => p.Id).Select(p => p.AddPrefix("Mr. ")).ToList(); var fullNames2 = session.Query.All().OrderBy(p => p.Id).Select(p => p.AddPrefix("Mr. ")).ToList(); - Assert.That(expected2, Is.EqualTo(fullNames2)); + Assert.That(expected2.SequenceEqual(fullNames2), Is.True); // Rollback } } diff --git a/Orm/Xtensive.Orm.Tests/Linq/DynamicallyDefinedFields.cs b/Orm/Xtensive.Orm.Tests/Linq/DynamicallyDefinedFields.cs index 24ea3bd9b..8e7ae24d2 100644 --- a/Orm/Xtensive.Orm.Tests/Linq/DynamicallyDefinedFields.cs +++ b/Orm/Xtensive.Orm.Tests/Linq/DynamicallyDefinedFields.cs @@ -1260,7 +1260,7 @@ public void LeftJoinTest() using (session.Activate()) using (var transction = session.OpenTransaction()) { Assert.DoesNotThrow(() => { - session.Query.All().LeftOuterJoin(session.Query.All(), area => (Group)area[testData.GroupFieldName], + session.Query.All().LeftJoinEx(session.Query.All(), area => (Group)area[testData.GroupFieldName], group => group, (area, @group) => new { Area = area, Group = group }); }); } diff --git a/Orm/Xtensive.Orm.Tests/Linq/FullTextColumnsDeclarationTest.cs b/Orm/Xtensive.Orm.Tests/Linq/FullTextColumnsDeclarationTest.cs index 579c0c832..7a45d6d5f 100644 --- a/Orm/Xtensive.Orm.Tests/Linq/FullTextColumnsDeclarationTest.cs +++ b/Orm/Xtensive.Orm.Tests/Linq/FullTextColumnsDeclarationTest.cs @@ -1,4 +1,4 @@ -using System; +using System; using System.Collections.Generic; using System.Linq; using System.Linq.Expressions; diff --git a/Orm/Xtensive.Orm.Tests/Linq/InTest.cs b/Orm/Xtensive.Orm.Tests/Linq/InTest.cs index 4f0069848..ac66f1462 100644 --- a/Orm/Xtensive.Orm.Tests/Linq/InTest.cs +++ b/Orm/Xtensive.Orm.Tests/Linq/InTest.cs @@ -76,7 +76,7 @@ public async Task StringContainsAsyncTest() public void MartinTest() { _ = Session.Query.All() - .LeftOuterJoin(Session.Query.All(), c => c, i => i.Customer, (c, i) => new { Customer = c, Invoice = i }) + .LeftJoinEx(Session.Query.All(), c => c, i => i.Customer, (c, i) => new { Customer = c, Invoice = i }) .GroupBy(i => new { i.Customer.FirstName, i.Customer.LastName }) .Select(g => new { Key = g.Key, Count = g.Count(j => j.Invoice != null) }) .ToList(); diff --git a/Orm/Xtensive.Orm.Tests/Linq/JoinTest.cs b/Orm/Xtensive.Orm.Tests/Linq/JoinTest.cs index efff17fc2..292e3d993 100644 --- a/Orm/Xtensive.Orm.Tests/Linq/JoinTest.cs +++ b/Orm/Xtensive.Orm.Tests/Linq/JoinTest.cs @@ -143,7 +143,7 @@ public void SimpleLeftTest() { var traclCount = Session.Query.All().Count(); var result = Session.Query.All() - .LeftOuterJoin(Session.Query.All(), + .LeftJoinEx(Session.Query.All(), track => track.Album.AlbumId, album => album.AlbumId, (track, album) => new {track.Name, album.Title, album.AlbumId}); @@ -159,7 +159,7 @@ public void LeftJoin1Test() Session.Current.SaveChanges(); var tracks = Session.Query.All(); var albums = Session.Query.All(); - var result = tracks.LeftOuterJoin( + var result = tracks.LeftJoinEx( albums, track => track.Album, album => album, @@ -179,7 +179,7 @@ public void LeftJoin2Test() Session.Current.SaveChanges(); var tracks = Session.Query.All(); var albums = Session.Query.All(); - var result = tracks.LeftOuterJoin( + var result = tracks.LeftJoinEx( albums, track => track.Album.AlbumId, album => album.AlbumId, diff --git a/Orm/Xtensive.Orm.Tests/Linq/TagTest.cs b/Orm/Xtensive.Orm.Tests/Linq/TagTest.cs index 234317500..07f6c0714 100644 --- a/Orm/Xtensive.Orm.Tests/Linq/TagTest.cs +++ b/Orm/Xtensive.Orm.Tests/Linq/TagTest.cs @@ -331,7 +331,7 @@ public void TagInJoin() var inner = session.Query.All().Tag("inner"); var outer = session.Query.All().Tag("outer"); - var query = outer.LeftOuterJoin(inner, o => o.Owner.Id, i => i.Id, (i, o) => new { i, o }); + var query = outer.LeftJoinEx(inner, o => o.Owner.Id, i => i.Id, (i, o) => new { i, o }); var queryFormatter = session.Services.Demand(); var queryString = queryFormatter.ToSqlString(query); @@ -589,7 +589,7 @@ public void TagInGrouping() .Tag("AfterSelect") .Where(g => g.Items.Count() >= 0) .Tag("AfterWhere") - .LeftOuterJoin(session.Query.All().Tag("WithinJoin"), g => g.Key, bu => bu.Id, (g, bu) => new { Key = bu, Items = g.Items }); + .LeftJoinEx(session.Query.All().Tag("WithinJoin"), g => g.Key, bu => bu.Id, (g, bu) => new { Key = bu, Items = g.Items }); using (var tagScope = session.Tag("sessionTag6")) { session.Events.DbCommandExecuting += SqlCapturer; diff --git a/Orm/Xtensive.Orm.Tests/Storage/Randomized/Tree.cs b/Orm/Xtensive.Orm.Tests/Storage/Randomized/Tree.cs index 65d50a8d8..97f68971c 100644 --- a/Orm/Xtensive.Orm.Tests/Storage/Randomized/Tree.cs +++ b/Orm/Xtensive.Orm.Tests/Storage/Randomized/Tree.cs @@ -7,6 +7,7 @@ using System; using System.Collections; using System.Collections.Generic; +using System.Linq; using Xtensive.Collections; using Xtensive.Core; diff --git a/Orm/Xtensive.Orm.Tests/Upgrade/DomainUpgradeTest.cs b/Orm/Xtensive.Orm.Tests/Upgrade/DomainUpgradeTest.cs index f3c0abce5..843f0de64 100644 --- a/Orm/Xtensive.Orm.Tests/Upgrade/DomainUpgradeTest.cs +++ b/Orm/Xtensive.Orm.Tests/Upgrade/DomainUpgradeTest.cs @@ -775,7 +775,7 @@ private async Task BuildDomainAsync(int version, DomainUpgradeMode upgra var configuration = CreateConfiguration(upgradeMode, types, keyCacheSize); using (Upgrader.EnableForVersion(version, modelParts)) { - return await BuildDomainFromConfig(configuration, true).ConfigureAwait(false); + return await BuildDomainFromConfig(configuration, true).ConfigureAwaitFalse(); } } diff --git a/Orm/Xtensive.Orm/Arithmetic/Internal/NullableArithmetic.cs b/Orm/Xtensive.Orm/Arithmetic/Internal/NullableArithmetic.cs index 7e7e93c83..030abd006 100644 --- a/Orm/Xtensive.Orm/Arithmetic/Internal/NullableArithmetic.cs +++ b/Orm/Xtensive.Orm/Arithmetic/Internal/NullableArithmetic.cs @@ -82,10 +82,7 @@ public override bool IsSigned } /// - protected override IArithmetic CreateNew(ArithmeticRules rules) - { - return new NullableArithmetic(Provider, rules); - } + protected override NullableArithmetic CreateNew(ArithmeticRules rules) => new(Provider, rules); // Constructors diff --git a/Orm/Xtensive.Orm/Arithmetic/Internal/PrimitiveArithmetics.tt b/Orm/Xtensive.Orm/Arithmetic/Internal/PrimitiveArithmetics.tt index 4477aa360..90e9a1a84 100644 --- a/Orm/Xtensive.Orm/Arithmetic/Internal/PrimitiveArithmetics.tt +++ b/Orm/Xtensive.Orm/Arithmetic/Internal/PrimitiveArithmetics.tt @@ -1,4 +1,4 @@ -<#@ template language="C#" #> +<#@ template language="C#" #> <#@ assembly name="System.Core" #> <#@ import namespace="System.Linq" #> // Copyright (C) 2008 Xtensive LLC. @@ -146,10 +146,7 @@ foreach (var type in types) { } /// - protected override IArithmetic<<#= primitiveName #>> CreateNew(ArithmeticRules rules) - { - return new <#= className #>(Provider, rules); - } + protected override <#= className #> CreateNew(ArithmeticRules rules) => new(Provider, rules); // Constructors diff --git a/Orm/Xtensive.Orm/Caching/InfiniteCache.cs b/Orm/Xtensive.Orm/Caching/InfiniteCache.cs index a55e59838..65ad244df 100644 --- a/Orm/Xtensive.Orm/Caching/InfiniteCache.cs +++ b/Orm/Xtensive.Orm/Caching/InfiniteCache.cs @@ -116,7 +116,7 @@ public InfiniteCache(int capacity, Converter keyExtractor) { ArgumentNullException.ThrowIfNull(keyExtractor); if (capacity < 0) - throw new ArgumentOutOfRangeException("capacity", capacity, Strings.ExArgumentValueMustBeGreaterThanOrEqualToZero); + throw new ArgumentOutOfRangeException(nameof(capacity), capacity, Strings.ExArgumentValueMustBeGreaterThanOrEqualToZero); this.KeyExtractor = keyExtractor; items = new Dictionary(capacity); } diff --git a/Orm/Xtensive.Orm/Caching/LruCache{TKey, TItem, TCached}.cs b/Orm/Xtensive.Orm/Caching/LruCache{TKey, TItem, TCached}.cs index 1873e49c1..ab1af7096 100644 --- a/Orm/Xtensive.Orm/Caching/LruCache{TKey, TItem, TCached}.cs +++ b/Orm/Xtensive.Orm/Caching/LruCache{TKey, TItem, TCached}.cs @@ -245,7 +245,7 @@ public LruCache(long maxSize, Converter keyExtractor, ArgumentValidator.EnsureArgumentIsInRange(maxSize, 1, long.MaxValue, "maxSize"); ArgumentNullException.ThrowIfNull(keyExtractor); this.maxSize = maxSize; - this.KeyExtractor = keyExtractor; + this.KeyExtractor = keyExtractor ?? throw new ArgumentNullException(nameof(keyExtractor)); this.cacheConverter = cacheConverter; this.chainedCache = chainedCache; // deque = new TopDeque(1 + (int) maxSize); diff --git a/Orm/Xtensive.Orm/Caching/LruCache{TKey, TItem}.cs b/Orm/Xtensive.Orm/Caching/LruCache{TKey, TItem}.cs index 52ec441c4..9e73ccffc 100644 --- a/Orm/Xtensive.Orm/Caching/LruCache{TKey, TItem}.cs +++ b/Orm/Xtensive.Orm/Caching/LruCache{TKey, TItem}.cs @@ -239,8 +239,8 @@ public LruCache(long maxSize, Converter keyExtractor, ArgumentNullException.ThrowIfNull(keyExtractor); ArgumentNullException.ThrowIfNull(sizeExtractor); this.maxSize = maxSize; - this.KeyExtractor = keyExtractor; - this.sizeExtractor = sizeExtractor; + this.KeyExtractor = keyExtractor ?? throw new ArgumentNullException(nameof(keyExtractor)); + this.sizeExtractor = sizeExtractor ?? throw new ArgumentNullException(nameof(sizeExtractor)); this.chainedCache = chainedCache; // deque = new TopDeque>(1 + (int) maxSize); deque = new TopDeque>(); diff --git a/Orm/Xtensive.Orm/Caching/MfLruCache.cs b/Orm/Xtensive.Orm/Caching/MfLruCache.cs index 2d4eca20e..d9cb71461 100644 --- a/Orm/Xtensive.Orm/Caching/MfLruCache.cs +++ b/Orm/Xtensive.Orm/Caching/MfLruCache.cs @@ -415,7 +415,7 @@ public MfLruCache(int lruCapacity, int mfuCapacity, int efficiencyFactor, this.efficiencyFactor = efficiencyFactor; if (efficiencyFactor<0) timeShift = -efficiencyFactor-1; // Constant timeShift is defined - this.KeyExtractor = keyExtractor; + this.KeyExtractor = keyExtractor ?? throw new ArgumentNullException(nameof(keyExtractor)); this.chainedCache = chainedCache; // items = new Dictionary(1 + capacity); items = new Dictionary(); diff --git a/Orm/Xtensive.Orm/Caching/WeakCache.cs b/Orm/Xtensive.Orm/Caching/WeakCache.cs index 78b5b89ca..8a5ad555a 100644 --- a/Orm/Xtensive.Orm/Caching/WeakCache.cs +++ b/Orm/Xtensive.Orm/Caching/WeakCache.cs @@ -227,7 +227,7 @@ public WeakCache(bool trackResurrection, Converter keyExtractor) { ArgumentNullException.ThrowIfNull(keyExtractor); this.trackResurrection = trackResurrection; - this.KeyExtractor = keyExtractor; + this.KeyExtractor = keyExtractor ?? throw new ArgumentNullException(nameof(keyExtractor)); } // Dispose pattern diff --git a/Orm/Xtensive.Orm/Caching/WeakestCache.cs b/Orm/Xtensive.Orm/Caching/WeakestCache.cs index 5db7f7613..d681d296b 100644 --- a/Orm/Xtensive.Orm/Caching/WeakestCache.cs +++ b/Orm/Xtensive.Orm/Caching/WeakestCache.cs @@ -360,7 +360,7 @@ public WeakestCache(bool trackKeyResurrection, bool trackItemResurrection, Conve ArgumentNullException.ThrowIfNull(keyExtractor); this.trackKeyResurrection = trackKeyResurrection; this.trackItemResurrection = trackItemResurrection; - this.KeyExtractor = keyExtractor; + this.KeyExtractor = keyExtractor ?? throw new ArgumentNullException(nameof(keyExtractor)); items = new Dictionary(1024, new WeakEntryEqualityComparer()); } diff --git a/Orm/Xtensive.Orm/Collections/ChainedBuffer.cs b/Orm/Xtensive.Orm/Collections/ChainedBuffer.cs index 713c8a77b..d9dabe7e2 100644 --- a/Orm/Xtensive.Orm/Collections/ChainedBuffer.cs +++ b/Orm/Xtensive.Orm/Collections/ChainedBuffer.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2013-2020 Xtensive LLC. +// Copyright (C) 2013-2020 Xtensive LLC. // This code is distributed under MIT license terms. // See the License.txt file in the project root for more information. // Created by: Alena Mikshina diff --git a/Orm/Xtensive.Orm/Collections/CollectionUtils.cs b/Orm/Xtensive.Orm/Collections/CollectionUtils.cs index 401ba968c..a154bd494 100644 --- a/Orm/Xtensive.Orm/Collections/CollectionUtils.cs +++ b/Orm/Xtensive.Orm/Collections/CollectionUtils.cs @@ -23,6 +23,7 @@ public static class CollectionUtils /// /// is less than 0.-or- /// + -1 is larger than . + [Obsolete("Enumerable.Range().ToArray() is several times faster")] public static int[] RangeToArray(int start, int count) { ArgumentOutOfRangeException.ThrowIfNegative(count); @@ -40,15 +41,19 @@ public static int[] RangeToArray(int start, int count) /// /// is less than 0.-or- /// + -1 is larger than . - public static List RangeToList(ColNum start, ColNum count) + public static List RangeToList(int start, int count) { ArgumentOutOfRangeException.ThrowIfNegative(count); var result = new List(count); - result.AddRange(Enumerable.Range(start, count).Select(i => (ColNum) i)); + for (int i = 0; i < count; ++i) { + result.Add((ColNum)(start + i)); + } return result; } - private static readonly IReadOnlyList[] preallocatedRanges = Enumerable.Range(0, 100).Select(len => (IReadOnlyList)Enumerable.Range(0, len).Select(i => (ColNum)i).ToArray()).ToArray(); + private static readonly IReadOnlyList[] preallocatedRanges = Enumerable.Range(0, 100) + .Select(len => (IReadOnlyList)Enumerable.Range(0, len).Select(i => (ColNum)i).ToArray()) + .ToArray(); public static IReadOnlyList ColNumRange(int count) => count < preallocatedRanges.Length ? preallocatedRanges[count] : Enumerable.Range(0, count).Select(i => (ColNum)i).ToArray(); diff --git a/Orm/Xtensive.Orm/Collections/ExtensionCollection.cs b/Orm/Xtensive.Orm/Collections/ExtensionCollection.cs index ca07839d3..587fd408a 100644 --- a/Orm/Xtensive.Orm/Collections/ExtensionCollection.cs +++ b/Orm/Xtensive.Orm/Collections/ExtensionCollection.cs @@ -71,10 +71,10 @@ public void Set(Type extensionType, object value) ArgumentNullException.ThrowIfNull(extensionType); if (extensionType.IsValueType) throw new ArgumentException(string.Format( - Strings.ExTypeXMustBeReferenceType, extensionType.GetShortName()), "extensionType"); + Strings.ExTypeXMustBeReferenceType, extensionType.GetShortName()), nameof(extensionType)); if (value!=null && !extensionType.IsAssignableFrom(value.GetType())) throw new ArgumentException(string.Format( - Strings.ExTypeXMustImplementY, value.GetType(), extensionType.GetShortName()), "value"); + Strings.ExTypeXMustImplementY, value.GetType(), extensionType.GetShortName()), nameof(value)); if (extensions==null) if (value==null) @@ -106,9 +106,14 @@ public override void Lock(bool recursive = true) #region ICloneable methods /// - public ExtensionCollection Clone() => new(this); object ICloneable.Clone() => Clone(); + /// + /// Creates a new object that is a copy of the current instance. + /// + /// A new object that is a copy of this instance. + public ExtensionCollection Clone() => new(this); + #endregion #region IEnumerable methods diff --git a/Orm/Xtensive.Orm/Collections/Interfaces/IPriorityQueue.cs b/Orm/Xtensive.Orm/Collections/Interfaces/IPriorityQueue.cs index f346f8ca7..84ea144aa 100644 --- a/Orm/Xtensive.Orm/Collections/Interfaces/IPriorityQueue.cs +++ b/Orm/Xtensive.Orm/Collections/Interfaces/IPriorityQueue.cs @@ -16,6 +16,7 @@ namespace Xtensive.Collections /// /// of items to be stored in queue. /// of priority value. + [Obsolete] public interface IPriorityQueue : IEnumerable, ICloneable where TPriority : IComparable diff --git a/Orm/Xtensive.Orm/Collections/TypeRegistry.cs b/Orm/Xtensive.Orm/Collections/TypeRegistry.cs index 87a1b11dc..7f2f17624 100644 --- a/Orm/Xtensive.Orm/Collections/TypeRegistry.cs +++ b/Orm/Xtensive.Orm/Collections/TypeRegistry.cs @@ -147,14 +147,14 @@ public override void Lock(bool recursive) #region ICloneable members + /// + object ICloneable.Clone() => Clone(); + /// /// Clones this instance. /// /// - public virtual object Clone() - { - return new TypeRegistry(this); - } + public virtual TypeRegistry Clone() => new TypeRegistry(this); #endregion diff --git a/Orm/Xtensive.Orm/Comparison/AdvancedComparerBase.cs b/Orm/Xtensive.Orm/Comparison/AdvancedComparerBase.cs index 4ad7c9faa..9e3bc60e9 100644 --- a/Orm/Xtensive.Orm/Comparison/AdvancedComparerBase.cs +++ b/Orm/Xtensive.Orm/Comparison/AdvancedComparerBase.cs @@ -159,7 +159,7 @@ public AdvancedComparerBase(IComparerProvider provider, ComparisonRules comparis false, default(T), false, default(T), false, default(T)); - this.provider = provider; + this.provider = provider ?? throw new ArgumentNullException(nameof(provider)); ComparisonRules = comparisonRules; DefaultDirectionMultiplier = comparisonRules.Value.Direction == Direction.Negative ? -1 : 1; } diff --git a/Orm/Xtensive.Orm/Comparison/CastingComparer.cs b/Orm/Xtensive.Orm/Comparison/CastingComparer.cs index 77033a2e5..b97c95dec 100644 --- a/Orm/Xtensive.Orm/Comparison/CastingComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/CastingComparer.cs @@ -40,7 +40,7 @@ public AsymmetricCompareHandler(Func baseCompare) private readonly AdvancedComparer sourceComparer; /// - protected override IAdvancedComparer CreateNew(ComparisonRules rules) + protected override CastingComparer CreateNew(ComparisonRules rules) => new CastingComparer(sourceComparer.ApplyRules(rules)); /// diff --git a/Orm/Xtensive.Orm/Comparison/Internals/ArrayComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/ArrayComparer.cs index e775b0673..e8a04998d 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/ArrayComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/ArrayComparer.cs @@ -13,8 +13,7 @@ namespace Xtensive.Comparison internal sealed class ArrayComparer : WrappingComparer, ISystemComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new ArrayComparer(Provider, ComparisonRules.Combine(rules)); + protected override ArrayComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); public override int Compare(T[] x, T[] y) { diff --git a/Orm/Xtensive.Orm/Comparison/Internals/AssemblyComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/AssemblyComparer.cs index af3e73747..52f34e71d 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/AssemblyComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/AssemblyComparer.cs @@ -14,8 +14,7 @@ namespace Xtensive.Comparison internal sealed class AssemblyComparer: WrappingComparer, ISystemComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new AssemblyComparer(Provider, ComparisonRules.Combine(rules)); + protected override AssemblyComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); public override int Compare(Assembly x, Assembly y) { diff --git a/Orm/Xtensive.Orm/Comparison/Internals/BaseComparerWrapper.cs b/Orm/Xtensive.Orm/Comparison/Internals/BaseComparerWrapper.cs index ef4e624db..3c9e8be56 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/BaseComparerWrapper.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/BaseComparerWrapper.cs @@ -14,8 +14,7 @@ namespace Xtensive.Comparison internal class BaseComparerWrapper: WrappingComparer where T: TBase { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new BaseComparerWrapper(Provider, ComparisonRules.Combine(rules)); + protected override BaseComparerWrapper CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); public override int Compare(T x, T y) => BaseComparer.Compare(x, y); diff --git a/Orm/Xtensive.Orm/Comparison/Internals/BooleanComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/BooleanComparer.cs index 0b5fd6ad6..153784f94 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/BooleanComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/BooleanComparer.cs @@ -14,7 +14,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class BooleanComparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) => new BooleanComparer(Provider, ComparisonRules.Combine(rules)); + protected override BooleanComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); public override bool GetNearestValue(bool value, Direction direction) { diff --git a/Orm/Xtensive.Orm/Comparison/Internals/ByteComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/ByteComparer.cs index ebef97031..f6a6b834e 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/ByteComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/ByteComparer.cs @@ -12,8 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class ByteComparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new ByteComparer(Provider, ComparisonRules.Combine(rules)); + protected override ByteComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Comparison/Internals/CharComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/CharComparer.cs index 6a2eca9ed..136524c2f 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/CharComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/CharComparer.cs @@ -12,8 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class CharComparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new CharComparer(Provider, ComparisonRules.Combine(rules)); + protected override CharComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Comparison/Internals/DecimalComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/DecimalComparer.cs index 2190b2c79..579df40e2 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/DecimalComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/DecimalComparer.cs @@ -12,8 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class DecimalComparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new DecimalComparer(Provider, ComparisonRules.Combine(rules)); + protected override DecimalComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Comparison/Internals/DoubleComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/DoubleComparer.cs index 7d8fe1167..1a686c910 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/DoubleComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/DoubleComparer.cs @@ -12,8 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class DoubleComparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new DoubleComparer(Provider, ComparisonRules.Combine(rules)); + protected override DoubleComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Comparison/Internals/EnumComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/EnumComparer.cs index fd904619e..d0c7dd0a5 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/EnumComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/EnumComparer.cs @@ -26,8 +26,7 @@ internal sealed class EnumComparer : WrappingComparer valueToIndex; private readonly int maxIndex; - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new EnumComparer(Provider, ComparisonRules.Combine(rules)); + protected override EnumComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); public override int Compare(TEnum x, TEnum y) => BaseComparer.Compare(EnumToSystem(x), EnumToSystem(y)); diff --git a/Orm/Xtensive.Orm/Comparison/Internals/EnumerableInterfaceComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/EnumerableInterfaceComparer.cs index af5896047..eca2e7de7 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/EnumerableInterfaceComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/EnumerableInterfaceComparer.cs @@ -15,8 +15,8 @@ internal sealed class EnumerableInterfaceComparer : WrappingComp ISystemComparer where TEnumerable: class, IEnumerable { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new EnumerableInterfaceComparer(Provider, ComparisonRules.Combine(rules)); + protected override EnumerableInterfaceComparer CreateNew(ComparisonRules rules) + => new(Provider, ComparisonRules.Combine(rules)); public override int Compare(TEnumerable x, TEnumerable y) { diff --git a/Orm/Xtensive.Orm/Comparison/Internals/GuidComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/GuidComparer.cs index 42271594d..63be565e9 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/GuidComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/GuidComparer.cs @@ -12,8 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class GuidComparer: ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new GuidComparer(Provider, ComparisonRules.Combine(rules)); + protected override GuidComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Comparison/Internals/Int16Comparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/Int16Comparer.cs index fe10bc585..6ddd8d06b 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/Int16Comparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/Int16Comparer.cs @@ -12,8 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class Int16Comparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new Int16Comparer(Provider, ComparisonRules.Combine(rules)); + protected override Int16Comparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Comparison/Internals/Int32Comparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/Int32Comparer.cs index bbe22f1d0..9e77defa4 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/Int32Comparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/Int32Comparer.cs @@ -12,7 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class Int32Comparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) => new Int32Comparer(Provider, ComparisonRules.Combine(rules)); + protected override Int32Comparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Comparison/Internals/Int64Comparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/Int64Comparer.cs index 50dfb9d1c..df62ffc00 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/Int64Comparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/Int64Comparer.cs @@ -12,8 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class Int64Comparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new Int64Comparer(Provider, ComparisonRules.Combine(rules)); + protected override Int64Comparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Comparison/Internals/KeyValuePairComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/KeyValuePairComparer.cs index c61ff9bf5..b691600c5 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/KeyValuePairComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/KeyValuePairComparer.cs @@ -15,8 +15,7 @@ namespace Xtensive.Comparison internal sealed class KeyValuePairComparer: WrappingComparer, T1, T2>, ISystemComparer> { - protected override IAdvancedComparer> CreateNew(ComparisonRules rules) - => new KeyValuePairComparer(Provider, ComparisonRules.Combine(rules)); + protected override KeyValuePairComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); public override int Compare(KeyValuePair x, KeyValuePair y) { diff --git a/Orm/Xtensive.Orm/Comparison/Internals/NullableComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/NullableComparer.cs index 935248b46..4727b41a0 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/NullableComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/NullableComparer.cs @@ -23,8 +23,7 @@ internal sealed class NullableComparer: WrappingComparer private Func currentBaseGetHashCode; - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new NullableComparer(Provider, ComparisonRules.Combine(rules)); + protected override NullableComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); public override int Compare(T? x, T? y) { diff --git a/Orm/Xtensive.Orm/Comparison/Internals/ObjectComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/ObjectComparer.cs index f53972f32..9c6d5da60 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/ObjectComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/ObjectComparer.cs @@ -20,8 +20,7 @@ internal sealed class ObjectComparer: AdvancedComparerBase [NonSerialized] private int nullHashCode; - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new ObjectComparer(Provider, ComparisonRules.Combine(rules)); + protected override ObjectComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); public override int Compare(T x, T y) { diff --git a/Orm/Xtensive.Orm/Comparison/Internals/SByteComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/SByteComparer.cs index 720d62b58..5ae937bbf 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/SByteComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/SByteComparer.cs @@ -12,8 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class SByteComparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new SByteComparer(Provider, ComparisonRules.Combine(rules)); + protected override SByteComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Comparison/Internals/SingleComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/SingleComparer.cs index a7c901bbe..f6b790a9e 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/SingleComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/SingleComparer.cs @@ -12,8 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class SingleComparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new SingleComparer(Provider, ComparisonRules.Combine(rules)); + protected override SingleComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Comparison/Internals/StringComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/StringComparer.cs index 006eacfcf..aa749126f 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/StringComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/StringComparer.cs @@ -22,10 +22,7 @@ internal sealed class StringComparer: AdvancedComparerBase, [NonSerialized] private Func stringIsSuffix; - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - { - return new StringComparer(Provider, ComparisonRules.Combine(rules)); - } + protected override StringComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); public override int Compare(string x, string y) { diff --git a/Orm/Xtensive.Orm/Comparison/Internals/TupleComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/TupleComparer.cs index 98fd93171..6b3f54a02 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/TupleComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/TupleComparer.cs @@ -17,8 +17,7 @@ internal sealed class TupleComparer : AdvancedComparerBase, [NonSerialized] private int nullHashCode; - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new TupleComparer(Provider, ComparisonRules.Combine(rules)); + protected override TupleComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); public override int Compare(Tuple x, Tuple y) => throw new NotSupportedException(); diff --git a/Orm/Xtensive.Orm/Comparison/Internals/TupleDescriptorComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/TupleDescriptorComparer.cs index 8252629eb..d1c17f341 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/TupleDescriptorComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/TupleDescriptorComparer.cs @@ -19,8 +19,7 @@ namespace Xtensive.Comparison internal sealed class TupleDescriptorComparer: WrappingComparer, ISystemComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new TupleDescriptorComparer(Provider, ComparisonRules.Combine(rules)); + protected override TupleDescriptorComparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); public override int Compare(TupleDescriptor x, TupleDescriptor y) => throw new NotSupportedException(); diff --git a/Orm/Xtensive.Orm/Comparison/Internals/TypeComparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/TypeComparer.cs index ada19dc97..118291666 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/TypeComparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/TypeComparer.cs @@ -21,8 +21,7 @@ internal sealed class TypeComparer: WrappingComparer, [NonSerialized] private ConcurrentDictionary<(Type, Type, TypeComparer), int> results; - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new TypeComparer(Provider, ComparisonRules.Combine(rules)); + protected override TypeComparer CreateNew(ComparisonRules rules) => new TypeComparer(Provider, ComparisonRules.Combine(rules)); public override int Compare(Type x, Type y) { diff --git a/Orm/Xtensive.Orm/Comparison/Internals/UInt16Comparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/UInt16Comparer.cs index 19c230f0f..750ba0171 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/UInt16Comparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/UInt16Comparer.cs @@ -12,8 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class UInt16Comparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new UInt16Comparer(Provider, ComparisonRules.Combine(rules)); + protected override UInt16Comparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Comparison/Internals/UInt32Comparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/UInt32Comparer.cs index 31c0fecb5..37522d85d 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/UInt32Comparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/UInt32Comparer.cs @@ -12,8 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class UInt32Comparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new UInt32Comparer(Provider, ComparisonRules.Combine(rules)); + protected override UInt32Comparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Comparison/Internals/UInt64Comparer.cs b/Orm/Xtensive.Orm/Comparison/Internals/UInt64Comparer.cs index 5fc58bfe5..e928554ff 100644 --- a/Orm/Xtensive.Orm/Comparison/Internals/UInt64Comparer.cs +++ b/Orm/Xtensive.Orm/Comparison/Internals/UInt64Comparer.cs @@ -12,8 +12,7 @@ namespace Xtensive.Comparison [Serializable] internal sealed class UInt64Comparer : ValueTypeComparer { - protected override IAdvancedComparer CreateNew(ComparisonRules rules) - => new UInt64Comparer(Provider, ComparisonRules.Combine(rules)); + protected override UInt64Comparer CreateNew(ComparisonRules rules) => new(Provider, ComparisonRules.Combine(rules)); // Constructors diff --git a/Orm/Xtensive.Orm/Conversion/Internals/NullableForwardAdvancedConverter.cs b/Orm/Xtensive.Orm/Conversion/Internals/NullableForwardAdvancedConverter.cs index c494ef258..2a41fa4b1 100644 --- a/Orm/Xtensive.Orm/Conversion/Internals/NullableForwardAdvancedConverter.cs +++ b/Orm/Xtensive.Orm/Conversion/Internals/NullableForwardAdvancedConverter.cs @@ -18,7 +18,7 @@ internal sealed class NullableForwardAdvancedConverter : WrappingAdv public override TTo Convert(TFrom? value) { if (toIsValueType && !value.HasValue) - throw new ArgumentNullException("value"); + throw new ArgumentNullException(nameof(value)); return BaseConverter.Convert(value.GetValueOrDefault()); } diff --git a/Orm/Xtensive.Orm/Core/Extensions/CollectionExtensions.cs b/Orm/Xtensive.Orm/Core/Extensions/CollectionExtensions.cs index 872fc604d..aac676773 100644 --- a/Orm/Xtensive.Orm/Core/Extensions/CollectionExtensions.cs +++ b/Orm/Xtensive.Orm/Core/Extensions/CollectionExtensions.cs @@ -34,9 +34,9 @@ public static void Copy(this ICollection source, TItem[] target, i ArgumentNullException.ThrowIfNull(source); ArgumentNullException.ThrowIfNull(target); if (targetIndex < 0 || targetIndex > target.Length) - throw new ArgumentOutOfRangeException("targetIndex"); + throw new ArgumentOutOfRangeException(nameof(targetIndex)); if ((target.Length - targetIndex) < source.Count) - throw new ArgumentException(Strings.ExDestionationArrayIsTooSmall, "target"); + throw new ArgumentException(Strings.ExDestionationArrayIsTooSmall, nameof(target)); foreach (TItem item in source) target[targetIndex++] = item; @@ -58,11 +58,11 @@ public static void Copy(this ICollection source, Array target, int ArgumentNullException.ThrowIfNull(source); ArgumentNullException.ThrowIfNull(target); if (targetIndex < 0 || targetIndex > target.Length) - throw new ArgumentOutOfRangeException("targetIndex"); + throw new ArgumentOutOfRangeException(nameof(targetIndex)); if ((target.Length - targetIndex) < source.Count) - throw new ArgumentException(Strings.ExDestionationArrayIsTooSmall, "target"); + throw new ArgumentException(Strings.ExDestionationArrayIsTooSmall, nameof(target)); if (target.Rank != 1) - throw new ArgumentException(Strings.ExArrayIsMultidimensional, "target"); + throw new ArgumentException(Strings.ExArrayIsMultidimensional, nameof(target)); // if (target.GetType().GetElementType().IsAssignableFrom(typeof(T))) // throw new ArgumentException(Strings.ExIncompatibleArrayType, "target"); diff --git a/Orm/Xtensive.Orm/Core/Extensions/ExpressionExtensions.cs b/Orm/Xtensive.Orm/Core/Extensions/ExpressionExtensions.cs index 18e6ef4da..8cc0068e3 100644 --- a/Orm/Xtensive.Orm/Core/Extensions/ExpressionExtensions.cs +++ b/Orm/Xtensive.Orm/Core/Extensions/ExpressionExtensions.cs @@ -178,7 +178,7 @@ public static MemberInfo GetMember(this Expression expression) var me = expression as MemberExpression; if (me==null) throw new ArgumentException( - string.Format(Strings.ExInvalidArgumentType, typeof (MemberExpression)), "expression"); + string.Format(Strings.ExInvalidArgumentType, typeof (MemberExpression)), nameof(expression)); return me.Member; } @@ -227,7 +227,7 @@ public static MethodInfo GetMethod(this Expression expression) var mce = expression as MethodCallExpression; if (mce==null) throw new ArgumentException( - string.Format(Strings.ExInvalidArgumentType, typeof (MethodCallExpression)), "expression"); + string.Format(Strings.ExInvalidArgumentType, typeof (MethodCallExpression)), nameof(expression)); return mce.Method; } @@ -244,7 +244,7 @@ public static PropertyInfo GetIndexer(this Expression expression) var ie = expression as IndexExpression; if (ie==null) throw new ArgumentException( - string.Format(Strings.ExInvalidArgumentType, typeof (IndexExpression)), "expression"); + string.Format(Strings.ExInvalidArgumentType, typeof (IndexExpression)), nameof(expression)); return ie.Indexer; } @@ -261,7 +261,7 @@ public static ConstructorInfo GetConstructor(this Expression expression) var ne = expression as NewExpression; if (ne==null) throw new ArgumentException( - string.Format(Strings.ExInvalidArgumentType, typeof (NewExpression)), "expression"); + string.Format(Strings.ExInvalidArgumentType, typeof (NewExpression)), nameof(expression)); return ne.Constructor; } diff --git a/Orm/Xtensive.Orm/Core/Extensions/ListExtensions.cs b/Orm/Xtensive.Orm/Core/Extensions/ListExtensions.cs index d0c24d4b0..af53e270c 100644 --- a/Orm/Xtensive.Orm/Core/Extensions/ListExtensions.cs +++ b/Orm/Xtensive.Orm/Core/Extensions/ListExtensions.cs @@ -59,9 +59,9 @@ public static void Copy(this IList source, TItem[] target, int tar ArgumentNullException.ThrowIfNull(source); ArgumentNullException.ThrowIfNull(target); if (targetIndex < 0 || targetIndex > target.Length) - throw new ArgumentOutOfRangeException("targetIndex"); + throw new ArgumentOutOfRangeException(nameof(targetIndex)); if ((target.Length - targetIndex) < source.Count) - throw new ArgumentException(Strings.ExDestionationArrayIsTooSmall, "target"); + throw new ArgumentException(Strings.ExDestionationArrayIsTooSmall, nameof(target)); int count = source.Count; for (int i = 0; i < count; i++) @@ -84,11 +84,11 @@ public static void Copy(this IList source, Array target, int targe ArgumentNullException.ThrowIfNull(source); ArgumentNullException.ThrowIfNull(target); if (targetIndex < 0 || targetIndex > target.Length) - throw new ArgumentOutOfRangeException("targetIndex"); + throw new ArgumentOutOfRangeException(nameof(targetIndex)); if ((target.Length - targetIndex) < source.Count) - throw new ArgumentException(Strings.ExDestionationArrayIsTooSmall, "target"); + throw new ArgumentException(Strings.ExDestionationArrayIsTooSmall, nameof(target)); if (target.Rank != 1) - throw new ArgumentException(Strings.ExArrayIsMultidimensional, "target"); + throw new ArgumentException(Strings.ExArrayIsMultidimensional, nameof(target)); // if (target.GetType().GetElementType().IsAssignableFrom(typeof(T))) // throw new ArgumentException(Strings.ExIncompatibleArrayType, "target"); diff --git a/Orm/Xtensive.Orm/Core/Extensions/StringBuilderExtensions.cs b/Orm/Xtensive.Orm/Core/Extensions/StringBuilderExtensions.cs index 51b56a2e7..723c46a80 100644 --- a/Orm/Xtensive.Orm/Core/Extensions/StringBuilderExtensions.cs +++ b/Orm/Xtensive.Orm/Core/Extensions/StringBuilderExtensions.cs @@ -16,6 +16,7 @@ namespace Xtensive.Core public static class StringBuilderExtensions { private const char IndentChar = ' '; + private const string LowerHexChars = "0123456789abcdef"; /// /// Appends the specified indented by specified count of spaces. @@ -79,10 +80,9 @@ public static StringBuilder AppendHexArray(this StringBuilder builder, byte[] va ArgumentNullException.ThrowIfNull(builder); ArgumentNullException.ThrowIfNull(values); - const string lowerHexChars = "0123456789abcdef"; foreach (var item in values) { - _ = builder.Append(lowerHexChars[item >> 4]) - .Append(lowerHexChars[item & 0xF]); + _ = builder.Append(LowerHexChars[item >> 4]) + .Append(LowerHexChars[item & 0xF]); } return builder; } @@ -99,10 +99,9 @@ public static StringBuilder AppendHexArray(this StringBuilder builder, in ReadOn { ArgumentNullException.ThrowIfNull(builder); - const string lowerHexChars = "0123456789abcdef"; foreach (var item in values) { - _ = builder.Append(lowerHexChars[item >> 4]) - .Append(lowerHexChars[item & 0xF]); + _ = builder.Append(LowerHexChars[item >> 4]) + .Append(LowerHexChars[item & 0xF]); } return builder; } diff --git a/Orm/Xtensive.Orm/Core/Extensions/TaskExtensions.cs b/Orm/Xtensive.Orm/Core/Extensions/TaskExtensions.cs index 56f914768..d592011f0 100644 --- a/Orm/Xtensive.Orm/Core/Extensions/TaskExtensions.cs +++ b/Orm/Xtensive.Orm/Core/Extensions/TaskExtensions.cs @@ -1,30 +1,26 @@ -using System; -using System.Collections.Generic; using System.Runtime.CompilerServices; -using System.Threading.Tasks; -namespace Xtensive.Core +namespace Xtensive.Core; + +public static class TaskExtensions { - public static class TaskExtensions - { #if DO_CONFIGURE_AWAIT_FALSE - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredTaskAwaitable ConfigureAwaitFalse(this Task task) => task.ConfigureAwait(false); - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredTaskAwaitable ConfigureAwaitFalse(this Task task) => task.ConfigureAwait(false); - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredValueTaskAwaitable ConfigureAwaitFalse(this ValueTask task) => task.ConfigureAwait(false); - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredValueTaskAwaitable ConfigureAwaitFalse(this ValueTask task) => task.ConfigureAwait(false); - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredAsyncDisposable ConfigureAwaitFalse(this IAsyncDisposable source) => source.ConfigureAwait(false); - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredCancelableAsyncEnumerable ConfigureAwaitFalse(this IAsyncEnumerable source) => source.ConfigureAwait(false); - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredAsyncDisposable ConfigureAwaitFalse(this T source) where T: struct, IAsyncDisposable => source.ConfigureAwait(false);; - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredCancelableAsyncEnumerable ConfigureAwaitFalse(this ConfiguredCancelableAsyncEnumerable source) => source.ConfigureAwait(false); + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredTaskAwaitable ConfigureAwaitFalse(this Task task) => task.ConfigureAwait(false); + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredTaskAwaitable ConfigureAwaitFalse(this Task task) => task.ConfigureAwait(false); + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredValueTaskAwaitable ConfigureAwaitFalse(this ValueTask task) => task.ConfigureAwait(false); + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredValueTaskAwaitable ConfigureAwaitFalse(this ValueTask task) => task.ConfigureAwait(false); + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredAsyncDisposable ConfigureAwaitFalse(this IAsyncDisposable source) => source.ConfigureAwait(false); + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredCancelableAsyncEnumerable ConfigureAwaitFalse(this IAsyncEnumerable source) => source.ConfigureAwait(false); + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredAsyncDisposable ConfigureAwaitFalse(this T source) where T: struct, IAsyncDisposable => source.ConfigureAwait(false);; + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredCancelableAsyncEnumerable ConfigureAwaitFalse(this ConfiguredCancelableAsyncEnumerable source) => source.ConfigureAwait(false); #else - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static Task ConfigureAwaitFalse(this Task task) => task; - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static Task ConfigureAwaitFalse(this Task task) => task; - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ValueTask ConfigureAwaitFalse(this ValueTask task) => task; - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ValueTask ConfigureAwaitFalse(this ValueTask task) => task; - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static IAsyncDisposable ConfigureAwaitFalse(this IAsyncDisposable source) => source; - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static IAsyncEnumerable ConfigureAwaitFalse(this IAsyncEnumerable source) => source; - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static T ConfigureAwaitFalse(this T source) where T: struct, IAsyncDisposable => source; - [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredCancelableAsyncEnumerable ConfigureAwaitFalse(this ConfiguredCancelableAsyncEnumerable source) => source; + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static Task ConfigureAwaitFalse(this Task task) => task; + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static Task ConfigureAwaitFalse(this Task task) => task; + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ValueTask ConfigureAwaitFalse(this ValueTask task) => task; + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ValueTask ConfigureAwaitFalse(this ValueTask task) => task; + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static IAsyncDisposable ConfigureAwaitFalse(this IAsyncDisposable source) => source; + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static IAsyncEnumerable ConfigureAwaitFalse(this IAsyncEnumerable source) => source; + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static T ConfigureAwaitFalse(this T source) where T: struct, IAsyncDisposable => source; + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static ConfiguredCancelableAsyncEnumerable ConfigureAwaitFalse(this ConfiguredCancelableAsyncEnumerable source) => source; #endif - } } diff --git a/Orm/Xtensive.Orm/Core/Parameter.cs b/Orm/Xtensive.Orm/Core/Parameter.cs index 7ea6ab45d..1dac4472d 100644 --- a/Orm/Xtensive.Orm/Core/Parameter.cs +++ b/Orm/Xtensive.Orm/Core/Parameter.cs @@ -4,6 +4,7 @@ // Created by: Alex Kofman // Created: 2008.08.14 +using System; using System.Diagnostics; diff --git a/Orm/Xtensive.Orm/Core/Segment.cs b/Orm/Xtensive.Orm/Core/Segment.cs index 15dc56ade..4865da7dc 100644 --- a/Orm/Xtensive.Orm/Core/Segment.cs +++ b/Orm/Xtensive.Orm/Core/Segment.cs @@ -44,26 +44,26 @@ public T EndOffset { } /// - public bool Equals((T, T) other) + public bool Equals(Segment other) { - return AdvancedComparerStruct.System.Equals(Offset, other.Item1) && - AdvancedComparerStruct.System.Equals(Length, other.Item2); + return AdvancedComparerStruct.System.Equals(Offset, other.Offset) && + AdvancedComparerStruct.System.Equals(Length, other.Length); } /// - public int CompareTo((T, T) other) + public int CompareTo(Segment other) { - int result = AdvancedComparerStruct.System.Compare(Offset, other.Item1); + int result = AdvancedComparerStruct.System.Compare(Offset, other.Offset); if (result!=0) return result; - return AdvancedComparerStruct.System.Compare(Length, other.Item2); + return AdvancedComparerStruct.System.Compare(Length, other.Length); } #region Equals, GetHashCode /// public override bool Equals(object obj) => - obj is ValueTuple other && Equals(other); + obj is Segment other && Equals(other); /// public override int GetHashCode() => HashCode.Combine(Offset, Length); diff --git a/Orm/Xtensive.Orm/Core/SimpleXmlSerializer.cs b/Orm/Xtensive.Orm/Core/SimpleXmlSerializer.cs index 303ccf1af..d53f9fa62 100644 --- a/Orm/Xtensive.Orm/Core/SimpleXmlSerializer.cs +++ b/Orm/Xtensive.Orm/Core/SimpleXmlSerializer.cs @@ -4,6 +4,7 @@ // Created by: Denis Krjuchkov // Created: 2013.07.18 +using System; using System.IO; using System.Text; using System.Xml; @@ -32,7 +33,7 @@ public sealed class SimpleXmlSerializer /// Deserialized instance. public T Deserialize(string value) { - ArgumentNullException.ThrowIfNull(value, "serialized"); + ArgumentNullException.ThrowIfNull(value); using StringReader reader = new(value); return (T) serializer.Deserialize(reader); diff --git a/Orm/Xtensive.Orm/Core/SynchronousFutureResult.cs b/Orm/Xtensive.Orm/Core/SynchronousFutureResult.cs index 994ee49de..a9c9c21ee 100644 --- a/Orm/Xtensive.Orm/Core/SynchronousFutureResult.cs +++ b/Orm/Xtensive.Orm/Core/SynchronousFutureResult.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2014-2020 Xtensive LLC. +// Copyright (C) 2014-2020 Xtensive LLC. // This code is distributed under MIT license terms. // See the License.txt file in the project root for more information. // Created by: Denis Krjuchkov diff --git a/Orm/Xtensive.Orm/IoC/ServiceContainer.cs b/Orm/Xtensive.Orm/IoC/ServiceContainer.cs index 8f34d651f..55acc79e3 100644 --- a/Orm/Xtensive.Orm/IoC/ServiceContainer.cs +++ b/Orm/Xtensive.Orm/IoC/ServiceContainer.cs @@ -179,7 +179,7 @@ public static IServiceContainer Create(Type containerType, object configuration, ArgumentNullException.ThrowIfNull(containerType); if (!iServiceContainerType.IsAssignableFrom(containerType)) throw new ArgumentException(string.Format( - Strings.ExContainerTypeMustImplementX, iServiceContainerType.Name), "containerType"); + Strings.ExContainerTypeMustImplementX, iServiceContainerType.Name)); Type configurationType = configuration?.GetType(), parentType = parent?.GetType(); @@ -187,7 +187,7 @@ public static IServiceContainer Create(Type containerType, object configuration, FindConstructorInvoker(containerType, configurationType, parentType)?.Invoke(configuration, parent) ?? FindConstructorInvoker(containerType, configurationType)?.Invoke(configuration) ?? FindConstructorInvoker(containerType, parentType)?.Invoke(parent) - ?? throw new ArgumentException(Strings.ExContainerTypeDoesNotProvideASuitableConstructor, "containerType") + ?? throw new ArgumentException(Strings.ExContainerTypeDoesNotProvideASuitableConstructor, nameof(containerType)) ); } diff --git a/Orm/Xtensive.Orm/Linq/ExpressionVisitor.cs b/Orm/Xtensive.Orm/Linq/ExpressionVisitor.cs index 29c4b3190..59f83d65e 100644 --- a/Orm/Xtensive.Orm/Linq/ExpressionVisitor.cs +++ b/Orm/Xtensive.Orm/Linq/ExpressionVisitor.cs @@ -21,7 +21,7 @@ public abstract class ExpressionVisitor(bool isCaching = false) : System.Linq.Ex { private readonly Dictionary cache = isCaching ? new() : null; - protected virtual IEnumerable VisitExpressionList(IReadOnlyList expressions) => + protected virtual IReadOnlyList VisitExpressionList(IReadOnlyList expressions) => VisitList(expressions, Visit); public override Expression Visit(Expression e) @@ -72,6 +72,24 @@ protected virtual ElementInit VisitElementInitializer(ElementInit initializer) protected virtual IEnumerable VisitElementInitializerList(ReadOnlyCollection original) => VisitList(original, VisitElementInitializer); + /// + /// Visits the element initializer list. + /// + /// The original element initializer list. + /// Visit result. + protected virtual IReadOnlyList VisitElementInitializerList(IReadOnlyList original) + { + var results = new ElementInit[original.Count]; + bool isChanged = false; + for (int i = 0, n = original.Count; i < n; i++) { + var originalIntializer = original[i]; + ElementInit p = VisitElementInitializer(originalIntializer); + results[i] = p; + isChanged |= !ReferenceEquals(originalIntializer, p); + } + return isChanged ? results : original; + } + /// protected override Expression VisitUnary(UnaryExpression u) => u.Update(Visit(u.Operand)); @@ -236,12 +254,12 @@ protected override MemberMemberBinding VisitMemberMemberBinding(MemberMemberBind /// /// The original binding list. /// Visit result. - protected virtual IEnumerable VisitBindingList(ReadOnlyCollection original) => + protected virtual IReadOnlyList VisitBindingList(ReadOnlyCollection original) => VisitList(original, VisitBinding); - public static IEnumerable VisitList(IReadOnlyList original, Func func) where T : class + public static IReadOnlyList VisitList(IReadOnlyList original, Func func) where T : class { - for (int i = 0, n = original.Count; i < n; ++i) { + for (int i = 0, n = original.Count; i < n; i++) { var originalValue = original[i]; if (func(originalValue) is var p && !ReferenceEquals(p, originalValue)) { return VisitListIterator(original, func, p, i); @@ -250,22 +268,41 @@ public static IEnumerable VisitList(IReadOnlyList original, Func return original; } - private static IEnumerable VisitListIterator(IReadOnlyList original, Func func, T p, int pIdx) where T : class + private static IReadOnlyList VisitListIterator(IReadOnlyList original, Func func, T p, int pIdx) where T : class { + T[] result = new T[original.Count]; for (var i = 0; i < pIdx; ++i) { - yield return original[i]; + result[i] = original[i]; } - yield return p; + result[pIdx] = p; for (int i = pIdx + 1, n = original.Count; i < n; ++i) { - yield return func(original[i]); + result[i] = func(original[i]); } + return result; } + /// + /// Visits the binding list. + /// + /// The original binding list. + /// Visit result. + protected virtual IReadOnlyList VisitBindingList(IReadOnlyList original) + { + var results = new MemberBinding[original.Count]; + bool isChanged = false; + for (int i = 0, n = original.Count; i < n; i++) { + var originalBinding = original[i]; + MemberBinding p = VisitBinding(originalBinding); + results[i] = p; + isChanged |= !ReferenceEquals(originalBinding, p); + } + return isChanged ? results : original; + } + protected override MemberListBinding VisitMemberListBinding(MemberListBinding binding) { - var bindingInitializers = binding.Initializers; - IEnumerable initializers = VisitElementInitializerList(bindingInitializers); - if (initializers != bindingInitializers) + IEnumerable initializers = VisitElementInitializerList((IReadOnlyList) binding.Initializers); + if (initializers!=binding.Initializers) return Expression.ListBind(binding.Member, initializers); return binding; } diff --git a/Orm/Xtensive.Orm/Linq/ExpressionVisitor{TResult}.cs b/Orm/Xtensive.Orm/Linq/ExpressionVisitor{TResult}.cs index c3348d122..348f5a2a1 100644 --- a/Orm/Xtensive.Orm/Linq/ExpressionVisitor{TResult}.cs +++ b/Orm/Xtensive.Orm/Linq/ExpressionVisitor{TResult}.cs @@ -95,6 +95,35 @@ or ExpressionType.LeftShift return result; } + /// + /// Visits the expression list. + /// + /// The expression list. + /// Visit result. + protected virtual ReadOnlyCollection VisitExpressionList(ReadOnlyCollection expressions) + { + var results = new List(expressions.Count); + for (int i = 0, n = expressions.Count; i < n; i++) { + var p = Visit(expressions[i]); + results.Add(p); + } + return results.AsReadOnly(); + } + + /// + /// Visits the expression list. + /// + /// The expression list. + /// Visit result. + protected virtual IReadOnlyList VisitExpressionList(IReadOnlyList expressions) + { + var results = new TResult[expressions.Count]; + for (int i = 0, n = expressions.Count; i < n; i++) { + results[i] = Visit(expressions[i]); + } + return results; + } + /// /// Visits the unknown expression. /// diff --git a/Orm/Xtensive.Orm/Linq/ExpressionWriter.cs b/Orm/Xtensive.Orm/Linq/ExpressionWriter.cs index dcff74ab8..babbc4523 100644 --- a/Orm/Xtensive.Orm/Linq/ExpressionWriter.cs +++ b/Orm/Xtensive.Orm/Linq/ExpressionWriter.cs @@ -4,12 +4,9 @@ // Created by: Alexey Kochetov // Created: 2008.11.25 -using System; using System.Collections; -using System.Collections.Generic; using System.Diagnostics; using System.IO; -using System.Linq; using System.Linq.Expressions; using System.Runtime.CompilerServices; using Xtensive.Core; @@ -444,8 +441,21 @@ protected override System.Collections.ObjectModel.ReadOnlyCollection - protected override IReadOnlyList VisitExpressionList( - IReadOnlyList expressions) + protected override IReadOnlyList VisitElementInitializerList(IReadOnlyList original) + { + for (int i = 0, n = original.Count; i < n; i++) { + VisitElementInitializer(original[i]); + if (i < n - 1) { + Write(","); + WriteLine(IndentType.Same); + } + } + + return original; + } + + /// + protected override IReadOnlyList VisitExpressionList(IReadOnlyList expressions) { for (int i = 0, n = expressions.Count; i < n; i++) { Visit(expressions[i]); @@ -578,7 +588,7 @@ protected override MethodCallExpression VisitMethodCall(MethodCallExpression mc) if (mc.Method.GetAttributes(AttributeSearchOptions.InheritNone).Count > 0) { // A special case: extension method Visit(mc.Arguments[0]); - arguments = new System.Collections.ObjectModel.ReadOnlyCollection(mc.Arguments.Skip(1).ToList()); + arguments = new System.Collections.ObjectModel.ReadOnlyCollection(mc.Arguments.Skip(1).ToList(mc.Arguments.Count - 1)); } else { Write(GetTypeName(mc.Method.DeclaringType)); diff --git a/Orm/Xtensive.Orm/Linq/SerializableExpressions/Internals/ExpressionToSerializableExpressionConverter.cs b/Orm/Xtensive.Orm/Linq/SerializableExpressions/Internals/ExpressionToSerializableExpressionConverter.cs index df87b52d0..62175aba9 100644 --- a/Orm/Xtensive.Orm/Linq/SerializableExpressions/Internals/ExpressionToSerializableExpressionConverter.cs +++ b/Orm/Xtensive.Orm/Linq/SerializableExpressions/Internals/ExpressionToSerializableExpressionConverter.cs @@ -192,53 +192,45 @@ protected override SerializableInvocationExpression VisitInvocation(InvocationEx #region Private / internal methods - private SerializableMemberBinding[] VisitMemberBindingSequence(IEnumerable bindings) - { - var result = new List(); - foreach (var binding in bindings) - switch (binding.BindingType) { - case MemberBindingType.Assignment: - result.Add(new SerializableMemberAssignment - { - BindingType = MemberBindingType.Assignment, - Member = binding.Member, - Expression = Visit(((MemberAssignment) binding).Expression) - }); - break; - case MemberBindingType.ListBinding: - result.Add(new SerializableMemberListBinding - { - BindingType = MemberBindingType.ListBinding, - Member = binding.Member, - Initializers = VisitElementInitSequence(((MemberListBinding) binding).Initializers) - }); - break; - case MemberBindingType.MemberBinding: - result.Add(new SerializableMemberMemberBinding - { - BindingType = MemberBindingType.MemberBinding, - Member = binding.Member, - Bindings = VisitMemberBindingSequence(((MemberMemberBinding) binding).Bindings) - }); - break; - default: - throw new ArgumentOutOfRangeException(); - } - return result.ToArray(); - } - - private SerializableElementInit[] VisitElementInitSequence(IEnumerable initializers) + private SerializableMemberBinding[] VisitMemberBindingSequence(IReadOnlyList bindings) + { + var arrayResult = new SerializableMemberBinding[bindings.Count]; + for (int i = 0, count = bindings.Count; i < count; i++) { + var binding = bindings[i]; + arrayResult[i] = binding.BindingType switch { + MemberBindingType.Assignment => new SerializableMemberAssignment() { + BindingType = MemberBindingType.Assignment, + Member = binding.Member, + Expression = Visit(((MemberAssignment) binding).Expression) + }, + MemberBindingType.ListBinding => new SerializableMemberListBinding { + BindingType = MemberBindingType.ListBinding, + Member = binding.Member, + Initializers = VisitElementInitSequence(((MemberListBinding) binding).Initializers) + }, + MemberBindingType.MemberBinding => new SerializableMemberMemberBinding { + BindingType = MemberBindingType.MemberBinding, + Member = binding.Member, + Bindings = VisitMemberBindingSequence(((MemberMemberBinding) binding).Bindings) + }, + _ => throw new ArgumentOutOfRangeException() + + }; + } + return arrayResult; + } + + private SerializableElementInit[] VisitElementInitSequence(IList initializers) { return initializers .Select(initializer => new SerializableElementInit { AddMethod = initializer.AddMethod, Arguments = VisitExpressionSequence(initializer.Arguments) - }) - .ToArray(); + }).ToArray(); } - private SerializableExpression[] VisitExpressionSequence(IEnumerable expressions) + private SerializableExpression[] VisitExpressionSequence(IList expressions) where T : Expression { return expressions.Select(e => Visit(e)).ToArray(); @@ -252,4 +244,4 @@ public ExpressionToSerializableExpressionConverter(Expression source) this.source = source; } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Linq/SerializableExpressions/Internals/SerializableExpressionToExpressionConverter.cs b/Orm/Xtensive.Orm/Linq/SerializableExpressions/Internals/SerializableExpressionToExpressionConverter.cs index 2c981cf36..97c83e02a 100644 --- a/Orm/Xtensive.Orm/Linq/SerializableExpressions/Internals/SerializableExpressionToExpressionConverter.cs +++ b/Orm/Xtensive.Orm/Linq/SerializableExpressions/Internals/SerializableExpressionToExpressionConverter.cs @@ -9,6 +9,7 @@ using System.Linq; using System.Linq.Expressions; using System.Reflection; +using Xtensive.Core; namespace Xtensive.Linq.SerializableExpressions.Internals { @@ -200,7 +201,7 @@ private Expression VisitMethodCall(SerializableMethodCallExpression mc) private Expression VisitLambda(SerializableLambdaExpression l) { - var parameters = l.Parameters.Select(p => (ParameterExpression) Visit(p)).ToList(); + var parameters = l.Parameters.Select(p => (ParameterExpression) Visit(p)).ToArray(); using (CreateParameterScope(parameters)) { return FastExpression.Lambda(l.Type, Visit(l.Body), parameters); } @@ -319,4 +320,4 @@ public SerializableExpressionToExpressionConverter(SerializableExpression source parameterScopes = new Stack>(); } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Modelling/Comparison/Comparer.cs b/Orm/Xtensive.Orm/Modelling/Comparison/Comparer.cs index 4f3eb8407..0af7e3873 100644 --- a/Orm/Xtensive.Orm/Modelling/Comparison/Comparer.cs +++ b/Orm/Xtensive.Orm/Modelling/Comparison/Comparer.cs @@ -491,7 +491,7 @@ from diff in newDiffs let nodeDiff = diff as NodeDifference where nodeDiff!=null && (nodeDiff.MovementInfo & MovementInfo.Changed)!=0 select nodeDiff; - // query = query.ToList(); + return query.Any(); } diff --git a/Orm/Xtensive.Orm/Modelling/Comparison/Upgrader.cs b/Orm/Xtensive.Orm/Modelling/Comparison/Upgrader.cs index f8333e7ec..7a39e5d7c 100644 --- a/Orm/Xtensive.Orm/Modelling/Comparison/Upgrader.cs +++ b/Orm/Xtensive.Orm/Modelling/Comparison/Upgrader.cs @@ -129,7 +129,7 @@ public IReadOnlyList GetUpgradeSequence(Difference difference, HintS SourceModel = (IModel) difference.Source; TargetModel = (IModel) difference.Target; Hints = hints ?? new HintSet(SourceModel, TargetModel); - Comparer = comparer; + Comparer = comparer ?? throw new ArgumentNullException(nameof(comparer)); if (Hints.SourceModel != SourceModel) { throw new ArgumentOutOfRangeException("hints.SourceModel"); } diff --git a/Orm/Xtensive.Orm/Modelling/NodeCollection.cs b/Orm/Xtensive.Orm/Modelling/NodeCollection.cs index 5104edfde..76710a883 100644 --- a/Orm/Xtensive.Orm/Modelling/NodeCollection.cs +++ b/Orm/Xtensive.Orm/Modelling/NodeCollection.cs @@ -373,7 +373,7 @@ protected NodeCollection(Node parent, string name) ArgumentNullException.ThrowIfNull(parent); ArgumentException.ThrowIfNullOrEmpty(name); this.name = name; - this.parent = parent; + this.parent = parent ?? throw new ArgumentNullException(nameof(parent)); Initialize(); } diff --git a/Orm/Xtensive.Orm/Orm/Building/Builders/DomainBuilder.cs b/Orm/Xtensive.Orm/Orm/Building/Builders/DomainBuilder.cs index b08be911b..0a44205a3 100644 --- a/Orm/Xtensive.Orm/Orm/Building/Builders/DomainBuilder.cs +++ b/Orm/Xtensive.Orm/Orm/Building/Builders/DomainBuilder.cs @@ -4,6 +4,7 @@ // Created by: Dmitri Maximov // Created: 2007.08.03 +using System; using System.Collections.Generic; using System.Linq; using Xtensive.Core; diff --git a/Orm/Xtensive.Orm/Orm/Building/Builders/ModelBuilder.cs b/Orm/Xtensive.Orm/Orm/Building/Builders/ModelBuilder.cs index 12504c0de..ff8089a34 100644 --- a/Orm/Xtensive.Orm/Orm/Building/Builders/ModelBuilder.cs +++ b/Orm/Xtensive.Orm/Orm/Building/Builders/ModelBuilder.cs @@ -172,7 +172,8 @@ private void BuildPrefetchActions() foreach (var type in context.Model.Types.Entities) { var associations = type.GetOwnerAssociations() .Where(static a => a.OnOwnerRemove is OnRemoveAction.Cascade or OnRemoveAction.Clear); - if (PrefetchActionContainer.BuildPrefetchAction(type, associations) is { } action) { + var action = new PrefetchActionContainer(type).BuildPrefetchAction(associations); + if (action != null) { domain.PrefetchActionMap.Add(type, action); } } diff --git a/Orm/Xtensive.Orm/Orm/Building/Builders/StorageMappingBuilder.cs b/Orm/Xtensive.Orm/Orm/Building/Builders/StorageMappingBuilder.cs index 867af82e2..70ce5d914 100644 --- a/Orm/Xtensive.Orm/Orm/Building/Builders/StorageMappingBuilder.cs +++ b/Orm/Xtensive.Orm/Orm/Building/Builders/StorageMappingBuilder.cs @@ -69,7 +69,7 @@ private readonly Dictionary mappingCache = new Dictionary(); private readonly bool verbose; - private readonly List mappingRules; + private readonly MappingRule[] mappingRules; private readonly string defaultDatabase; private readonly string defaultSchema; @@ -133,12 +133,16 @@ private static bool RuleMatch(MappingRule rule, Type type) private StorageMappingBuilder(BuildingContext context) { this.context = context; + var configuration = context.Configuration; // Adding a special catch-all rule that maps all types to default schema/database. - - mappingRules = context.Configuration.MappingRules - .Concat(Enumerable.Repeat(new MappingRule(null, null, null, null), 1)) - .ToList(); + if (configuration.MappingRules.Count == 0) + mappingRules = new[] { new MappingRule(null, null, null, null) }; + else { + mappingRules = new MappingRule[context.Configuration.MappingRules.Count + 1]; + configuration.MappingRules.CopyTo(mappingRules, 0); + mappingRules[^1] = new MappingRule(null, null, null, null); + } defaultDatabase = context.Configuration.DefaultDatabase ?? string.Empty; defaultSchema = context.Configuration.DefaultSchema ?? string.Empty; diff --git a/Orm/Xtensive.Orm/Orm/Building/FixupActionProcessor.cs b/Orm/Xtensive.Orm/Orm/Building/FixupActionProcessor.cs index f3b86d026..15efc4809 100644 --- a/Orm/Xtensive.Orm/Orm/Building/FixupActionProcessor.cs +++ b/Orm/Xtensive.Orm/Orm/Building/FixupActionProcessor.cs @@ -7,6 +7,7 @@ using System; using System.Collections.Generic; using System.Linq; +using Xtensive.Core; using Xtensive.Orm.Building.Builders; using Xtensive.Orm.Building.Definitions; using Xtensive.Orm.Building.DependencyGraph; @@ -92,9 +93,8 @@ public void Process(BuildGenericTypeInstancesAction action) var typeSubstitutions = new Type[arguments.Length][]; for (var i = 0; i < arguments.Length; i++) { var argument = arguments[i]; - var constraints = argument.GetGenericParameterConstraints() - .ToList(); - if (constraints.Count==0 || !constraints.Any(c => WellKnownOrmInterfaces.Entity.IsAssignableFrom(c))) + var constraints = argument.GetGenericParameterConstraints(); + if (constraints.Length==0 || !constraints.Any(c => WellKnownOrmInterfaces.Entity.IsAssignableFrom(c))) return; // No IEntity / Entity constraints var queue = new Queue( from hierarchy in hierarchies diff --git a/Orm/Xtensive.Orm/Orm/Building/PrefetchActionContainer.cs b/Orm/Xtensive.Orm/Orm/Building/PrefetchActionContainer.cs index d265f44e9..e8ed4e832 100644 --- a/Orm/Xtensive.Orm/Orm/Building/PrefetchActionContainer.cs +++ b/Orm/Xtensive.Orm/Orm/Building/PrefetchActionContainer.cs @@ -11,20 +11,28 @@ namespace Xtensive.Orm.Building; [Serializable] -internal static class PrefetchActionContainer +internal class PrefetchActionContainer { + private readonly TypeInfo type; + private IReadOnlyList fields; + // Returns null if associations is empty - public static Action> BuildPrefetchAction(TypeInfo type, IEnumerable associations) + public Action> BuildPrefetchAction(IEnumerable associations) + { + fields = associations.Select(static association => new PrefetchFieldDescriptor(association.OwnerField, true, false)) + .ToArray(); + return fields.Count > 0 ? Prefetch : null; + } + + private void Prefetch(SessionHandler sh, IEnumerable keys) { - var fields = associations.Select(static association => new PrefetchFieldDescriptor(association.OwnerField, true, false)).ToArray(); - return fields.Length > 0 - ? Prefetch - : null; + foreach (var key in keys) + sh.Prefetch(key, type, fields); + } - void Prefetch(SessionHandler sh, IEnumerable keys) - { - foreach (var key in keys) - sh.Prefetch(key, type, fields); - } + public PrefetchActionContainer(TypeInfo type) + { + this.type = type; + fields = Array.Empty(); } } diff --git a/Orm/Xtensive.Orm/Orm/Configuration/DatabaseConfigurationCollection.cs b/Orm/Xtensive.Orm/Orm/Configuration/DatabaseConfigurationCollection.cs index fe9a45729..1536ab043 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/DatabaseConfigurationCollection.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/DatabaseConfigurationCollection.cs @@ -27,6 +27,12 @@ public IDatabaseConfigurationFlow Add(string name) } /// + object ICloneable.Clone() => Clone(); + + /// + /// Creates a new object that is a copy of the current instance. + /// + /// A new object that is a copy of this instance. public DatabaseConfigurationCollection Clone() { var result = new DatabaseConfigurationCollection(); @@ -35,8 +41,6 @@ public DatabaseConfigurationCollection Clone() return result; } - object ICloneable.Clone() => Clone(); - /// public override void Lock(bool recursive) { @@ -47,4 +51,4 @@ public override void Lock(bool recursive) base.Lock(recursive); } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Configuration/DomainConfiguration.cs b/Orm/Xtensive.Orm/Orm/Configuration/DomainConfiguration.cs index 5608aecd5..d99d0d2d8 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/DomainConfiguration.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/DomainConfiguration.cs @@ -814,7 +814,7 @@ protected override void CopyFrom(ConfigurationBase source) versioningConvention = configuration.VersioningConvention.Clone(); preferTypeIdsAsQueryParameters = configuration.PreferTypeIdsAsQueryParameters; maxNumberOfConditons = configuration.MaxNumberOfConditions; - extensionConfigurations = (ExtensionConfigurationCollection) configuration.ExtensionConfigurations.Clone(); + extensionConfigurations = configuration.ExtensionConfigurations.Clone(); } /// diff --git a/Orm/Xtensive.Orm/Orm/Configuration/DomainTypeRegistry.cs b/Orm/Xtensive.Orm/Orm/Configuration/DomainTypeRegistry.cs index 53542fc35..5040c9615 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/DomainTypeRegistry.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/DomainTypeRegistry.cs @@ -266,7 +266,7 @@ public static bool IsDbConnectionAccessor(Type type) #region ICloneable members /// - public override DomainTypeRegistry Clone() => new(this); + public override DomainTypeRegistry Clone() => new DomainTypeRegistry(this); #endregion diff --git a/Orm/Xtensive.Orm/Orm/Configuration/ExtensionConfigurationCollection.cs b/Orm/Xtensive.Orm/Orm/Configuration/ExtensionConfigurationCollection.cs index d0170a29e..d14b3af2e 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/ExtensionConfigurationCollection.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/ExtensionConfigurationCollection.cs @@ -86,7 +86,7 @@ public override void Lock(bool recursive) #region ICloneable methods /// - public object Clone() + public ExtensionConfigurationCollection Clone() { return new ExtensionConfigurationCollection(this); } diff --git a/Orm/Xtensive.Orm/Orm/Configuration/IgnoreRuleCollection.cs b/Orm/Xtensive.Orm/Orm/Configuration/IgnoreRuleCollection.cs index 4a380b226..9fb739731 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/IgnoreRuleCollection.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/IgnoreRuleCollection.cs @@ -51,6 +51,12 @@ public IIgnoreRuleConstructionFlow IgnoreIndex(string indexName) } /// + object ICloneable.Clone() => Clone(); + + /// + /// Creates a new object that is a copy of the current instance. + /// + /// A new object that is a copy of this instance. public IgnoreRuleCollection Clone() { var result = new IgnoreRuleCollection(); @@ -59,8 +65,6 @@ public IgnoreRuleCollection Clone() return result; } - object ICloneable.Clone() => Clone(); - /// public override void Lock(bool recursive) { diff --git a/Orm/Xtensive.Orm/Orm/Configuration/KeyGeneratorConfigurationCollection.cs b/Orm/Xtensive.Orm/Orm/Configuration/KeyGeneratorConfigurationCollection.cs index f4f0c6229..0acbca03a 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/KeyGeneratorConfigurationCollection.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/KeyGeneratorConfigurationCollection.cs @@ -42,6 +42,12 @@ public IKeyGeneratorConfigurationFlow Add() } /// + object ICloneable.Clone() => Clone(); + + /// + /// Creates a new object that is a copy of the current instance. + /// + /// A new object that is a copy of this instance. public KeyGeneratorConfigurationCollection Clone() { var result = new KeyGeneratorConfigurationCollection(); @@ -50,7 +56,6 @@ public KeyGeneratorConfigurationCollection Clone() return result; } - object ICloneable.Clone() => Clone(); /// public override void Lock(bool recursive) { @@ -61,4 +66,4 @@ public override void Lock(bool recursive) base.Lock(recursive); } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Configuration/LinqExtensionRegistration.cs b/Orm/Xtensive.Orm/Orm/Configuration/LinqExtensionRegistration.cs index 08de1b4f3..4b8f2b466 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/LinqExtensionRegistration.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/LinqExtensionRegistration.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2011 Xtensive LLC. +// Copyright (C) 2011 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Denis Krjuchkov diff --git a/Orm/Xtensive.Orm/Orm/Configuration/LinqExtensionRegistry.cs b/Orm/Xtensive.Orm/Orm/Configuration/LinqExtensionRegistry.cs index ae76f6d98..cf8197dca 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/LinqExtensionRegistry.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/LinqExtensionRegistry.cs @@ -78,9 +78,15 @@ IEnumerator IEnumerable.GetEnumerator() /// Clones this instance. /// /// Clone of this instance. - public LinqExtensionRegistry Clone() => new(this); object ICloneable.Clone() => Clone(); + /// + /// Creates a new object that is a copy of the current instance. + /// + /// A new object that is a copy of this instance. + public LinqExtensionRegistry Clone() => new LinqExtensionRegistry(this); + + // Constructors /// diff --git a/Orm/Xtensive.Orm/Orm/Configuration/LoggingConfiguration.cs b/Orm/Xtensive.Orm/Orm/Configuration/LoggingConfiguration.cs index 8f534357e..e43217b2a 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/LoggingConfiguration.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/LoggingConfiguration.cs @@ -43,12 +43,14 @@ public IList Logs { public override void Lock(bool recursive) { - if (logs is ListnativeList) { - logs = nativeList.AsReadOnly(); - } - else { - logs = logs.ToList().AsReadOnly(); - } +#if NET8_0_OR_GREATER + logs = logs.AsReadOnly(); +#else + logs = logs switch { + List nativeList1 => nativeList1.AsReadOnly(), + _ => logs.ToList().AsReadOnly() + }; +#endif base.Lock(recursive); foreach (var log in logs) { diff --git a/Orm/Xtensive.Orm/Orm/Configuration/MappingRuleCollection.cs b/Orm/Xtensive.Orm/Orm/Configuration/MappingRuleCollection.cs index 9fd5ddde6..6db36a184 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/MappingRuleCollection.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/MappingRuleCollection.cs @@ -51,6 +51,12 @@ public IMappingRuleConstructionFlow Map(Assembly assembly, string @namespace) } /// + object ICloneable.Clone() => Clone(); + + /// + /// Creates a new object that is a copy of the current instance. + /// + /// A new object that is a copy of this instance. public MappingRuleCollection Clone() { var result = new MappingRuleCollection(); @@ -59,8 +65,6 @@ public MappingRuleCollection Clone() return result; } - object ICloneable.Clone() => Clone(); - /// public override void Lock(bool recursive) { @@ -71,4 +75,4 @@ public override void Lock(bool recursive) base.Lock(recursive); } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Configuration/NameMappingCollection.cs b/Orm/Xtensive.Orm/Orm/Configuration/NameMappingCollection.cs index 6819b5020..e51b4898b 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/NameMappingCollection.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/NameMappingCollection.cs @@ -93,9 +93,14 @@ public IEnumerator> GetEnumerator() /// Creates clone of this instance. /// /// Clone of this instance. - public NameMappingCollection Clone() => new(this); object ICloneable.Clone() => Clone(); + /// + /// Creates a new object that is a copy of the current instance. + /// + /// A new object that is a copy of this instance. + public NameMappingCollection Clone() => new NameMappingCollection(this); + /// /// Initializes new instance of this type. /// diff --git a/Orm/Xtensive.Orm/Orm/Configuration/NamingConvention.cs b/Orm/Xtensive.Orm/Orm/Configuration/NamingConvention.cs index fcecfaa93..50d465141 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/NamingConvention.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/NamingConvention.cs @@ -96,19 +96,23 @@ public override void Lock(bool recursive) #region ICloneable members /// + object ICloneable.Clone() => Clone(); + + /// + /// Creates a new object that is a copy of the current instance. + /// + /// A new object that is a copy of this instance. public NamingConvention Clone() { - EnsureNotLocked(); - var result = new NamingConvention(); - result.letterCasePolicy = letterCasePolicy; - result.namespacePolicy = namespacePolicy; - result.namingRules = namingRules; - result.namespaceSynonyms = new Dictionary(namespaceSynonyms); + var result = new NamingConvention { + letterCasePolicy = letterCasePolicy, + namespacePolicy = namespacePolicy, + namingRules = namingRules, + namespaceSynonyms = new Dictionary(namespaceSynonyms) + }; return result; } - object ICloneable.Clone() => Clone(); - #endregion } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Configuration/NodeConfiguration.cs b/Orm/Xtensive.Orm/Orm/Configuration/NodeConfiguration.cs index f3288ea6e..17876db57 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/NodeConfiguration.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/NodeConfiguration.cs @@ -92,6 +92,8 @@ public override void Lock(bool recursive = true) DatabaseMapping.Lock(); } + object ICloneable.Clone() => Clone(); + /// /// Creates clone of this instance. /// @@ -106,8 +108,6 @@ public NodeConfiguration Clone() => TypeIdRegistry = TypeIdRegistry, }; - object ICloneable.Clone() => Clone(); - internal void Validate(DomainConfiguration configuration) { if (string.IsNullOrEmpty(nodeId)) diff --git a/Orm/Xtensive.Orm/Orm/Configuration/Options/NamedOptionsCollection{T}.cs b/Orm/Xtensive.Orm/Orm/Configuration/Options/NamedOptionsCollection{T}.cs index 342a60140..8583f8f6f 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/Options/NamedOptionsCollection{T}.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/Options/NamedOptionsCollection{T}.cs @@ -64,10 +64,8 @@ public T this[string key] public void Add(string name, T value) { ValidateName(name); + ArgumentNullException.ThrowIfNull(value); - if (value == null) { - throw new ArgumentNullException(nameof(value)); - } value.Name = name; if (!internalDictionary.TryAdd(name, value)) { diff --git a/Orm/Xtensive.Orm/Orm/Configuration/SessionConfiguration.cs b/Orm/Xtensive.Orm/Orm/Configuration/SessionConfiguration.cs index ba8f41156..ef5ae2df1 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/SessionConfiguration.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/SessionConfiguration.cs @@ -272,7 +272,7 @@ protected override void CopyFrom(ConfigurationBase source) /// Clones this configuration. /// /// The clone of this configuration. - public new SessionConfiguration Clone() + public override SessionConfiguration Clone() { return (SessionConfiguration) base.Clone(); } diff --git a/Orm/Xtensive.Orm/Orm/Configuration/SessionConfigurationCollection.cs b/Orm/Xtensive.Orm/Orm/Configuration/SessionConfigurationCollection.cs index e4e9ef869..831f60ece 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/SessionConfigurationCollection.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/SessionConfigurationCollection.cs @@ -141,6 +141,12 @@ public override void Lock(bool recursive) } /// + object ICloneable.Clone() => Clone(); + + /// + /// Creates a new object that is a copy of the current instance. + /// + /// A new object that is a copy of this instance. public SessionConfigurationCollection Clone() { var result = new SessionConfigurationCollection(); @@ -149,8 +155,6 @@ public SessionConfigurationCollection Clone() return result; } - object ICloneable.Clone() => Clone(); - private SessionConfiguration GetConfiguration(string name, SessionConfiguration fallback) { return !IsLocked ? this[name] : fallback; diff --git a/Orm/Xtensive.Orm/Orm/Configuration/VersioningConvention.cs b/Orm/Xtensive.Orm/Orm/Configuration/VersioningConvention.cs index 8325e6083..e5f1a9fb2 100644 --- a/Orm/Xtensive.Orm/Orm/Configuration/VersioningConvention.cs +++ b/Orm/Xtensive.Orm/Orm/Configuration/VersioningConvention.cs @@ -45,16 +45,21 @@ public bool DenyEntitySetOwnerVersionChange } /// + object ICloneable.Clone() => Clone(); + + /// + /// Creates a new object that is a copy of the current instance. + /// + /// A new object that is a copy of this instance. public VersioningConvention Clone() { - var result = new VersioningConvention(); - result.EntityVersioningPolicy = entityVersioningPolicy; - result.DenyEntitySetOwnerVersionChange = denyEntitySetOwnerVersionChange; + var result = new VersioningConvention { + entityVersioningPolicy = entityVersioningPolicy, + denyEntitySetOwnerVersionChange = denyEntitySetOwnerVersionChange + }; return result; } - object ICloneable.Clone() => Clone(); - /// public VersioningConvention() { @@ -63,4 +68,3 @@ public VersioningConvention() } } } - diff --git a/Orm/Xtensive.Orm/Orm/ConnectionEventData.cs b/Orm/Xtensive.Orm/Orm/ConnectionEventData.cs index 568a76607..58422d500 100644 --- a/Orm/Xtensive.Orm/Orm/ConnectionEventData.cs +++ b/Orm/Xtensive.Orm/Orm/ConnectionEventData.cs @@ -2,6 +2,7 @@ // This code is distributed under MIT license terms. // See the License.txt file in the project root for more information. +using System; using System.Data.Common; using Xtensive.Core; diff --git a/Orm/Xtensive.Orm/Orm/Entity.cs b/Orm/Xtensive.Orm/Orm/Entity.cs index baed27cdb..e20cb6ff4 100644 --- a/Orm/Xtensive.Orm/Orm/Entity.cs +++ b/Orm/Xtensive.Orm/Orm/Entity.cs @@ -91,7 +91,7 @@ internal EntityState State { set { ArgumentNullException.ThrowIfNull(value); if (state!=null) - throw Exceptions.AlreadyInitialized("State"); + throw Exceptions.AlreadyInitialized(nameof(State)); state = value; state.Entity = this; } diff --git a/Orm/Xtensive.Orm/Orm/FullTextSearchCondition/Nodes/ComplexTerm.cs b/Orm/Xtensive.Orm/Orm/FullTextSearchCondition/Nodes/ComplexTerm.cs index 1572de5fb..9a86bb730 100644 --- a/Orm/Xtensive.Orm/Orm/FullTextSearchCondition/Nodes/ComplexTerm.cs +++ b/Orm/Xtensive.Orm/Orm/FullTextSearchCondition/Nodes/ComplexTerm.cs @@ -1,9 +1,10 @@ -// Copyright (C) 2003-2016 Xtensive LLC. +// Copyright (C) 2003-2016 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Alexey Kulakov // Created: 2016.12.09 +using System; using Xtensive.Core; using Xtensive.Orm.FullTextSearchCondition.Interfaces; diff --git a/Orm/Xtensive.Orm/Orm/FullTextSearchCondition/Nodes/GenerationTerm.cs b/Orm/Xtensive.Orm/Orm/FullTextSearchCondition/Nodes/GenerationTerm.cs index da23fcd6a..680b24264 100644 --- a/Orm/Xtensive.Orm/Orm/FullTextSearchCondition/Nodes/GenerationTerm.cs +++ b/Orm/Xtensive.Orm/Orm/FullTextSearchCondition/Nodes/GenerationTerm.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2003-2016 Xtensive LLC. +// Copyright (C) 2003-2016 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Alexey Kulakov @@ -35,9 +35,9 @@ internal GenerationTerm(IOperator source, GenerationType generationType, ICollec ArgumentNullException.ThrowIfNull(source); ArgumentNullException.ThrowIfNull(terms); if (terms.Count==0) - throw new ArgumentException(Strings.ExCollectionIsEmpty, "terms"); + throw new ArgumentException(Strings.ExCollectionIsEmpty, nameof(terms)); if (terms.Any(c=>c.IsNullOrEmpty() || c.Trim().IsNullOrEmpty())) - throw new ArgumentException(Strings.ExCollectionCannotContainAnyNeitherNullOrEmptyStringValues, "terms"); + throw new ArgumentException(Strings.ExCollectionCannotContainAnyNeitherNullOrEmptyStringValues, nameof(terms)); GenerationType = generationType; Terms = terms.ToArray().AsSafeWrapper(); } diff --git a/Orm/Xtensive.Orm/Orm/Internals/KeyGenerators/Caching/DomainCachingSequenceProvider.cs b/Orm/Xtensive.Orm/Orm/Internals/KeyGenerators/Caching/DomainCachingSequenceProvider.cs index 3dfa6be36..f9bed1ce6 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/KeyGenerators/Caching/DomainCachingSequenceProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/KeyGenerators/Caching/DomainCachingSequenceProvider.cs @@ -4,6 +4,7 @@ // Created by: Denis Krjuchkov // Created: 2012.05.17 +using System; using Xtensive.Core; using Xtensive.Orm.Model; using Xtensive.Orm.Providers; diff --git a/Orm/Xtensive.Orm/Orm/Internals/KeyGenerators/Caching/SessionCachingSequenceProvider.cs b/Orm/Xtensive.Orm/Orm/Internals/KeyGenerators/Caching/SessionCachingSequenceProvider.cs index 28fd7e863..ff396abf4 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/KeyGenerators/Caching/SessionCachingSequenceProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/KeyGenerators/Caching/SessionCachingSequenceProvider.cs @@ -4,6 +4,7 @@ // Created by: Denis Krjuchkov // Created: 2012.05.17 +using System; using System.Collections.Generic; using Xtensive.Core; using Xtensive.Orm.Model; diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/EntityContainer.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/EntityContainer.cs index bd70b3212..03c6e6a70 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/EntityContainer.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/EntityContainer.cs @@ -91,9 +91,9 @@ protected EntityContainer(Key key, TypeInfo type, bool exactType, PrefetchManage ArgumentNullException.ThrowIfNull(type); ArgumentNullException.ThrowIfNull(manager, "processor"); Key = key; - Type = type; + Type = type ?? throw new ArgumentNullException(nameof(type)); ExactType = exactType; - Manager = manager; + Manager = manager ?? throw new ArgumentNullException(nameof(manager)); } } } \ No newline at end of file diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/EntitySetTask.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/EntitySetTask.cs index 5b0b0df54..ace3377f6 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/EntitySetTask.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/EntitySetTask.cs @@ -259,7 +259,7 @@ public EntitySetTask(Key ownerKey, in PrefetchFieldDescriptor referencingFieldDe this.referencingFieldDescriptor = referencingFieldDescriptor; this.isOwnerCached = isOwnerCached; ItemCountLimit = referencingFieldDescriptor.EntitySetItemCountLimit; - this.manager = manager; + this.manager = manager ?? throw new ArgumentNullException(nameof(manager)); cacheKey = new ItemsQueryCacheKey(ReferencingField, ItemCountLimit); } } diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Fetcher.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Fetcher.cs index a983b3872..fe87987d7 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Fetcher.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Fetcher.cs @@ -4,6 +4,7 @@ // Created by: Alexander Nikolaev // Created: 2009.10.20 +using System; using System.Collections.Generic; using System.Linq; using System.Threading; diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/GraphContainer.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/GraphContainer.cs index f451574cc..6e84a1278 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/GraphContainer.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/GraphContainer.cs @@ -9,6 +9,7 @@ using Xtensive.Core; using Xtensive.Tuples; using Xtensive.Orm.Model; +using System; namespace Xtensive.Orm.Internals.Prefetch { diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/ExpressionMapBuilder.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/ExpressionMapBuilder.cs index f660b1235..647aafebf 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/ExpressionMapBuilder.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/ExpressionMapBuilder.cs @@ -34,7 +34,7 @@ public override Expression Visit(Expression e) return e; } - protected override Expression VisitParameter(ParameterExpression p) + protected override ParameterExpression VisitParameter(ParameterExpression p) { ValidateParameter(p); return p; @@ -49,7 +49,7 @@ protected override Expression VisitLambda(Expression l) return l; } - protected override Expression VisitMethodCall(MethodCallExpression call) + protected override MethodCallExpression VisitMethodCall(MethodCallExpression call) { // Unpack nested "target.Prefetch(lambda)" call // We will directly map lambda to target to simplify work for NodeBuilder. @@ -80,7 +80,7 @@ protected override Expression VisitMethodCall(MethodCallExpression call) return call; } - protected override Expression VisitMember(MemberExpression m) + protected override MemberExpression VisitMember(MemberExpression m) { ValidateMemberAccess(m); result.RegisterChild(m.Expression, m); @@ -106,6 +106,7 @@ private static void ValidateExpressionType(Expression e) private void ValidateParameter(ParameterExpression p) { if (currentParameter!=p) + throw new NotSupportedException("Outer parameter should not be accessed from nested Prefetch() call"); } @@ -135,4 +136,4 @@ private ExpressionMapBuilder() { } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/IHasNestedNodes.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/IHasNestedNodes.cs index 283995835..d179e3e0b 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/IHasNestedNodes.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/IHasNestedNodes.cs @@ -13,7 +13,7 @@ internal interface IHasNestedNodes { IReadOnlyList NestedNodes { get; } - IReadOnlyCollection ExtractKeys(object target); + IReadOnlyList ExtractKeys(object target); IHasNestedNodes ReplaceNestedNodes(IReadOnlyList nestedNodes); } diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/KeyExtractorNode.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/KeyExtractorNode.cs index ceb67b91a..6a30b38ed 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/KeyExtractorNode.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/KeyExtractorNode.cs @@ -13,22 +13,24 @@ namespace Xtensive.Orm.Internals.Prefetch { internal sealed class KeyExtractorNode : Node, IHasNestedNodes { - public Func> KeyExtractor { get; } + public Func> KeyExtractor { get; } public IReadOnlyList NestedNodes { get; } - IReadOnlyCollection IHasNestedNodes.ExtractKeys(object target) + IReadOnlyList IHasNestedNodes.ExtractKeys(object target) { return ExtractKeys((T) target); } - public IReadOnlyCollection ExtractKeys(T target) + public IReadOnlyList ExtractKeys(T target) { return KeyExtractor.Invoke(target); } - public IHasNestedNodes ReplaceNestedNodes(IReadOnlyList nestedNodes) => - new KeyExtractorNode(KeyExtractor, nestedNodes); + public IHasNestedNodes ReplaceNestedNodes(IReadOnlyList nestedNodes) + { + return new KeyExtractorNode(KeyExtractor, nestedNodes); + } public override Node Accept(NodeVisitor visitor) { @@ -40,7 +42,7 @@ protected override string GetDescription() return $"KeyExtraction<{typeof(T).Name}>"; } - public KeyExtractorNode(Func> extractor, IReadOnlyList nestedNodes) + public KeyExtractorNode(Func> extractor, IReadOnlyList nestedNodes) : base("*") { ArgumentNullException.ThrowIfNull(extractor); diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/NodeAggregator.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/NodeAggregator.cs index 3f859f932..0a6e40521 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/NodeAggregator.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/NodeAggregator.cs @@ -19,7 +19,7 @@ public static IList> Aggregate(IEnumerable ken.Path, (path, @group) => (Node) @group.First().ReplaceNestedNodes( - @group.SelectMany(ken => ken.NestedNodes).ToList().AsSafeWrapper())) + @group.SelectMany(ken => ken.NestedNodes).ToList())) .Select(aggregator.Visit) .Cast>() .ToList(); @@ -36,11 +36,11 @@ public override IReadOnlyList VisitNodeList(IReadOnlyList().SelectMany(c => c.NestedNodes).ToList().AsSafeWrapper()); + group.Cast().SelectMany(c => c.NestedNodes).ToList()); result.Add((BaseFieldNode) Visit(nodeToVisit)); } } - return result.AsSafeWrapper(); + return result; } // Constructor diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/NodeBuilder.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/NodeBuilder.cs index c71c5114e..b000aac21 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/NodeBuilder.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/NodeBuilder.cs @@ -34,7 +34,7 @@ public static KeyExtractorNode Build(DomainModel model, Expression return new KeyExtractorNode(GetExtractor(), nestedNodes); } - private static Func> GetExtractor() + private static Func> GetExtractor() { return target => new[] {((IEntity) target).Key}; } diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/NodeVisitor.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/NodeVisitor.cs index ec98bc9a9..bf69038fd 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/NodeVisitor.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/NodeVisitor.cs @@ -5,8 +5,6 @@ // Created: 2011.01.14 using System.Collections.Generic; -using System.Collections.ObjectModel; -using Xtensive.Core; namespace Xtensive.Orm.Internals.Prefetch { @@ -37,7 +35,9 @@ public virtual IReadOnlyList VisitNodeList(IReadOnlyList(KeyExtractorNode keyExtractorNode) diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/ReferenceNode.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/ReferenceNode.cs index 2c21be991..64344a98c 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/ReferenceNode.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/ReferenceNode.cs @@ -17,7 +17,7 @@ internal sealed class ReferenceNode : BaseFieldNode, IHasNestedNodes public IReadOnlyList NestedNodes { get; private set; } - public IReadOnlyCollection ExtractKeys(object target) + public IReadOnlyList ExtractKeys(object target) { if (target == null) { return Array.Empty(); @@ -30,8 +30,10 @@ public IReadOnlyCollection ExtractKeys(object target) : new[] {referenceKey}; } - public IHasNestedNodes ReplaceNestedNodes(IReadOnlyList nestedNodes) => - new ReferenceNode(Path, Field, ReferenceType, NestedNodes); + public IHasNestedNodes ReplaceNestedNodes(IReadOnlyList nestedNodes) + { + return new ReferenceNode(Path, Field, ReferenceType, NestedNodes); + } public override Node Accept(NodeVisitor visitor) { diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/SetNode.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/SetNode.cs index 3e7e5f52e..e7bc0fdfc 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/SetNode.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/Nodes/SetNode.cs @@ -18,7 +18,7 @@ internal sealed class SetNode : BaseFieldNode, IHasNestedNodes public TypeInfo ElementType { get; } - public IReadOnlyCollection ExtractKeys(object target) + public IReadOnlyList ExtractKeys(object target) { if (target == null) { return Array.Empty(); diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/PrefetchFieldDescriptor.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/PrefetchFieldDescriptor.cs index 377cd1d01..ae0b3dcdb 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/PrefetchFieldDescriptor.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/PrefetchFieldDescriptor.cs @@ -155,7 +155,7 @@ private PrefetchFieldDescriptor( if (entitySetItemCountLimit != null) { ArgumentOutOfRangeException.ThrowIfLessThanOrEqual(entitySetItemCountLimit.Value, 0); } - Field = field; + Field = field ?? throw new ArgumentNullException(nameof(field)); FetchFieldsOfReferencedEntity = fetchFieldsOfReferencedEntity; EntitySetItemCountLimit = entitySetItemCountLimit; FetchLazyFields = fetchLazyFields; diff --git a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/PrefetchHelper.cs b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/PrefetchHelper.cs index a18c9b15a..68e86175f 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/Prefetch/PrefetchHelper.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/Prefetch/PrefetchHelper.cs @@ -18,8 +18,7 @@ internal static class PrefetchHelper type.Fields .Where(field => field.Parent == null && IsFieldToBeLoadedByDefault(field)) .Select(field => new PrefetchFieldDescriptor(field, false, false)) - .ToList() - .AsSafeWrapper(); + .ToArray(); public static bool IsFieldToBeLoadedByDefault(FieldInfo field) { diff --git a/Orm/Xtensive.Orm/Orm/Internals/ReferentialIntegrity/RemovalProcessor.cs b/Orm/Xtensive.Orm/Orm/Internals/ReferentialIntegrity/RemovalProcessor.cs index 12a3c7553..685024968 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/ReferentialIntegrity/RemovalProcessor.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/ReferentialIntegrity/RemovalProcessor.cs @@ -58,7 +58,7 @@ public void Remove(IEnumerable entities, EntityRemoveReason reason) if (isEmpty) { return; } - var processedEntities = new List(); + IReadOnlyList processedEntities = Array.Empty(); var notifiedEntities = new HashSet(); try { var operations = Session.Operations; diff --git a/Orm/Xtensive.Orm/Orm/Internals/RemapContext.cs b/Orm/Xtensive.Orm/Orm/Internals/RemapContext.cs index 13324463a..bdf7786ae 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/RemapContext.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/RemapContext.cs @@ -4,6 +4,7 @@ // Created by: Alexey Kulakov // Created: 2014.04.07 +using System; using System.Collections.Generic; using System.Collections.ObjectModel; using Xtensive.Core; diff --git a/Orm/Xtensive.Orm/Orm/Internals/StorageNodeRegistry.cs b/Orm/Xtensive.Orm/Orm/Internals/StorageNodeRegistry.cs index e4c47f09f..8f628f5c3 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/StorageNodeRegistry.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/StorageNodeRegistry.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2014 Xtensive LLC. +// Copyright (C) 2014 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Denis Krjuchkov diff --git a/Orm/Xtensive.Orm/Orm/Internals/VersionGenerator.cs b/Orm/Xtensive.Orm/Orm/Internals/VersionGenerator.cs index 7ffe41cca..efc18f10b 100644 --- a/Orm/Xtensive.Orm/Orm/Internals/VersionGenerator.cs +++ b/Orm/Xtensive.Orm/Orm/Internals/VersionGenerator.cs @@ -24,7 +24,7 @@ public static class VersionGenerator /// Unsupported type. public static object GenerateNextVersion(object currentVersion) { - ArgumentNullException.ThrowIfNull(currentVersion, "currentValue"); + ArgumentNullException.ThrowIfNull(currentVersion); TypeCode code = Type.GetTypeCode(currentVersion.GetType()); switch (code) { diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/ConstructorExpression.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/ConstructorExpression.cs index 50f986efe..71443d828 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/ConstructorExpression.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/ConstructorExpression.cs @@ -1,19 +1,17 @@ -// Copyright (C) 2003-2010 Xtensive LLC. -// All rights reserved. -// For conditions of distribution and use, see license. +// Copyright (C) 2009-2026 Xtensive LLC. +// This code is distributed under MIT license terms. +// See the License.txt file in the project root for more information. // Created by: Alexey Gamzov // Created: 2009.10.16 using System; using System.Collections.Generic; -using System.Diagnostics; -using System.Linq; using System.Linq.Expressions; using System.Reflection; -using Xtensive.Collections; using Xtensive.Core; using Xtensive.Orm.Linq.Expressions; using Xtensive.Orm.Linq.Expressions.Visitors; +using System.Linq; namespace Xtensive.Orm.Linq { @@ -30,26 +28,32 @@ internal sealed class ConstructorExpression : ParameterizedExpression public override ParameterizedExpression BindParameter(ParameterExpression parameter, Dictionary processedExpressions) { - GenericExpressionVisitor genericVisitor = new(mapped => mapped.BindParameter(parameter, processedExpressions)); - var genericBinder = genericVisitor.Process; + Func genericBinder = + e => GenericExpressionVisitor.Process(e, mapped => mapped.BindParameter(parameter, processedExpressions)); + return new ConstructorExpression( Type, - Bindings.ToDictionary(kvp => kvp.Key, kvp => genericBinder(kvp.Value)), - NativeBindings.ToDictionary(kvp=>kvp.Key, kvp => genericBinder(kvp.Value)), + Bindings.ToDictionary(kvp => kvp.Key, kvp => genericBinder(kvp.Value), Bindings.Count), + NativeBindings.ToDictionary(kvp=>kvp.Key, kvp => genericBinder(kvp.Value), NativeBindings.Count), Constructor, - ConstructorArguments.Select(genericBinder).ToArray()); + ReferenceEquals(ConstructorArguments, Array.Empty()) + ? ConstructorArguments + : ConstructorArguments.Select(genericBinder).ToArray()); } public override Expression RemoveOuterParameter(Dictionary processedExpressions) { - GenericExpressionVisitor genericVisitor = new(mapped => mapped.RemoveOuterParameter(processedExpressions)); - var genericRemover = genericVisitor.Process; + Func genericRemover = + e => GenericExpressionVisitor.Process(e, mapped => mapped.RemoveOuterParameter(processedExpressions)); + var result = new ConstructorExpression( Type, Bindings.ToDictionary(kvp => kvp.Key, kvp => genericRemover(kvp.Value)), NativeBindings = NativeBindings.ToDictionary(kvp => kvp.Key, kvp => genericRemover(kvp.Value)), Constructor, - ConstructorArguments.Select(genericRemover).ToArray()); + ReferenceEquals(ConstructorArguments, Array.Empty()) + ? ConstructorArguments + : ConstructorArguments.Select(genericRemover).ToArray()); return result; } @@ -61,10 +65,12 @@ public override Expression Remap(ColNum offset, Dictionary()); return (Expression) mapped; }; - GenericExpressionVisitor genericVisitor = new(remapper); - var newBindings = Bindings.ToDictionary(kvp => kvp.Key, kvp => genericVisitor.Process(kvp.Value)); - var newConstructorArguments = ConstructorArguments.Select(genericVisitor.Process).ToArray(); - var newNativeBindings = NativeBindings.ToDictionary(kvp => kvp.Key, kvp => genericVisitor.Process(kvp.Value)); + + var newBindings = Bindings.ToDictionary(kvp => kvp.Key, kvp => GenericExpressionVisitor.Process(kvp.Value, remapper)); + var newConstructorArguments = ConstructorArguments.Count == 0 + ? ConstructorArguments + : ConstructorArguments.Select(arg => GenericExpressionVisitor.Process(arg, remapper)).ToArray(); + var newNativeBindings = NativeBindings.ToDictionary(kvp => kvp.Key, kvp => GenericExpressionVisitor.Process(kvp.Value, remapper)); var result = new ConstructorExpression( Type, newBindings, @@ -82,20 +88,28 @@ public override Expression Remap(ColumnMap map, Dictionary()); return (Expression) mapped; }; - GenericExpressionVisitor genericVisitor = new(remapper); - var newBindings = Bindings.ToDictionary(kvp => kvp.Key, kvp => genericVisitor.Process(kvp.Value)); - var newConstructorArguments = ConstructorArguments.Select(genericVisitor.Process).ToArray(); - var newNativeBindings = NativeBindings.ToDictionary(kvp => kvp.Key, kvp => genericVisitor.Process(kvp.Value)); + + var newBindings = Bindings.ToDictionary(kvp => kvp.Key, kvp => GenericExpressionVisitor.Process(kvp.Value, remapper)); + var newConstructorArguments = ConstructorArguments.Count == 0 + ? ConstructorArguments + : ConstructorArguments.Select(arg => GenericExpressionVisitor.Process(arg, remapper)).ToArray(); + var newNativeBindings = NativeBindings.ToDictionary(kvp => kvp.Key, kvp => GenericExpressionVisitor.Process(kvp.Value, remapper)); return new ConstructorExpression(Type, newBindings, newNativeBindings, Constructor, newConstructorArguments); } internal override Expression Accept(ExtendedExpressionVisitor visitor) => visitor.VisitConstructorExpression(this); - public ConstructorExpression(Type type, Dictionary bindings, Dictionary nativeBindings, ConstructorInfo constructor, IReadOnlyList constructorArguments) + public ConstructorExpression(Type type, + Dictionary bindings, + Dictionary nativeBindings, + ConstructorInfo constructor, + IReadOnlyList constructorArguments) : base(ExtendedExpressionType.Constructor, type, null, false) { Bindings = bindings ?? new Dictionary(); NativeBindings = nativeBindings; + // consistently use keep empty array instead of any other empty collection, + // there are checks that help to not instanciate collections ConstructorArguments = constructorArguments ?? Array.Empty(); Constructor = constructor; } diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/EntityExpression.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/EntityExpression.cs index c59ccac85..2fc2525ee 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/EntityExpression.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/EntityExpression.cs @@ -122,7 +122,7 @@ public static void Fill(EntityExpression entityExpression, ColNum offset) _ = entityExpression.Remap(offset, new Dictionary()); } var typeInfo = entityExpression.PersistentType; - foreach (var nestedField in typeInfo.Fields.Except(entityExpression.Fields.OfType().Select(field => field.Field))) { + foreach (var nestedField in typeInfo.Fields.Except(entityExpression.Fields.OfAnyFieldExpression().Select(field => field.Field))) { var nestedFieldExpression = BuildNestedFieldExpression(nestedField, offset); if (nestedFieldExpression is FieldExpression fieldExpression) { fieldExpression.Owner = entityExpression; diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/KeyExpression.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/KeyExpression.cs index d6219a224..f7cd939a3 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/KeyExpression.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/KeyExpression.cs @@ -77,10 +77,25 @@ public override KeyExpression BindParameter( for (int i = 0; i < n; ++i) { fields[i] = KeyFields[i].BindParameter(parameter, processedExpressions); } + return BindParameterWithNoCheck(parameter, processedExpressions); + } + + // Having this code as a separate method helps to avoid closure allocation during BindParameter call + // in case processedExpressions dictionary already contains a result. + private KeyExpression BindParameterWithNoCheck( + ParameterExpression parameter, Dictionary processedExpressions) + { + var fields = KeyFields.Select(BindParameter).ToArray(KeyFields.Count); var result = new KeyExpression(EntityType, fields, Mapping, UnderlyingProperty, parameter, DefaultIfEmpty); processedExpressions.Add(this, result); return result; + + + FieldExpression BindParameter(FieldExpression f) + { + return (FieldExpression) f.BindParameter(parameter, processedExpressions); + } } public override KeyExpression RemoveOuterParameter(Dictionary processedExpressions) @@ -94,18 +109,30 @@ public override KeyExpression RemoveOuterParameter(Dictionary processedExpressions) + { + var fields = KeyFields.Select(RemoveOuterParameter).ToArray(KeyFields.Count); var result = new KeyExpression(EntityType, fields, Mapping, UnderlyingProperty, null, DefaultIfEmpty); processedExpressions.Add(this, result); return result; + + + FieldExpression RemoveOuterParameter(FieldExpression f) + { + return (FieldExpression) f.RemoveOuterParameter(processedExpressions); + } } public static KeyExpression Create(TypeInfo entityType, ColNum offset) { var mapping = new Segment(offset, entityType.Key.TupleDescriptor.Count); - FieldExpression CreateField(ColumnInfo c) => FieldExpression.CreateField(c.Field, offset); - var fields = entityType.IsLocked ? entityType.Key.Columns.Select(CreateField).ToArray() : entityType.Columns @@ -114,6 +141,12 @@ public static KeyExpression Create(TypeInfo entityType, ColNum offset) .Select(CreateField) .ToArray(); return new KeyExpression(entityType, fields, mapping, WellKnownMembers.IEntityKey, null, false); + + + FieldExpression CreateField(ColumnInfo c) + { + return FieldExpression.CreateField(c.Field, offset); + } } internal override Expression Accept(ExtendedExpressionVisitor visitor) => visitor.VisitKeyExpression(this); diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/ParameterizedExpressionExtensions.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/ParameterizedExpressionExtensions.cs new file mode 100644 index 000000000..77297ac4b --- /dev/null +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/ParameterizedExpressionExtensions.cs @@ -0,0 +1,44 @@ +// Copyright (C) 2009-2020 Xtensive LLC. +// This code is distributed under MIT license terms. +// See the License.txt file in the project root for more information. +// Created by: Alexis Kochetov +// Created: 2009.05.05 + +using System.Linq; +using System.Collections.Generic; + +namespace Xtensive.Orm.Linq.Expressions +{ + internal static class ParameterizedExpressionExtensions + { + /// + /// Gets instances of any implementation of + /// + /// Sequence of expressions. + /// Filtered results. + public static IEnumerable OfAnyFieldExpression(this IEnumerable fields) + { + // Faster than .OfType() + return fields + .Where(static f => f.ExtendedType is ExtendedExpressionType.Field + or ExtendedExpressionType.EntityField + or ExtendedExpressionType.EntitySet + or ExtendedExpressionType.StructureField) + .Cast(); + } + + /// + /// Gets instances of only type. + /// + /// Sequence of expressions. + /// Filtered results. + public static IEnumerable OfExactlyFieldExpression(this IEnumerable fields) + { + // A lot faster than fields.OfType().Where(static f => f.ExtendedType is ExtendedExpressionType.Field) + // because contains less casts and more basic comparisons + return fields + .Where(static f => f.ExtendedType is ExtendedExpressionType.Field) + .Cast(); + } + } +} diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureExpression.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureExpression.cs index fa693980c..514cff2f0 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureExpression.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureExpression.cs @@ -28,10 +28,10 @@ internal sealed class StructureExpression : ParameterizedExpression, IPersistent private void SetFields(IReadOnlyList value) { - fields = value; - foreach (var fieldExpression in fields.OfType()) { - fieldExpression.Owner = this; - } + fields = value; + foreach (var fieldExpression in fields.OfAnyFieldExpression()) { + fieldExpression.Owner = this; + } } public override Expression Remap(ColNum offset, Dictionary processedExpressions) @@ -135,14 +135,13 @@ public static StructureExpression CreateLocalCollectionStructure(TypeInfo typeIn var sourceFields = typeInfo.Fields; var destinationFields = new PersistentFieldExpression[sourceFields.Count]; - var result = new StructureExpression(typeInfo, mapping); - result.SetFields(destinationFields); int i = 0; foreach (var field in sourceFields) { // Do not convert to LINQ. We intentionally avoiding closure creation here destinationFields[i++] = BuildNestedFieldExpression(field, mapping.Offset); } - + var result = new StructureExpression(typeInfo, mapping); + result.SetFields(destinationFields); return result; } diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureFieldExpression.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureFieldExpression.cs index d5142c056..c161bbca8 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureFieldExpression.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/StructureFieldExpression.cs @@ -24,7 +24,7 @@ internal sealed class StructureFieldExpression : FieldExpression, private void SetFields(IReadOnlyList value) { fields = value; - foreach (var fieldExpression in fields.OfType()) { + foreach (var fieldExpression in fields.OfAnyFieldExpression()) { fieldExpression.Owner = this; } } diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/ColumnGatherer.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/ColumnGatherer.cs index 13392066e..d029f5aa8 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/ColumnGatherer.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/ColumnGatherer.cs @@ -70,20 +70,20 @@ public static ColNum[] GetColumns(Expression expression, ColumnExtractionModes c return ordered.ToArray(); } - internal override Expression VisitMarker(MarkerExpression expression) + internal protected override MarkerExpression VisitMarker(MarkerExpression expression) { Visit(expression.Target); return expression; } - internal override Expression VisitFieldExpression(FieldExpression f) + internal protected override FieldExpression VisitFieldExpression(FieldExpression f) { ProcessFieldOwner(f); AddColumns(f, f.Mapping.GetItems()); return f; } - internal override Expression VisitStructureFieldExpression(StructureFieldExpression s) + internal protected override StructureFieldExpression VisitStructureFieldExpression(StructureFieldExpression s) { ProcessFieldOwner(s); AddColumns(s, @@ -93,13 +93,13 @@ internal override Expression VisitStructureFieldExpression(StructureFieldExpress return s; } - internal override Expression VisitKeyExpression(KeyExpression k) + internal protected override KeyExpression VisitKeyExpression(KeyExpression k) { AddColumns(k, k.Mapping.GetItems()); return k; } - internal override Expression VisitEntityExpression(EntityExpression e) + internal protected override EntityExpression VisitEntityExpression(EntityExpression e) { if (TreatEntityAsKey) { var keyExpression = (KeyExpression) e.Fields.First(f => f.ExtendedType==ExtendedExpressionType.Key); @@ -110,15 +110,16 @@ internal override Expression VisitEntityExpression(EntityExpression e) else { AddColumns(e, e.Fields - .OfType() - .Where(f => f.ExtendedType==ExtendedExpressionType.Field) + //.OfType() + .Where(static f => f.ExtendedType == ExtendedExpressionType.Field) + .Cast() .Where(f => !(OmitLazyLoad && f.Field.IsLazyLoad)) .Select(f => f.Mapping.Offset)); } return e; } - internal override Expression VisitEntityFieldExpression(EntityFieldExpression ef) + internal protected override EntityFieldExpression VisitEntityFieldExpression(EntityFieldExpression ef) { var keyExpression = (KeyExpression) ef.Fields.First(f => f.ExtendedType==ExtendedExpressionType.Key); AddColumns(ef, keyExpression.Mapping.GetItems()); @@ -127,19 +128,19 @@ internal override Expression VisitEntityFieldExpression(EntityFieldExpression ef return ef; } - internal override Expression VisitEntitySetExpression(EntitySetExpression es) + internal protected override EntitySetExpression VisitEntitySetExpression(EntitySetExpression es) { VisitEntityExpression((EntityExpression) es.Owner); return es; } - internal override Expression VisitColumnExpression(ColumnExpression c) + internal protected override ColumnExpression VisitColumnExpression(ColumnExpression c) { AddColumns(c, c.Mapping.GetItems()); return c; } - internal override Expression VisitStructureExpression(StructureExpression expression) + internal protected override StructureExpression VisitStructureExpression(StructureExpression expression) { AddColumns(expression, expression.Fields @@ -148,14 +149,14 @@ internal override Expression VisitStructureExpression(StructureExpression expres return expression; } - internal override Expression VisitGroupingExpression(GroupingExpression expression) + internal protected override GroupingExpression VisitGroupingExpression(GroupingExpression expression) { Visit(expression.KeyExpression); VisitSubQueryExpression(expression); return expression; } - internal override Expression VisitSubQueryExpression(SubQueryExpression subQueryExpression) + internal protected override SubQueryExpression VisitSubQueryExpression(SubQueryExpression subQueryExpression) { bool isTopSubquery = false; @@ -178,14 +179,14 @@ internal override Expression VisitSubQueryExpression(SubQueryExpression subQuery return subQueryExpression; } - internal override Expression VisitLocalCollectionExpression(LocalCollectionExpression expression) + internal protected override LocalCollectionExpression VisitLocalCollectionExpression(LocalCollectionExpression expression) { foreach (var field in expression.Fields) Visit((Expression) field.Value); return expression; } - internal override Expression VisitConstructorExpression(ConstructorExpression expression) + internal protected override Expression VisitConstructorExpression(ConstructorExpression expression) { foreach (var binding in expression.Bindings) Visit(binding.Value); @@ -228,7 +229,7 @@ private void AddColumns(ParameterizedExpression parameterizedExpression, IEnumer columns.AddRange(expressionColumns.Select(i => (i, (Expression)parameterizedExpression))); } - internal override Expression VisitFullTextExpression(FullTextExpression expression) + internal protected override FullTextExpression VisitFullTextExpression(FullTextExpression expression) { VisitEntityExpression(expression.EntityExpression); VisitColumnExpression(expression.RankExpression); diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/EntityExpressionJoiner.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/EntityExpressionJoiner.cs index f5b74e941..2a19af0d2 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/EntityExpressionJoiner.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/EntityExpressionJoiner.cs @@ -14,7 +14,7 @@ internal sealed class EntityExpressionJoiner : ExtendedExpressionVisitor private readonly Translator translator; private readonly ItemProjectorExpression itemProjectorExpression; - internal override System.Linq.Expressions.Expression VisitEntityExpression(EntityExpression expression) + internal protected override System.Linq.Expressions.Expression VisitEntityExpression(EntityExpression expression) { translator.EnsureEntityFieldsAreJoined(expression, itemProjectorExpression); return base.VisitEntityExpression(expression); @@ -32,4 +32,4 @@ private EntityExpressionJoiner(Translator translator, ItemProjectorExpression it this.itemProjectorExpression = itemProjectorExpression; } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/ExtendedExpressionReplacer.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/ExtendedExpressionReplacer.cs index 4a3a5750e..ca9df34a8 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/ExtendedExpressionReplacer.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/ExtendedExpressionReplacer.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2009-2024 Xtensive LLC. +// Copyright (C) 2009-2026 Xtensive LLC. // This code is distributed under MIT license terms. // See the License.txt file in the project root for more information. // Created by: Alexis Kochetov @@ -28,7 +28,7 @@ public override Expression Visit(Expression e) return result ?? base.Visit(e); } - internal override Expression VisitProjectionExpression(ProjectionExpression projectionExpression) + internal protected override ProjectionExpression VisitProjectionExpression(ProjectionExpression projectionExpression) { var item = Visit(projectionExpression.ItemProjector.Item); var provider = providerVisitor.VisitCompilable(projectionExpression.ItemProjector.DataSource); @@ -41,7 +41,7 @@ internal override Expression VisitProjectionExpression(ProjectionExpression proj return projectionExpression; } - internal override Expression VisitGroupingExpression(GroupingExpression expression) + internal protected override GroupingExpression VisitGroupingExpression(GroupingExpression expression) { var keyExpression = Visit(expression.KeyExpression); if (keyExpression!=expression.KeyExpression) @@ -56,7 +56,7 @@ internal override Expression VisitGroupingExpression(GroupingExpression expressi return expression; } - internal override Expression VisitFullTextExpression(FullTextExpression expression) + internal protected override FullTextExpression VisitFullTextExpression(FullTextExpression expression) { var rankExpression = (ColumnExpression) Visit(expression.RankExpression); var entityExpression = (EntityExpression) Visit(expression.EntityExpression); @@ -65,7 +65,7 @@ internal override Expression VisitFullTextExpression(FullTextExpression expressi return expression; } - internal override Expression VisitSubQueryExpression(SubQueryExpression expression) + internal protected override SubQueryExpression VisitSubQueryExpression(SubQueryExpression expression) { return expression; } @@ -76,42 +76,42 @@ private Expression TranslateExpression(CompilableProvider provider, Expression o return result ?? original; } - internal override Expression VisitFieldExpression(FieldExpression expression) + internal protected override FieldExpression VisitFieldExpression(FieldExpression expression) { return expression; } - internal override Expression VisitStructureFieldExpression(StructureFieldExpression expression) + internal protected override StructureFieldExpression VisitStructureFieldExpression(StructureFieldExpression expression) { return expression; } - internal override Expression VisitKeyExpression(KeyExpression expression) + internal protected override KeyExpression VisitKeyExpression(KeyExpression expression) { return expression; } - internal override Expression VisitEntityExpression(EntityExpression expression) + internal protected override EntityExpression VisitEntityExpression(EntityExpression expression) { return expression; } - internal override Expression VisitEntityFieldExpression(EntityFieldExpression expression) + internal protected override EntityFieldExpression VisitEntityFieldExpression(EntityFieldExpression expression) { return expression; } - internal override Expression VisitEntitySetExpression(EntitySetExpression expression) + internal protected override EntitySetExpression VisitEntitySetExpression(EntitySetExpression expression) { return expression; } - internal override Expression VisitColumnExpression(ColumnExpression expression) + internal protected override ColumnExpression VisitColumnExpression(ColumnExpression expression) { return expression; } - internal override Expression VisitConstructorExpression(ConstructorExpression expression) + internal protected override ConstructorExpression VisitConstructorExpression(ConstructorExpression expression) { var bindings = new Dictionary(expression.Bindings.Count); var nativeBindings = new Dictionary(expression.NativeBindings.Count); @@ -143,7 +143,7 @@ internal override Expression VisitConstructorExpression(ConstructorExpression ex arguments); } - internal override Expression VisitMarker(MarkerExpression expression) + internal protected override MarkerExpression VisitMarker(MarkerExpression expression) { var target = Visit(expression.Target); return target == expression.Target diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/ExtendedExpressionVisitor.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/ExtendedExpressionVisitor.cs index f4b1c3956..68da62bb2 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/ExtendedExpressionVisitor.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/ExtendedExpressionVisitor.cs @@ -17,23 +17,23 @@ protected override Expression VisitExtension(Expression node) => (node as ExtendedExpression ?? throw new NotSupportedException(string.Format(Strings.ExpressionXIsUnknown, node))) .Accept(this); - internal virtual Expression VisitFullTextExpression(FullTextExpression expression) => expression; - internal virtual Expression VisitConstructorExpression(ConstructorExpression expression) => expression; - internal virtual Expression VisitStructureExpression(StructureExpression expression) => expression; - internal virtual Expression VisitLocalCollectionExpression(LocalCollectionExpression expression) => expression; - internal virtual Expression VisitGroupingExpression(GroupingExpression expression) => expression; - internal virtual Expression VisitSubQueryExpression(SubQueryExpression expression) => expression; - internal virtual Expression VisitProjectionExpression(ProjectionExpression projectionExpression) => projectionExpression; - internal virtual Expression VisitFieldExpression(FieldExpression expression) => expression; - internal virtual Expression VisitStructureFieldExpression(StructureFieldExpression expression) => expression; - internal virtual Expression VisitKeyExpression(KeyExpression expression) => expression; - internal virtual Expression VisitEntityExpression(EntityExpression expression) => expression; - internal virtual Expression VisitEntityFieldExpression(EntityFieldExpression expression) => expression; - internal virtual Expression VisitEntitySetExpression(EntitySetExpression expression) => expression; - internal virtual Expression VisitItemProjectorExpression(ItemProjectorExpression itemProjectorExpression) => itemProjectorExpression; - internal virtual Expression VisitColumnExpression(ColumnExpression expression) => expression; + internal protected virtual Expression VisitFullTextExpression(FullTextExpression expression) => expression; + internal protected virtual Expression VisitConstructorExpression(ConstructorExpression expression) => expression; + internal protected virtual Expression VisitStructureExpression(StructureExpression expression) => expression; + internal protected virtual Expression VisitLocalCollectionExpression(LocalCollectionExpression expression) => expression; + internal protected virtual Expression VisitGroupingExpression(GroupingExpression expression) => expression; + internal protected virtual Expression VisitSubQueryExpression(SubQueryExpression expression) => expression; + internal protected virtual Expression VisitProjectionExpression(ProjectionExpression projectionExpression) => projectionExpression; + internal protected virtual Expression VisitFieldExpression(FieldExpression expression) => expression; + internal protected virtual Expression VisitStructureFieldExpression(StructureFieldExpression expression) => expression; + internal protected virtual Expression VisitKeyExpression(KeyExpression expression) => expression; + internal protected virtual Expression VisitEntityExpression(EntityExpression expression) => expression; + internal protected virtual Expression VisitEntityFieldExpression(EntityFieldExpression expression) => expression; + internal protected virtual Expression VisitEntitySetExpression(EntitySetExpression expression) => expression; + internal protected virtual Expression VisitItemProjectorExpression(ItemProjectorExpression itemProjectorExpression) => itemProjectorExpression; + internal protected virtual Expression VisitColumnExpression(ColumnExpression expression) => expression; - internal virtual Expression VisitMarker(MarkerExpression expression) + internal protected virtual Expression VisitMarker(MarkerExpression expression) { var processedTarget = Visit(expression.Target); return processedTarget == expression.Target ? expression : new MarkerExpression(processedTarget, expression.MarkerType); diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/IncludeFilterMappingGatherer.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/IncludeFilterMappingGatherer.cs index 1a9a37f3f..7b1f8ffb9 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/IncludeFilterMappingGatherer.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/IncludeFilterMappingGatherer.cs @@ -37,14 +37,14 @@ public MappingEntry(LambdaExpression calculatedColumn) private static readonly IReadOnlyList CalculatedColumnParameters = [CalculatedColumnParameter]; public static void Gather(Expression filterExpression, Expression filterDataTuple, ApplyParameter filteredTuple, ArraySegment mapping) - { + { var visitor = new IncludeFilterMappingGatherer(filterDataTuple, filteredTuple, mapping); _ = visitor.Visit(filterExpression); if (mapping.Contains(null)) throw Exceptions.InternalError("Failed to gather mappings for IncludeProvider", OrmLog.Instance); } - protected override Expression VisitBinary(BinaryExpression b) + protected override BinaryExpression VisitBinary(BinaryExpression b) { var result = (BinaryExpression) base.VisitBinary(b); var expressions = new[] {result.Left, result.Right}; diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/OwnerRemover.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/OwnerRemover.cs index cd4dce206..8b09e1c4c 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/OwnerRemover.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/OwnerRemover.cs @@ -1,9 +1,11 @@ -// Copyright (C) 2009-2020 Xtensive LLC. +// Copyright (C) 2009-2026 Xtensive LLC. // This code is distributed under MIT license terms. // See the License.txt file in the project root for more information. // Created by: Alexis Kochetov // Created: 2009.05.26 +using System; +using System.Collections.Generic; using System.Linq; using System.Linq.Expressions; using Xtensive.Core; @@ -17,35 +19,50 @@ internal sealed class OwnerRemover : PersistentExpressionVisitor public static Expression RemoveOwner(Expression target) => Instance.Visit(target); - internal override Expression VisitGroupingExpression(GroupingExpression expression) + internal protected override GroupingExpression VisitGroupingExpression(GroupingExpression expression) { return expression; } - internal override Expression VisitSubQueryExpression(SubQueryExpression expression) + internal protected override SubQueryExpression VisitSubQueryExpression(SubQueryExpression expression) { return expression; } - internal override Expression VisitFieldExpression(FieldExpression expression) + internal protected override FieldExpression VisitFieldExpression(FieldExpression expression) { return expression.RemoveOwner(); } - internal override Expression VisitStructureFieldExpression(StructureFieldExpression expression) + internal protected override FieldExpression VisitStructureFieldExpression(StructureFieldExpression expression) { return expression.RemoveOwner(); } - internal override Expression VisitKeyExpression(KeyExpression expression) + internal protected override KeyExpression VisitKeyExpression(KeyExpression expression) { return expression; } - internal override Expression VisitConstructorExpression(ConstructorExpression expression) + internal protected override ConstructorExpression VisitConstructorExpression(ConstructorExpression expression) { - var oldConstructorArguments = expression.ConstructorArguments; - var newConstructorArguments = VisitExpressionList(oldConstructorArguments); + IReadOnlyList oldConstructorArguments; + IReadOnlyList newConstructorArguments; + + if (ReferenceEquals(expression.ConstructorArguments, Array.Empty())) { + oldConstructorArguments = newConstructorArguments = Array.Empty(); + } + else if (expression.ConstructorArguments is IReadOnlyList argsAsList) { + oldConstructorArguments = argsAsList; + newConstructorArguments = VisitExpressionList(argsAsList); // creates a copy internally + } + else { + oldConstructorArguments = expression.ConstructorArguments.ToList(); + if (oldConstructorArguments.Count == 0) + oldConstructorArguments = newConstructorArguments = Array.Empty(); + else + newConstructorArguments = VisitExpressionList(oldConstructorArguments); + } var oldBindings = expression.Bindings.Values.ToArray(); var newBindings = VisitExpressionList(oldBindings); @@ -70,22 +87,22 @@ internal override Expression VisitConstructorExpression(ConstructorExpression ex return new ConstructorExpression(expression.Type, bindings, nativeBingings, expression.Constructor, newConstructorArguments.ToReadOnlyList()); } - internal override Expression VisitEntityExpression(EntityExpression expression) + internal protected override EntityExpression VisitEntityExpression(EntityExpression expression) { return expression; } - internal override Expression VisitEntityFieldExpression(EntityFieldExpression expression) + internal protected override FieldExpression VisitEntityFieldExpression(EntityFieldExpression expression) { return expression.RemoveOwner(); } - internal override Expression VisitEntitySetExpression(EntitySetExpression expression) + internal protected override EntitySetExpression VisitEntitySetExpression(EntitySetExpression expression) { return expression; } - internal override Expression VisitColumnExpression(ColumnExpression expression) + internal protected override ColumnExpression VisitColumnExpression(ColumnExpression expression) { return expression; } diff --git a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/PersistentExpressionVisitor.cs b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/PersistentExpressionVisitor.cs index d9ffaeb91..56b248e62 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/PersistentExpressionVisitor.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Expressions/Visitors/PersistentExpressionVisitor.cs @@ -13,13 +13,13 @@ namespace Xtensive.Orm.Linq.Expressions.Visitors { internal abstract class PersistentExpressionVisitor : ExtendedExpressionVisitor { - internal override Expression VisitProjectionExpression(ProjectionExpression projectionExpression) => + internal protected override Expression VisitProjectionExpression(ProjectionExpression projectionExpression) => throw Exceptions.InternalError(string.Format(Strings.ExXDoesNotSupportX, typeof(PersistentExpressionVisitor), WellKnownOrmTypes.ProjectionExpression), OrmLog.Instance); - internal override Expression VisitItemProjectorExpression(ItemProjectorExpression itemProjectorExpression) + internal protected override Expression VisitItemProjectorExpression(ItemProjectorExpression itemProjectorExpression) { throw Exceptions.InternalError(String.Format(Strings.ExXDoesNotSupportX, typeof (PersistentExpressionVisitor), typeof (ItemProjectorExpression)), OrmLog.Instance); } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Linq/Materialization/ExpressionMaterializer.cs b/Orm/Xtensive.Orm/Orm/Linq/Materialization/ExpressionMaterializer.cs index 2d1a6ebb6..591c0e075 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Materialization/ExpressionMaterializer.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Materialization/ExpressionMaterializer.cs @@ -4,12 +4,8 @@ // Created by: Alexey Gamzov // Created: 2009.05.21 -using System; -using System.Collections.Generic; -using System.Linq; using System.Linq.Expressions; using System.Reflection; -using Xtensive.Collections; using Xtensive.Core; using Xtensive.Linq; using Xtensive.Orm.Internals; @@ -30,6 +26,7 @@ internal class ExpressionMaterializer : PersistentExpressionVisitor internal static readonly IReadOnlySet> EmptyTupleParameters = new HashSet>(); + private const int NumberOfItemsOnStack = 64; private static readonly MethodInfo BuildPersistentTupleMethod = typeof(ExpressionMaterializer).GetMethod(nameof(BuildPersistentTuple), BindingFlags.NonPublic | BindingFlags.Static); private static readonly MethodInfo GetTupleSegmentMethod = typeof(ExpressionMaterializer).GetMethod(nameof(GetTupleSegment), BindingFlags.NonPublic | BindingFlags.Static); private static readonly MethodInfo GetParameterValueMethod = WellKnownOrmTypes.ParameterContext.GetMethod(nameof(ParameterContext.GetValue)); @@ -85,7 +82,7 @@ public static MaterializationInfo MakeMaterialization(ItemProjectorExpression pr #region Visitor methods overrsides - internal override Expression VisitFullTextExpression(FullTextExpression expression) + internal protected override Expression VisitFullTextExpression(FullTextExpression expression) { var rankMaterializer = Visit(expression.RankExpression); var entityMaterializer = Visit(expression.EntityExpression); @@ -99,7 +96,7 @@ internal override Expression VisitFullTextExpression(FullTextExpression expressi entityMaterializer); } - internal override Expression VisitMarker(MarkerExpression expression) + internal protected override Expression VisitMarker(MarkerExpression expression) { var target = expression.Target; var processedTarget = Visit(target); @@ -114,7 +111,7 @@ internal override Expression VisitMarker(MarkerExpression expression) return processedTarget; } - internal override Expression VisitGroupingExpression(GroupingExpression groupingExpression) + internal protected override Expression VisitGroupingExpression(GroupingExpression groupingExpression) { // 1. Prepare subquery parameters. var translatedQuery = PrepareSubqueryParameters(groupingExpression, @@ -146,7 +143,7 @@ internal override Expression VisitGroupingExpression(GroupingExpression grouping return Expression.Convert(resultExpression, groupingExpression.Type); } - internal override Expression VisitSubQueryExpression(SubQueryExpression subQueryExpression) + internal protected override Expression VisitSubQueryExpression(SubQueryExpression subQueryExpression) { // 1. Prepare subquery parameters. var translatedQuery = PrepareSubqueryParameters( @@ -209,7 +206,7 @@ private TranslatedQuery PrepareSubqueryParameters(SubQueryExpression subQueryExp } } - internal override Expression VisitFieldExpression(FieldExpression expression) + internal protected override Expression VisitFieldExpression(FieldExpression expression) { var tupleExpression = GetTupleExpression(expression); @@ -240,11 +237,11 @@ internal override Expression VisitFieldExpression(FieldExpression expression) return MaterializeThroughOwner(expression, tupleExpression); } - internal override Expression VisitLocalCollectionExpression(LocalCollectionExpression expression) => + internal protected override Expression VisitLocalCollectionExpression(LocalCollectionExpression expression) => throw new NotSupportedException( string.Format(Strings.ExUnableToMaterializeBackLocalCollectionItem, expression.ToString())); - internal override Expression VisitStructureFieldExpression(StructureFieldExpression expression) + internal protected override Expression VisitStructureFieldExpression(StructureFieldExpression expression) { var tupleExpression = GetTupleExpression(expression); @@ -252,10 +249,29 @@ internal override Expression VisitStructureFieldExpression(StructureFieldExpress if (expression.Owner==null) { var typeInfo = expression.PersistentType; var tuplePrototype = typeInfo.TuplePrototype; - var mappingInfo = expression.Fields - .OfType() - .Where(f => f.ExtendedType==ExtendedExpressionType.Field) - .Select(f => (f.Field.MappingInfo.Offset, f.Mapping.Offset)); + + var mappingSequence = expression.Fields + .OfExactlyFieldExpression() + .OrderBy(static f => f.Field.MappingInfo.Offset) + .Select(f => (f.Field.MappingInfo.Offset, f.Mapping.Offset)) + .Distinct(); + + (ColNum, ColNum)[] mappingInfo; + if (expression.Fields.Count > NumberOfItemsOnStack * 2) { + mappingInfo = mappingSequence.ToArray(); + } + else { + Span<(ColNum, ColNum)> mappingInfoSpan = (expression.Fields.Count < NumberOfItemsOnStack) + ? stackalloc (ColNum, ColNum)[expression.Fields.Count] + : new (ColNum, ColNum)[expression.Fields.Count]; + + int actualCount = 0; + foreach (var map in mappingSequence) { + mappingInfoSpan[actualCount++] = map; + } + + mappingInfo = mappingInfoSpan.Slice(0, actualCount).ToArray(); + } var columnMap = MaterializationHelper.CreateSingleSourceMap(tuplePrototype.Count, mappingInfo); @@ -276,7 +292,7 @@ internal override Expression VisitStructureFieldExpression(StructureFieldExpress return MaterializeThroughOwner(expression, tupleExpression); } - internal override Expression VisitConstructorExpression(ConstructorExpression expression) + internal protected override Expression VisitConstructorExpression(ConstructorExpression expression) { var newExpression = expression.Constructor==null ? Expression.New(expression.Type) // Value type with default ctor (expression.Constructor is null in that case) @@ -286,22 +302,41 @@ internal override Expression VisitConstructorExpression(ConstructorExpression ex return expression.NativeBindings.Count == 0 ? newExpression - : (Expression) Expression.MemberInit(newExpression, expression - .NativeBindings - .Where(item => Translator.FilterBindings(item.Key, item.Key.Name, item.Value.Type)) - .Select(item => Expression.Bind(item.Key, Visit(item.Value))).Cast()); + : Expression.MemberInit(newExpression, expression + .NativeBindings + .Where(item => Translator.FilterBindings(item.Key, item.Key.Name, item.Value.Type)) + .Select(item => Expression.Bind(item.Key, Visit(item.Value))).Cast()); } - internal override Expression VisitStructureExpression(StructureExpression expression) + internal protected override Expression VisitStructureExpression(StructureExpression expression) { var tupleExpression = GetTupleExpression(expression); var typeInfo = expression.PersistentType; var tuplePrototype = typeInfo.TuplePrototype; - var mappingInfo = expression.Fields - .OfType() - .Where(f => f.ExtendedType==ExtendedExpressionType.Field) - .Select(f => (f.Field.MappingInfo.Offset, f.Mapping.Offset)); + + var mappingSequence = expression.Fields + .OfExactlyFieldExpression() + .OrderBy(static f => f.Field.MappingInfo.Offset) + .Select(static f => (f.Field.MappingInfo.Offset, f.Mapping.Offset)) + .Distinct(); + + (ColNum, ColNum)[] mappingInfo; + if (expression.Fields.Count > NumberOfItemsOnStack * 2) { + mappingInfo = mappingSequence.ToArray(); + } + else { + Span<(ColNum, ColNum)> mappingInfoSpan = (expression.Fields.Count < NumberOfItemsOnStack) + ? stackalloc (ColNum, ColNum)[expression.Fields.Count] + : new (ColNum, ColNum)[expression.Fields.Count]; + + int actualCount = 0; + foreach (var map in mappingSequence) { + mappingInfoSpan[actualCount++] = map; + } + + mappingInfo = mappingInfoSpan.Slice(0, actualCount).ToArray(); + } var columnMap = MaterializationHelper.CreateSingleSourceMap(tuplePrototype.Count, mappingInfo); @@ -319,7 +354,7 @@ internal override Expression VisitStructureExpression(StructureExpression expres expression.Type); } - internal override Expression VisitKeyExpression(KeyExpression expression) + internal protected override Expression VisitKeyExpression(KeyExpression expression) { // TODO: http://code.google.com/p/dataobjectsdotnet/issues/detail?id=336 Expression tupleExpression = Expression.Call( @@ -337,7 +372,7 @@ internal override Expression VisitKeyExpression(KeyExpression expression) tupleExpression); } - internal override Expression VisitEntityExpression(EntityExpression expression) + internal protected override Expression VisitEntityExpression(EntityExpression expression) { var tupleExpression = GetTupleExpression(expression); return CreateEntity(expression, tupleExpression); @@ -360,11 +395,28 @@ private Expression CreateEntity(IEntityExpression expression, Expression tupleEx var typeIdField = expression.Fields.SingleOrDefault(f => f.Name==WellKnown.TypeIdFieldName); var typeIdIndex = typeIdField == null ? -1 : typeIdField.Mapping.Offset; - var mappingInfo = expression.Fields - .OfType() - .Where(f => f.ExtendedType==ExtendedExpressionType.Field) - .Select(f => (f.Field.MappingInfo.Offset, f.Mapping.Offset)) - .ToHashSet(); + var mappingSequence = expression.Fields + .OfExactlyFieldExpression() + .OrderBy(static f => f.Field.MappingInfo.Offset) + .Select(static f => (f.Field.MappingInfo.Offset, f.Mapping.Offset)) + .Distinct(); + + (ColNum, ColNum)[] mappingInfo; + if (expression.Fields.Count > NumberOfItemsOnStack * 4) { + mappingInfo = mappingSequence.ToArray(); + } + else { + Span<(ColNum, ColNum)> mappingInfoSpan = (expression.Fields.Count < NumberOfItemsOnStack) + ? stackalloc (ColNum, ColNum)[expression.Fields.Count] + : new (ColNum, ColNum)[expression.Fields.Count]; + + int actualCount = 0; + foreach (var map in mappingSequence) { + mappingInfoSpan[actualCount++] = map; + } + + mappingInfo = mappingInfoSpan.Slice(0, actualCount).ToArray(); + } var exprIndex = Expr.Constant(index); var isMaterializedExpression = Expression.Call( @@ -392,7 +444,7 @@ private Expression CreateEntity(IEntityExpression expression, Expression tupleEx } /// InvalidOperationException. - internal override Expression VisitEntityFieldExpression(EntityFieldExpression expression) + internal protected override Expression VisitEntityFieldExpression(EntityFieldExpression expression) { if (expression.Entity!=null) return Visit(expression.Entity); @@ -403,7 +455,7 @@ internal override Expression VisitEntityFieldExpression(EntityFieldExpression ex : CreateEntity(expression, tupleExpression); } - internal override Expression VisitEntitySetExpression(EntitySetExpression expression) + internal protected override Expression VisitEntitySetExpression(EntitySetExpression expression) { var tupleExpression = GetTupleExpression(expression); var materializedEntitySetExpression = MaterializeThroughOwner(expression, tupleExpression); @@ -416,7 +468,7 @@ internal override Expression VisitEntitySetExpression(EntitySetExpression expres return prefetchEntitySetExpression; } - internal override Expression VisitColumnExpression(ColumnExpression expression) + internal protected override Expression VisitColumnExpression(ColumnExpression expression) { var tupleExpression = GetTupleExpression(expression); return tupleExpression.MakeTupleAccess(expression.Type, expression.Mapping.Offset); diff --git a/Orm/Xtensive.Orm/Orm/Linq/MemberCompilation/MemberCompilerProvider.cs b/Orm/Xtensive.Orm/Orm/Linq/MemberCompilation/MemberCompilerProvider.cs index 62f04db98..cbdec7f4b 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/MemberCompilation/MemberCompilerProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/MemberCompilation/MemberCompilerProvider.cs @@ -169,7 +169,7 @@ private static (MemberInfo targetMember, Delegate compilerInvoker) ProcessCompil bool isGenericMethod = attribute.NumberOfGenericArguments > 0; bool isGenericType = targetType.IsGenericType; bool isGeneric = isGenericType || isGenericMethod; - + string memberName = attribute.TargetMember; if (memberName.IsNullOrEmpty()) @@ -186,18 +186,21 @@ private static (MemberInfo targetMember, Delegate compilerInvoker) ProcessCompil if (isCtor) bindingFlags |= BindingFlags.Instance; - else + else { if (!isStatic) { - if (parameterTypes.Length==0) + if (parameterTypes.Length == 0) throw new InvalidOperationException(string.Format( Strings.ExCompilerXShouldHaveThisParameter, compiler.GetFullName(true))); - parameterTypes = parameterTypes.Skip(1).ToArray(); + var noInstanceParameter = new Type[parameterTypes.Length - 1]; + Array.Copy(parameterTypes, 1, noInstanceParameter, 0, noInstanceParameter.Length); + parameterTypes = noInstanceParameter; bindingFlags |= BindingFlags.Instance; } else bindingFlags |= BindingFlags.Static; + } if (isPropertyGetter) { bindingFlags |= BindingFlags.GetProperty; diff --git a/Orm/Xtensive.Orm/Orm/Linq/ParameterExtractor.cs b/Orm/Xtensive.Orm/Orm/Linq/ParameterExtractor.cs index cfc253f96..480ea703a 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/ParameterExtractor.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/ParameterExtractor.cs @@ -32,7 +32,7 @@ protected override Expression VisitMember(MemberExpression m) protected override Expression VisitUnknown(Expression e) => e; - protected override Expression VisitConstant(ConstantExpression c) + protected override ConstantExpression VisitConstant(ConstantExpression c) { isParameter |= c.GetMemberType() is MemberType.Entity or MemberType.Structure; return c; diff --git a/Orm/Xtensive.Orm/Orm/Linq/Rewriters/ApplyParameterRewriter.cs b/Orm/Xtensive.Orm/Orm/Linq/Rewriters/ApplyParameterRewriter.cs index 56b8bc22f..5d887c307 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Rewriters/ApplyParameterRewriter.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Rewriters/ApplyParameterRewriter.cs @@ -38,7 +38,7 @@ protected override Expression VisitMember(MemberExpression m) } - internal override Expression VisitGroupingExpression(GroupingExpression expression) + internal protected override Expression VisitGroupingExpression(GroupingExpression expression) { var projectionExpression = expression.ProjectionExpression; var newProvider = Rewrite(projectionExpression.ItemProjector.DataSource, oldApplyParameter, newApplyParameter); @@ -56,7 +56,7 @@ internal override Expression VisitGroupingExpression(GroupingExpression expressi return expression; } - internal override Expression VisitSubQueryExpression(SubQueryExpression expression) + internal protected override Expression VisitSubQueryExpression(SubQueryExpression expression) { var projectionExpression = expression.ProjectionExpression; var newProvider = Rewrite(projectionExpression.ItemProjector.DataSource, oldApplyParameter, newApplyParameter); @@ -94,4 +94,4 @@ private ApplyParameterRewriter(ApplyParameter oldParameter, ApplyParameter newPa newApplyParameter = newParameter; } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Linq/Rewriters/ApplyParameterToTupleParameterRewriter.cs b/Orm/Xtensive.Orm/Orm/Linq/Rewriters/ApplyParameterToTupleParameterRewriter.cs index 95b61fefa..a1d7da9b3 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Rewriters/ApplyParameterToTupleParameterRewriter.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Rewriters/ApplyParameterToTupleParameterRewriter.cs @@ -39,7 +39,7 @@ protected override Expression VisitMember(MemberExpression m) return parameterOfTupleExpression; } - internal override Expression VisitGroupingExpression(GroupingExpression expression) + internal protected override Expression VisitGroupingExpression(GroupingExpression expression) { var projectionExpression = expression.ProjectionExpression; var newProvider = Rewrite(projectionExpression.ItemProjector.DataSource, parameterOfTuple, applyParameter); @@ -58,7 +58,7 @@ internal override Expression VisitGroupingExpression(GroupingExpression expressi return expression; } - internal override Expression VisitSubQueryExpression(SubQueryExpression expression) + internal protected override Expression VisitSubQueryExpression(SubQueryExpression expression) { var projectionExpression = expression.ProjectionExpression; var newProvider = Rewrite(projectionExpression.ItemProjector.DataSource, parameterOfTuple, applyParameter); @@ -95,4 +95,4 @@ private ApplyParameterToTupleParameterRewriter(Parameter parameterOfTuple this.applyParameter = applyParameter; } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Linq/Rewriters/SubqueryFilterRemover.cs b/Orm/Xtensive.Orm/Orm/Linq/Rewriters/SubqueryFilterRemover.cs index 52e3ee05b..6a7243a4b 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Rewriters/SubqueryFilterRemover.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Rewriters/SubqueryFilterRemover.cs @@ -31,14 +31,14 @@ public bool Check(Expression expression) return matchFound && @continue && meaningfulLefts.Count==meaningfulRights.Count; } - protected override Expression VisitConstant(ConstantExpression c) + protected override ConstantExpression VisitConstant(ConstantExpression c) { if (c.Value==filterParameter) matchFound = true; return c; } - protected override Expression VisitBinary(BinaryExpression b) + protected override BinaryExpression VisitBinary(BinaryExpression b) { if (b.NodeType==ExpressionType.Equal) { var leftAccess = b.Left.AsTupleAccess(); @@ -115,4 +115,4 @@ private SubqueryFilterRemover(ApplyParameter filterParameter) checker = new SubqueryFilterChecker(filterParameter); } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Linq/Translator.Expressions.cs b/Orm/Xtensive.Orm/Orm/Linq/Translator.Expressions.cs index ead3b3545..87b27141d 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Translator.Expressions.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Translator.Expressions.cs @@ -516,6 +516,8 @@ protected override Expression VisitMethodCall(MethodCallExpression mc) // Visit Queryable extensions. if (methodDeclaringType == typeof(QueryableExtensions)) { return methodName switch { + Reflection.WellKnown.QueryableExtensions.LeftJoin => VisitLeftJoin(mc), + Reflection.WellKnown.QueryableExtensions.LeftJoinEx => VisitLeftJoin(mc), Reflection.WellKnown.QueryableExtensions.LeftOuterJoin => VisitLeftJoin(mc), Reflection.WellKnown.QueryableExtensions.In => VisitIn(mc), Reflection.WellKnown.QueryableExtensions.Lock => VisitLock(mc), @@ -707,14 +709,13 @@ protected override Expression VisitNew(NewExpression newExpression) // ReSharper restore ConditionIsAlwaysTrueOrFalse // ReSharper restore HeuristicUnreachableCode - var arguments = VisitNewExpressionArguments(newExpression); - if (strippedMarkersExpression.IsAnonymousConstructor()) { - return newExpressionMembers is null + var arguments = VisitNewExpressionArguments(newExpression, out var constructorParameters); + if (newExpression.IsAnonymousConstructor()) { + return newExpression.Members == null ? Expression.New(newExpression.Constructor, arguments) : Expression.New(newExpression.Constructor, arguments, newExpressionMembers); } - var constructorParameters = newExpression.GetConstructorParameters(); if (constructorParameters.Length != arguments.Count) throw Exceptions.InternalError(Strings.ExInvalidNumberOfParametersInNewExpression, OrmLog.Instance); diff --git a/Orm/Xtensive.Orm/Orm/Linq/Translator.Materialization.cs b/Orm/Xtensive.Orm/Orm/Linq/Translator.Materialization.cs index d9c9b4dd9..5ae5186cf 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Translator.Materialization.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Translator.Materialization.cs @@ -149,10 +149,15 @@ private Materializer BuildMaterializer(ProjectionExpression projection, IReadOnl return new Materializer(projectorExpression.CachingCompile()); } - private IReadOnlyList VisitNewExpressionArguments(NewExpression n) + private IReadOnlyList VisitNewExpressionArguments(NewExpression n, out ParameterInfo[] constructorParameters) { + constructorParameters = n.GetConstructorParameters(); var origArguments = n.Arguments; int count = origArguments.Count; + if (count == 0) { + return []; + } + var arguments = new Expression[count]; for (int i = 0; i < count; i++) { var argument = origArguments[i]; @@ -164,21 +169,18 @@ private IReadOnlyList VisitNewExpressionArguments(NewExpression n) context.RegisterPossibleQueryReuse(n.Members[i]); } } - arguments[i] = body.StripMarkers().IsProjection() + body = body.IsProjection() ? BuildSubqueryResult((ProjectionExpression) body, argument.Type) : ProcessProjectionElement(body); - } - var constructorParameters = n.GetConstructorParameters(); - for (int i = 0; i < count; i++) { var parameterType = constructorParameters[i].ParameterType; - ref var argument = ref arguments[i]; - if (argument.Type != parameterType) { - argument = Expression.Convert(argument, parameterType); - } + arguments[i] = body.Type != parameterType + ? Expression.Convert(body, parameterType) + : body; } return arguments; } + private void VisitNewExpressionArgumentsSkipResults(NewExpression n) { var origArguments = n.Arguments; diff --git a/Orm/Xtensive.Orm/Orm/Linq/Translator.Queryable.cs b/Orm/Xtensive.Orm/Orm/Linq/Translator.Queryable.cs index 2764dc9c8..d4e0ac113 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/Translator.Queryable.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/Translator.Queryable.cs @@ -382,7 +382,7 @@ private ProjectionExpression VisitOfType(Expression source, Type targetType, Typ currentIndex++; } - var recordSet = targetTypeInfo.Indexes.PrimaryIndex.GetQuery().Alias(context.GetNextAlias()).Select(indexes); + CompilableProvider recordSet = targetTypeInfo.Indexes.PrimaryIndex.GetQuery().Alias(context.GetNextAlias()).Select(indexes); var keySegment = visitedSource.ItemProjector.GetColumns(ColumnExtractionModes.TreatEntityAsKey); var keyPairs = keySegment .Select((leftIndex, rightIndex) => (leftIndex, (ColNum)rightIndex)) diff --git a/Orm/Xtensive.Orm/Orm/Linq/WellknownMembers.Queryable.cs b/Orm/Xtensive.Orm/Orm/Linq/WellknownMembers.Queryable.cs index 64454f41e..4cc5e2b8d 100644 --- a/Orm/Xtensive.Orm/Orm/Linq/WellknownMembers.Queryable.cs +++ b/Orm/Xtensive.Orm/Orm/Linq/WellknownMembers.Queryable.cs @@ -123,6 +123,7 @@ public static class Queryable // Queryable extensions public static readonly MethodInfo ExtensionCount = GetQueryableExtensionsMethod(nameof(QueryableExtensions.Count), 0, 1); public static readonly MethodInfo ExtensionLeftJoin = GetQueryableExtensionsMethod(nameof(QueryableExtensions.LeftOuterJoin), 4, 5); + public static readonly MethodInfo ExtensionLeftJoinEx = GetQueryableExtensionsMethod(nameof(QueryableExtensions.LeftJoinEx), 4, 5); public static readonly MethodInfo ExtensionLock = GetQueryableExtensionsMethod(nameof(QueryableExtensions.Lock), 1, 3); public static readonly MethodInfo ExtensionTake = GetQueryableExtensionsMethod(nameof(QueryableExtensions.Take), 1, 2); public static readonly MethodInfo ExtensionSkip = GetQueryableExtensionsMethod(nameof(QueryableExtensions.Skip), 1, 2); diff --git a/Orm/Xtensive.Orm/Orm/Logging/BaseLog.cs b/Orm/Xtensive.Orm/Orm/Logging/BaseLog.cs index b21176c6e..8ea84c3d4 100644 --- a/Orm/Xtensive.Orm/Orm/Logging/BaseLog.cs +++ b/Orm/Xtensive.Orm/Orm/Logging/BaseLog.cs @@ -37,7 +37,7 @@ public abstract class BaseLog /// object. Region will closed by disposing of this object. public IndentManager.IndentScope DebugRegion(string messageId, params ReadOnlySpan parameters) { - ArgumentNullException.ThrowIfNull(messageId, "message"); + ArgumentNullException.ThrowIfNull(messageId); if (!IsLogged(LogLevel.Debug)) return IndentManager.IncreaseIndent(); var message = Strings.ResourceManager.GetString(messageId, Strings.Culture) ?? messageId; @@ -59,7 +59,7 @@ public IndentManager.IndentScope DebugRegion(string messageId, params ReadOnlySp /// object. Region will closed by disposing of this object. public IndentManager.IndentScope InfoRegion(string messageId, params ReadOnlySpan parameters) { - ArgumentNullException.ThrowIfNull(messageId, "message"); + ArgumentNullException.ThrowIfNull(messageId); if (!IsLogged(LogLevel.Info)) return IndentManager.IncreaseIndent(); var message = Strings.ResourceManager.GetString(messageId, Strings.Culture) ?? messageId; diff --git a/Orm/Xtensive.Orm/Orm/Logging/Internals/InternalLog.cs b/Orm/Xtensive.Orm/Orm/Logging/Internals/InternalLog.cs index ccd51506c..34d80084d 100644 --- a/Orm/Xtensive.Orm/Orm/Logging/Internals/InternalLog.cs +++ b/Orm/Xtensive.Orm/Orm/Logging/Internals/InternalLog.cs @@ -4,7 +4,7 @@ // Created by: Alexey Kulakov // Created: 2013.09.27 -using Xtensive.Core; +using System; namespace Xtensive.Orm.Logging { diff --git a/Orm/Xtensive.Orm/Orm/Model/Stored/Internals/TypeMappingUpdater.cs b/Orm/Xtensive.Orm/Orm/Model/Stored/Internals/TypeMappingUpdater.cs index 81010f37c..feca16377 100644 --- a/Orm/Xtensive.Orm/Orm/Model/Stored/Internals/TypeMappingUpdater.cs +++ b/Orm/Xtensive.Orm/Orm/Model/Stored/Internals/TypeMappingUpdater.cs @@ -1,5 +1,8 @@ - +// Copyright (C) 2016-2020 Xtensive LLC. +// This code is distributed under MIT license terms. +// See the License.txt file in the project root for more information. +using System; using Xtensive.Core; using Xtensive.Orm.Configuration; diff --git a/Orm/Xtensive.Orm/Orm/Model/TypeInfoCollection.cs b/Orm/Xtensive.Orm/Orm/Model/TypeInfoCollection.cs index 3d8665e5c..79b6aea0c 100644 --- a/Orm/Xtensive.Orm/Orm/Model/TypeInfoCollection.cs +++ b/Orm/Xtensive.Orm/Orm/Model/TypeInfoCollection.cs @@ -152,8 +152,7 @@ public override bool Contains(TypeInfo item) { if (item==null) return false; - TypeInfo result; - if (!TryGetValue(item.UnderlyingType, out result)) + if (!TryGetValue(item.UnderlyingType, out var result)) return false; return result==item; } diff --git a/Orm/Xtensive.Orm/Orm/Operations/MethodCallOperation.cs b/Orm/Xtensive.Orm/Orm/Operations/MethodCallOperation.cs index a6d41cfb1..f4fe74203 100644 --- a/Orm/Xtensive.Orm/Orm/Operations/MethodCallOperation.cs +++ b/Orm/Xtensive.Orm/Orm/Operations/MethodCallOperation.cs @@ -106,7 +106,7 @@ public MethodCallOperation( { ArgumentNullException.ThrowIfNull(executeAction); this.prepareAction = prepareAction; - this.executeAction = executeAction; + this.executeAction = executeAction ?? throw new ArgumentNullException(nameof(executeAction)); this.arguments = arguments; } } diff --git a/Orm/Xtensive.Orm/Orm/Providers/CommandProcessing/CommandProcessor.cs b/Orm/Xtensive.Orm/Orm/Providers/CommandProcessing/CommandProcessor.cs index 352c93b5e..f990e3b58 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/CommandProcessing/CommandProcessor.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/CommandProcessing/CommandProcessor.cs @@ -4,6 +4,7 @@ // Created by: Denis Krjuchkov // Created: 2009.08.20 +using System; using System.Collections.Generic; using System.Threading; using System.Threading.Tasks; diff --git a/Orm/Xtensive.Orm/Orm/Providers/CommandProcessing/DataReader.cs b/Orm/Xtensive.Orm/Orm/Providers/CommandProcessing/DataReader.cs index 413881b69..fe4bef7d3 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/CommandProcessing/DataReader.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/CommandProcessing/DataReader.cs @@ -2,11 +2,7 @@ // This code is distributed under MIT license terms. // See the License.txt file in the project root for more information. -using System; using System.Collections; -using System.Collections.Generic; -using System.Threading; -using System.Threading.Tasks; using Xtensive.Core; using Tuple = Xtensive.Tuples.Tuple; @@ -45,11 +41,32 @@ internal sealed class InMemoryDataReader(IEnumerable tuples) : DataReader public override void Dispose() => source.Dispose(); - public override async ValueTask DisposeAsync() => await ((IAsyncEnumerator) source).DisposeAsync().ConfigureAwaitFalse(); + /// + public async override ValueTask DisposeAsync() + { + if (source is IAsyncEnumerator asyncSource) { + // true async enumerable source + await asyncSource.DisposeAsync().ConfigureAwaitFalse(); + } + else { + // preloaded collection of elements, + // like in case of delayed query which has already been read from database + // or greedy enumeration + ((IEnumerator) source).Dispose(); + } + } public override ValueTask MoveNextAsync() => ValueTask.FromResult(MoveNext()); + } + /// + /// Creates wrapping active instance. + /// + /// instance to read data from. + /// instance + /// transforming raw database records to s. + /// to terminate operation if necessary. internal sealed class CommandDataReader(Command command, DbDataReaderAccessor accessor, CancellationToken token) : DataReader { /// @@ -61,6 +78,9 @@ internal sealed class CommandDataReader(Command command, DbDataReaderAccessor ac /// public override Tuple Current => command.ReadTupleWith(accessor); + public override ValueTask DisposeAsync() => command.DisposeAsync(); + + /// public override bool MoveNext() { @@ -90,8 +110,5 @@ public override async ValueTask MoveNextAsync() /// public override void Dispose() => command.Dispose(); - - /// - public override async ValueTask DisposeAsync() => await command.DisposeAsync().ConfigureAwaitFalse(); } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Providers/CommandProcessing/SqlLoadTask.cs b/Orm/Xtensive.Orm/Orm/Providers/CommandProcessing/SqlLoadTask.cs index 9dadea1d3..272504a0c 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/CommandProcessing/SqlLoadTask.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/CommandProcessing/SqlLoadTask.cs @@ -4,6 +4,7 @@ // Created by: Denis Krjuchkov // Created: 2009.08.21 +using System; using System.Collections.Generic; using Xtensive.Core; using Tuple = Xtensive.Tuples.Tuple; @@ -52,7 +53,7 @@ public SqlLoadTask(QueryRequest request, List output, ParameterContext pa Request = request; ParameterContext = parameterContext; - Output = output; + Output = output ?? throw new ArgumentNullException(nameof(output)); } } } \ No newline at end of file diff --git a/Orm/Xtensive.Orm/Orm/Providers/CommandWithDataReader.cs b/Orm/Xtensive.Orm/Orm/Providers/CommandWithDataReader.cs index d71fee8da..137d6d497 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/CommandWithDataReader.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/CommandWithDataReader.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2012-2020 Xtensive LLC. +// Copyright (C) 2012-2020 Xtensive LLC. // This code is distributed under MIT license terms. // See the License.txt file in the project root for more information. // Created by: Denis Krjuchkov diff --git a/Orm/Xtensive.Orm/Orm/Providers/Expressions/ExpressionProcessor.cs b/Orm/Xtensive.Orm/Orm/Providers/Expressions/ExpressionProcessor.cs index 8205ac52d..2babc71d7 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/Expressions/ExpressionProcessor.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/Expressions/ExpressionProcessor.cs @@ -470,7 +470,7 @@ protected override SqlExpression VisitNew(NewExpression n) return CompileMember(n.Constructor, null, n.Arguments.Select(a => Visit(a)).ToArray()); } - protected override SqlExpression VisitNewArray(NewArrayExpression expression) + protected override SqlContainer VisitNewArray(NewArrayExpression expression) { if (expression.NodeType!=ExpressionType.NewArrayInit) throw new NotSupportedException(); diff --git a/Orm/Xtensive.Orm/Orm/Providers/Expressions/QueryParameterIdentity.cs b/Orm/Xtensive.Orm/Orm/Providers/Expressions/QueryParameterIdentity.cs index 1b96f09b7..2edc5a832 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/Expressions/QueryParameterIdentity.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/Expressions/QueryParameterIdentity.cs @@ -41,8 +41,8 @@ public QueryParameterIdentity(TypeMapping mapping, object closureObject, string ArgumentNullException.ThrowIfNull(closureObject); ArgumentException.ThrowIfNullOrEmpty(fieldName); - Mapping = mapping; - ClosureObject = closureObject; + Mapping = mapping ?? throw new ArgumentNullException(nameof(mapping)); + ClosureObject = closureObject ?? throw new ArgumentNullException(nameof(closureObject)); FieldName = fieldName; BindingType = bindingType; } diff --git a/Orm/Xtensive.Orm/Orm/Providers/MappingResolver.cs b/Orm/Xtensive.Orm/Orm/Providers/MappingResolver.cs index d686d114d..f02c5ce6b 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/MappingResolver.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/MappingResolver.cs @@ -1,11 +1,11 @@ -// Copyright (C) 2012 Xtensive LLC. +// Copyright (C) 2012 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Denis Krjuchkov // Created: 2012.03.06 +using System; using System.Collections.Generic; -using Xtensive.Core; using Xtensive.Orm.Configuration; using Xtensive.Orm.Model; using Xtensive.Orm.Upgrade; diff --git a/Orm/Xtensive.Orm/Orm/Providers/MultidatabaseMappingResolver.cs b/Orm/Xtensive.Orm/Orm/Providers/MultidatabaseMappingResolver.cs index 984cf9a6c..cc55940b2 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/MultidatabaseMappingResolver.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/MultidatabaseMappingResolver.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2014 Xtensive LLC. +// Copyright (C) 2014 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Denis Krjuchkov @@ -87,8 +87,7 @@ from rule in configuration.MappingRules where db==database select string.IsNullOrEmpty(rule.Schema) ? configuration.DefaultSchema : rule.Schema; - return userSchemas - .Concat(Enumerable.Repeat(configuration.DefaultSchema, 1)) + return userSchemas.Append(configuration.DefaultSchema) .Distinct(); } @@ -97,7 +96,7 @@ private static IEnumerable GetDatabases(DomainConfiguration configuratio return configuration.MappingRules .Select(r => r.Database) .Where(db => !string.IsNullOrEmpty(db)) - .Concat(Enumerable.Repeat(configuration.DefaultDatabase, 1)) + .Append(configuration.DefaultDatabase) .Distinct(); } diff --git a/Orm/Xtensive.Orm/Orm/Providers/MultischemaMappingResolver.cs b/Orm/Xtensive.Orm/Orm/Providers/MultischemaMappingResolver.cs index 19812c160..b0bd5ba72 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/MultischemaMappingResolver.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/MultischemaMappingResolver.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2014 Xtensive LLC. +// Copyright (C) 2014 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Denis Krjuchkov @@ -7,6 +7,7 @@ using System; using System.Collections.Generic; using System.Linq; +using Xtensive.Collections; using Xtensive.Orm.Configuration; using Xtensive.Orm.Upgrade; using Xtensive.Sql; @@ -74,7 +75,7 @@ public MultischemaMappingResolver(DomainConfiguration configuration, NodeConfigu extractionTasks = configuration.MappingRules .Select(r => r.Schema) .Where(s => !string.IsNullOrEmpty(s)) - .Concat(Enumerable.Repeat(configuration.DefaultSchema, 1)) + .Append(configuration.DefaultSchema) .Distinct() .Select(s => new SqlExtractionTask(defaultSchemaInfo.Database, schemaMapping.Apply(s))) .ToList(); diff --git a/Orm/Xtensive.Orm/Orm/Providers/NameBuilder.cs b/Orm/Xtensive.Orm/Orm/Providers/NameBuilder.cs index fbb83dc0c..46b758fa6 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/NameBuilder.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/NameBuilder.cs @@ -578,12 +578,10 @@ public string ApplyNamingRules(string name) /// Computed hash. private static string GetHash(string name) { -#pragma warning disable SYSLIB0021 // Type or member is obsolete - using (var hashAlgorithm = new MD5CryptoServiceProvider()) { + using (var hashAlgorithm = MD5.Create()) { var hash = hashAlgorithm.ComputeHash(Encoding.UTF8.GetBytes(name)); return $"H{hash[0]:x2}{hash[1]:x2}{hash[2]:x2}{hash[3]:x2}"; } -#pragma warning restore SYSLIB0021 // Type or member is obsolete } private static string FormatKeyGeneratorName(string database, string name) diff --git a/Orm/Xtensive.Orm/Orm/Providers/Requests/QueryParameterBinding.cs b/Orm/Xtensive.Orm/Orm/Providers/Requests/QueryParameterBinding.cs index 3b1d96e68..b4d4a8ede 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/Requests/QueryParameterBinding.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/Requests/QueryParameterBinding.cs @@ -34,7 +34,7 @@ private QueryParameterBinding(TypeMapping typeMapping, Func - internal protected override SqlProvider VisitInclude(IncludeProvider provider) + internal protected override SqlIncludeProvider VisitInclude(IncludeProvider provider) { var source = Compile(provider.Source); var resultQuery = ExtractSqlSelect(provider, source); diff --git a/Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.NotSupported.cs b/Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.NotSupported.cs index 7d7c8f552..4c83940b7 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.NotSupported.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.NotSupported.cs @@ -12,19 +12,19 @@ namespace Xtensive.Orm.Providers public partial class SqlCompiler { /// - protected internal override SqlProvider VisitRaw(RawProvider provider) + internal protected override SqlProvider VisitRaw(RawProvider provider) { throw new NotSupportedException(); } /// - protected internal override SqlProvider VisitFreeText(FreeTextProvider provider) + internal protected override SqlProvider VisitFreeText(FreeTextProvider provider) { throw new NotSupportedException(); } /// - protected internal override SqlProvider VisitContainsTable(ContainsTableProvider provider) + internal protected override SqlProvider VisitContainsTable(ContainsTableProvider provider) { throw new NotSupportedException(); } diff --git a/Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.Paging.cs b/Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.Paging.cs index 12c9604a2..1331c63ae 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.Paging.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/SqlCompiler.Paging.cs @@ -160,4 +160,4 @@ private static Func BuildLimitOffsetAccessor(Func - internal protected override SqlProvider VisitStore(StoreProvider provider) + internal protected override SqlStoreProvider VisitStore(StoreProvider provider) { var source = provider.Source is RawProvider rawProvider ? (ExecutableProvider) (new Rse.Providers.ExecutableRawProvider(rawProvider)) diff --git a/Orm/Xtensive.Orm/Orm/Providers/SqlExecutor.cs b/Orm/Xtensive.Orm/Orm/Providers/SqlExecutor.cs index a29f34ae0..07e82bfbf 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/SqlExecutor.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/SqlExecutor.cs @@ -4,6 +4,7 @@ // Created by: Denis Krjuchkov // Created: 2012.02.29 +using System; using System.Collections.Generic; using System.Data; using System.Data.Common; diff --git a/Orm/Xtensive.Orm/Orm/Providers/SqlSelectProcessor.cs b/Orm/Xtensive.Orm/Orm/Providers/SqlSelectProcessor.cs index fbee7f252..2a3fb6b2a 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/SqlSelectProcessor.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/SqlSelectProcessor.cs @@ -1,6 +1,10 @@ +// Copyright (C) 2012-2026 Xtensive LLC. +// This code is distributed under MIT license terms. +// See the License.txt file in the project root for more information. + +using System; using System.Collections.Generic; using System.Linq; -using Xtensive.Core; using Xtensive.Sql; using Xtensive.Sql.Ddl; using Xtensive.Sql.Dml; diff --git a/Orm/Xtensive.Orm/Orm/Providers/StorageSequenceAccessor.cs b/Orm/Xtensive.Orm/Orm/Providers/StorageSequenceAccessor.cs index 75aca0d18..514a79644 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/StorageSequenceAccessor.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/StorageSequenceAccessor.cs @@ -7,6 +7,7 @@ using System; using System.Collections.Generic; using System.Linq; +using Xtensive.Collections; using Xtensive.Core; using Xtensive.IoC; using Xtensive.Orm.Configuration; diff --git a/Orm/Xtensive.Orm/Orm/Providers/TemporaryTables/RealTemporaryTableBackEnd.cs b/Orm/Xtensive.Orm/Orm/Providers/TemporaryTables/RealTemporaryTableBackEnd.cs index d96fd67d4..8b821c9cb 100644 --- a/Orm/Xtensive.Orm/Orm/Providers/TemporaryTables/RealTemporaryTableBackEnd.cs +++ b/Orm/Xtensive.Orm/Orm/Providers/TemporaryTables/RealTemporaryTableBackEnd.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2012 Xtensive LLC. +// Copyright (C) 2012 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Denis Krjuchkov @@ -10,7 +10,7 @@ namespace Xtensive.Orm.Providers { public class RealTemporaryTableBackEnd : TemporaryTableBackEnd { - public override Table CreateTemporaryTable(Schema schema, string tableName) + public override TemporaryTable CreateTemporaryTable(Schema schema, string tableName) { return schema.CreateTemporaryTable(tableName); } diff --git a/Orm/Xtensive.Orm/Orm/QueryEndpoint.cs b/Orm/Xtensive.Orm/Orm/QueryEndpoint.cs index 134f67a75..aa1c13bc8 100644 --- a/Orm/Xtensive.Orm/Orm/QueryEndpoint.cs +++ b/Orm/Xtensive.Orm/Orm/QueryEndpoint.cs @@ -290,7 +290,7 @@ public async ValueTask SingleAsync(Key key, CancellationToken token = de { if (key == null) return null; - var result = await SingleOrDefaultAsync(key, token).ConfigureAwait(false); + var result = await SingleOrDefaultAsync(key, token).ConfigureAwaitFalse(); if (result == null) throw new KeyNotFoundException(string.Format( Strings.EntityWithKeyXDoesNotExist, key)); @@ -338,7 +338,7 @@ private async ValueTask SingleOrDefaultInternal(Key key, bool isAsync, C } state = (isAsync) - ? await Session.Handler.FetchEntityStateAsync(key, token).ConfigureAwait(false) + ? await Session.Handler.FetchEntityStateAsync(key, token).ConfigureAwaitFalse() : Session.Handler.FetchEntityState(key); } else if (state.Tuple == null) { @@ -347,7 +347,7 @@ private async ValueTask SingleOrDefaultInternal(Key key, bool isAsync, C if (stateKeyType != keyType && !stateKeyType.IsAssignableFrom(keyType)) { Session.RemoveStateFromCache(state.Key, true); state = (isAsync) - ? await Session.Handler.FetchEntityStateAsync(key, token).ConfigureAwait(false) + ? await Session.Handler.FetchEntityStateAsync(key, token).ConfigureAwaitFalse() : Session.Handler.FetchEntityState(key); } } @@ -426,7 +426,7 @@ public T Single(params object[] keyValues) public async Task SingleAsync(object[] keyValues, CancellationToken token = default) where T : class, IEntity { - return (T) (object) (await SingleAsync(GetKeyByValues(keyValues), token).ConfigureAwait(false)); + return (T) (object) (await SingleAsync(GetKeyByValues(keyValues), token).ConfigureAwaitFalse()); } /// @@ -460,7 +460,7 @@ public T SingleOrDefault(Key key) public async Task SingleOrDefaultAsync(Key key, CancellationToken token = default) where T : class, IEntity { - return (T) (object) (await SingleOrDefaultAsync(key, token).ConfigureAwait(false)); + return (T) (object) (await SingleOrDefaultAsync(key, token).ConfigureAwaitFalse()); } /// diff --git a/Orm/Xtensive.Orm/Orm/QueryResult.cs b/Orm/Xtensive.Orm/Orm/QueryResult.cs index b483dc922..89c3f6bbf 100644 --- a/Orm/Xtensive.Orm/Orm/QueryResult.cs +++ b/Orm/Xtensive.Orm/Orm/QueryResult.cs @@ -55,9 +55,10 @@ public IEnumerator GetEnumerator() public async IAsyncEnumerable AsAsyncEnumerable() { EnsureResultsAlive(); - var enumerator = reader.AsAsyncEnumerator(); - while (await enumerator.MoveNextAsync().ConfigureAwaitFalse()) { - yield return enumerator.Current; + await using (var enumerator = reader.AsAsyncEnumerator()) { + while (await enumerator.MoveNextAsync().ConfigureAwaitFalse()) { + yield return enumerator.Current; + } } } diff --git a/Orm/Xtensive.Orm/Orm/QueryableExtensions.cs b/Orm/Xtensive.Orm/Orm/QueryableExtensions.cs index 72cd28db8..53600466f 100644 --- a/Orm/Xtensive.Orm/Orm/QueryableExtensions.cs +++ b/Orm/Xtensive.Orm/Orm/QueryableExtensions.cs @@ -328,7 +328,8 @@ public static bool In(this T source, IncludeAlgorithm algorithm, IEnumerable< /// /// One of provided arguments is . /// Queryable is not a query. - public static IQueryable LeftOuterJoin(this IQueryable outer, IEnumerable inner, Expression> outerKeySelector, Expression> innerKeySelector, Expression> resultSelector) + [Obsolete(".NET 10 has its own LeftJoin method declared, which will conflict with this. Use LeftJoinEx to prepare your code for future .NET change")] + public static IQueryable LeftJoin(this IQueryable outer, IEnumerable inner, Expression> outerKeySelector, Expression> innerKeySelector, Expression> resultSelector) { ArgumentNullException.ThrowIfNull(outer); ArgumentNullException.ThrowIfNull(inner); @@ -337,12 +338,51 @@ public static IQueryable LeftOuterJoin(t ArgumentNullException.ThrowIfNull(resultSelector); var outerProviderType = outer.Provider.GetType(); - if (outerProviderType!=WellKnownOrmTypes.QueryProvider) { + if (outerProviderType != WellKnownOrmTypes.QueryProvider) { var errorMessage = Strings.ExLeftJoinDoesNotSupportQueryProviderOfTypeX; throw new NotSupportedException(string.Format(errorMessage, outerProviderType)); } - var expression = Expression.Call(null, Traits.ExtensionLeftJoinMethodInfo, new[] {outer.Expression, GetSourceExpression(inner), outerKeySelector, innerKeySelector, resultSelector}); + var genericMethod = WellKnownMembers.Queryable.ExtensionLeftJoin.MakeGenericMethod(new[] { typeof(TOuter), typeof(TInner), typeof(TKey), typeof(TResult) }); + var expression = Expression.Call(null, genericMethod, new[] { outer.Expression, GetSourceExpression(inner), outerKeySelector, innerKeySelector, resultSelector }); + return outer.Provider.CreateQuery(expression); + } + + + public static IQueryable LeftOuterJoin(this IQueryable outer, IEnumerable inner, Expression> outerKeySelector, Expression> innerKeySelector, Expression> resultSelector) => + LeftJoinEx(outer, inner, outerKeySelector, innerKeySelector, resultSelector); + + /// + /// Correlates the elements of two sequences based on matching keys. + /// + /// The type of the elements of the first sequence. + /// The type of the elements of the second sequence. + /// The type of the keys returned by the key selector functions. + /// The type of the result elements. + /// The first sequence to join. + /// The sequence to join to the first sequence. + /// A function to extract the join key from each element of the first sequence. + /// A function to extract the join key from each element of the second sequence. + /// A function to create a result element from two matching elements. + /// + /// One of provided arguments is . + /// Queryable is not a query. + public static IQueryable LeftJoinEx(this IQueryable outer, IEnumerable inner, Expression> outerKeySelector, Expression> innerKeySelector, Expression> resultSelector) + { + ArgumentNullException.ThrowIfNull(outer); + ArgumentNullException.ThrowIfNull(inner); + ArgumentNullException.ThrowIfNull(outerKeySelector); + ArgumentNullException.ThrowIfNull(innerKeySelector); + ArgumentNullException.ThrowIfNull(resultSelector); + + var outerProviderType = outer.Provider.GetType(); + if (outerProviderType != WellKnownOrmTypes.QueryProvider) { + var errorMessage = Strings.ExLeftJoinDoesNotSupportQueryProviderOfTypeX; + throw new NotSupportedException(string.Format(errorMessage, outerProviderType)); + } + + var genericMethod = WellKnownMembers.Queryable.ExtensionLeftJoin.MakeGenericMethod(new[] { typeof(TOuter), typeof(TInner), typeof(TKey), typeof(TResult) }); + var expression = Expression.Call(null, genericMethod, new[] { outer.Expression, GetSourceExpression(inner), outerKeySelector, innerKeySelector, resultSelector }); return outer.Provider.CreateQuery(expression); } diff --git a/Orm/Xtensive.Orm/Orm/RecycledFieldDefinition.cs b/Orm/Xtensive.Orm/Orm/RecycledFieldDefinition.cs index e0e41d97e..956509cfc 100644 --- a/Orm/Xtensive.Orm/Orm/RecycledFieldDefinition.cs +++ b/Orm/Xtensive.Orm/Orm/RecycledFieldDefinition.cs @@ -66,9 +66,9 @@ private void Initialize(Type ownerType, string fieldName, Type fieldType) ArgumentException.ThrowIfNullOrEmpty(fieldName); ArgumentNullException.ThrowIfNull(fieldType); - OwnerType = ownerType; + OwnerType = ownerType ?? throw new ArgumentNullException(nameof(ownerType)); FieldName = fieldName; - FieldType = fieldType; + FieldType = fieldType ?? throw new ArgumentNullException(nameof(fieldType)); } public override string ToString() diff --git a/Orm/Xtensive.Orm/Orm/Rse/AggregateColumn.cs b/Orm/Xtensive.Orm/Orm/Rse/AggregateColumn.cs index 1c937a61e..32823cdd1 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/AggregateColumn.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/AggregateColumn.cs @@ -39,13 +39,13 @@ public override string ToString() } /// - public override Column Clone(ColNum newIndex) + public override AggregateColumn Clone(ColNum newIndex) { return new AggregateColumn(this, newIndex); } /// - public override Column Clone(string newName) + public override AggregateColumn Clone(string newName) { return new AggregateColumn(this, newName); } diff --git a/Orm/Xtensive.Orm/Orm/Rse/CalculatedColumn.cs b/Orm/Xtensive.Orm/Orm/Rse/CalculatedColumn.cs index 1abb8d19d..121a0cec8 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/CalculatedColumn.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/CalculatedColumn.cs @@ -35,13 +35,13 @@ public override string ToString() } /// - public override Column Clone(ColNum newIndex) + public override CalculatedColumn Clone(ColNum newIndex) { return new CalculatedColumn(this, newIndex); } /// - public override Column Clone(string newName) + public override CalculatedColumn Clone(string newName) { return new CalculatedColumn(this, newName); } diff --git a/Orm/Xtensive.Orm/Orm/Rse/CompilableProviderExtensions.cs b/Orm/Xtensive.Orm/Orm/Rse/CompilableProviderExtensions.cs index 3a9adab94..53fcdc721 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/CompilableProviderExtensions.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/CompilableProviderExtensions.cs @@ -24,32 +24,51 @@ namespace Xtensive.Orm.Rse /// public static class CompilableProviderExtensions { - public static CalculateProvider Calculate(this CompilableProvider source, - params CalculatedColumnDescriptor[] columns) - { - return new CalculateProvider(source, columns, false); - } - - public static CalculateProvider Calculate(this CompilableProvider source, bool isInlined, - params CalculatedColumnDescriptor[] columns) - { - return new CalculateProvider(source, columns, isInlined); - } - + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Calculated columns' descriptors. + /// instance. + public static CalculateProvider Calculate(this CompilableProvider source, params CalculatedColumnDescriptor[] columns) + => new CalculateProvider(source, columns, false); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Columns should be inlined or not. + /// Calculated columns' descriptors. + /// instance. + public static CalculateProvider Calculate(this CompilableProvider source, bool isInlined, params CalculatedColumnDescriptor[] columns) + => new CalculateProvider(source, columns, isInlined); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Calculated columns' descriptors. + /// instance. public static CalculateProvider Calculate(this CompilableProvider source, IReadOnlyList columns) - { - return new CalculateProvider(source, columns); - } - + => new CalculateProvider(source, columns); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Columns should be inlined or not. + /// Calculated columns' descriptors. + /// instance. public static CalculateProvider Calculate(this CompilableProvider source, bool isInlined, IReadOnlyList columns) - { - return new CalculateProvider(source, columns, isInlined); - } + => new CalculateProvider(source, columns, isInlined); - public static CompilableProvider RowNumber(this CompilableProvider source, string columnName) - { - return new RowNumberProvider(source, columnName); - } + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Name of column. + /// instance. + public static CompilableProvider RowNumber(this CompilableProvider source, string columnName) => new RowNumberProvider(source, columnName); public static CompilableProvider Join(this CompilableProvider left, CompilableProvider right, params (ColNum Left, ColNum Right)[] joinedColumnIndexes) @@ -80,92 +99,165 @@ public static CompilableProvider OrderBy(this CompilableProvider source, Directi return new SortProvider(source, columnIndexes); } - public static CompilableProvider Alias(this CompilableProvider source, string alias) - { - ArgumentException.ThrowIfNullOrEmpty(alias); - return new AliasProvider(source, alias); - } - - public static CompilableProvider Filter(this CompilableProvider source, Expression> predicate) - { - return new FilterProvider(source, predicate); - } - - public static CompilableProvider Select(this CompilableProvider source, IReadOnlyList columnIndexes) - { - ArgumentNullException.ThrowIfNull(columnIndexes); - return new SelectProvider(source, columnIndexes); - } - - public static CompilableProvider Seek(this CompilableProvider source, Func key) - { - return new SeekProvider(source, key); - } - - public static CompilableProvider Seek(this CompilableProvider source, Tuple key) - { - return new SeekProvider(source, key); - } - + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Alias. + /// instance. + public static CompilableProvider Alias(this CompilableProvider source, string alias) => new AliasProvider(source, alias); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Filtration predicate. + /// instance. + public static CompilableProvider Filter(this CompilableProvider source, Expression> predicate) => new FilterProvider(source, predicate); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Column indexes to select from the source. + /// instance. + public static CompilableProvider Select(this CompilableProvider source, IReadOnlyList columnIndexes) => new SelectProvider(source, columnIndexes); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Seek parameter. + /// instance. + public static CompilableProvider Seek(this CompilableProvider source, Func key) => new SeekProvider(source, key); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Seek parameter. + /// instance. + public static CompilableProvider Seek(this CompilableProvider source, Tuple key) => new SeekProvider(source, key); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Column indexes to group by. + /// Descriptors of aggregate columns. + /// instance. public static CompilableProvider Aggregate(this CompilableProvider recordQuery, IReadOnlyList groupIndexes, IEnumerable descriptors) { return new AggregateProvider(recordQuery, groupIndexes, (IReadOnlyList) descriptors); } - public static CompilableProvider Skip(this CompilableProvider source, Func count) - { - return new SkipProvider(source, count); - } - - public static CompilableProvider Skip(this CompilableProvider source, int count) - { - return new SkipProvider(source, count); - } - - public static CompilableProvider Take(this CompilableProvider source, Func count) - { - return new TakeProvider(source, count); - } - - public static CompilableProvider Take(this CompilableProvider source, int count) - { - return new TakeProvider(source, count); - } - - public static CompilableProvider Save(this CompilableProvider source) - { - return new StoreProvider(source); - } - - public static CompilableProvider Save(this CompilableProvider source, string name) - { - return new StoreProvider(source, name); - } - - public static CompilableProvider Distinct(this CompilableProvider source) - { - return new DistinctProvider(source); - } - - public static CompilableProvider Apply(this CompilableProvider source, - ApplyParameter applyParameter, CompilableProvider right) - { - return new ApplyProvider(applyParameter, source, right); - } - + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Column indexes to group by. + /// Descriptors of aggregate columns. + /// instance. + public static CompilableProvider Aggregate(this CompilableProvider recordQuery, + ColNum[] groupIndexes, IReadOnlyList descriptors) + => new AggregateProvider(recordQuery, groupIndexes, descriptors); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Skip amout function. + /// instance. + public static CompilableProvider Skip(this CompilableProvider source, Func count) => new SkipProvider(source, count); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Number of skippable items. + /// instance. + public static CompilableProvider Skip(this CompilableProvider source, int count) => new SkipProvider(source, count); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Take amount function. + /// instance. + public static TakeProvider Take(this CompilableProvider source, Func count) => new TakeProvider(source, count); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Number of items to take. + /// instance. + public static CompilableProvider Take(this CompilableProvider source, int count) => new TakeProvider(source, count); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// instance. + public static CompilableProvider Save(this CompilableProvider source) => new StoreProvider(source); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Name of saved data. + /// instance. + public static CompilableProvider Save(this CompilableProvider source, string name) => new StoreProvider(source, name); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// instance. + public static CompilableProvider Distinct(this CompilableProvider source) => new DistinctProvider(source); + + /// + /// Applies to the given source. + /// + /// Left source. + /// Apply parameter. + /// Compilable provider for right source (on each itteration of source). + /// instance. + public static CompilableProvider Apply(this CompilableProvider source, ApplyParameter applyParameter, CompilableProvider right) + => new ApplyProvider(applyParameter, source, right); + + /// + /// Applies to the given source. + /// + /// Left source. + /// Apply parameter. + /// Compilable provider for right source (on each itteration of source). + /// Inline column of apply provider or not. + /// Sequence type. + /// Apply type. + /// instance. public static CompilableProvider Apply(this CompilableProvider source, ApplyParameter applyParameter, CompilableProvider right, bool isInlined, ApplySequenceType sequenceType, JoinType applyType) - { - return new ApplyProvider(applyParameter, source, right, isInlined, sequenceType, applyType); - } - - public static CompilableProvider Existence(this CompilableProvider source, string existenceColumnName) - { - return new ExistenceProvider(source, existenceColumnName); - } - + => new ApplyProvider(applyParameter, source, right, isInlined, sequenceType, applyType); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Name of the existance column. + /// instance. + public static CompilableProvider Existence(this CompilableProvider source, string existenceColumnName) => new ExistenceProvider(source, existenceColumnName); + + /// + /// Applies to the given source. + /// + /// /// Compilable provider. + /// Filter data. + /// Result column name. + /// Filtered columns + /// instance. public static CompilableProvider Include(this CompilableProvider source, Expression>> filterDataSource, string resultColumnName, IReadOnlyList filteredColumns) { @@ -173,6 +265,15 @@ public static CompilableProvider Include(this CompilableProvider source, source, IncludeAlgorithm.Auto, false, filterDataSource, resultColumnName, filteredColumns); } + /// + /// Applies to the given source. + /// + /// /// Compilable provider. + /// Include algorithm. + /// Filter data. + /// Result column name. + /// Filtered columns + /// instance. public static CompilableProvider Include(this CompilableProvider source, IncludeAlgorithm algorithm, Expression>> filterDataSource, string resultColumnName, IReadOnlyList filteredColumns) @@ -180,6 +281,16 @@ public static CompilableProvider Include(this CompilableProvider source, return new IncludeProvider(source, algorithm, false, filterDataSource, resultColumnName, filteredColumns); } + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Include algorithm. + /// Result column should be inlined or not. + /// Filter data. + /// Result column name. + /// Filtered columns + /// instance. public static CompilableProvider Include(this CompilableProvider source, IncludeAlgorithm algorithm, bool isInlined, Expression>> filterDataSource, string resultColumnName, IReadOnlyList filteredColumns) @@ -187,47 +298,72 @@ public static CompilableProvider Include(this CompilableProvider source, return new IncludeProvider(source, algorithm, isInlined, filterDataSource, resultColumnName, filteredColumns); } - public static CompilableProvider Intersect(this CompilableProvider left, CompilableProvider right) - { - return new IntersectProvider(left, right); - } - - public static CompilableProvider Except(this CompilableProvider left, CompilableProvider right) - { - return new ExceptProvider(left, right); - } - - public static CompilableProvider Concat(this CompilableProvider left, CompilableProvider right) - { - return new ConcatProvider(left, right); - } - - public static CompilableProvider Union(this CompilableProvider left, CompilableProvider right) - { - return new UnionProvider(left, right); - } - - public static CompilableProvider Lock(this CompilableProvider source, - LockMode lockMode, LockBehavior lockBehavior) - { - return new LockProvider(source, lockMode, lockBehavior); - } - - public static CompilableProvider Lock(this CompilableProvider source, - Func lockMode, Func lockBehavior) - { - return new LockProvider(source, lockMode, lockBehavior); - } - - public static CompilableProvider Tag(this CompilableProvider source, string tag) - { - return new TagProvider(source, tag); - } - - public static CompilableProvider MakeVoid(this CompilableProvider source) - { - return new VoidProvider(source.Header); - } + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Compilable provider. + /// instance. + public static CompilableProvider Intersect(this CompilableProvider left, CompilableProvider right) => new IntersectProvider(left, right); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Compilable provider. + /// instance. + public static CompilableProvider Except(this CompilableProvider left, CompilableProvider right) => new ExceptProvider(left, right); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Compilable provider. + /// instance. + public static CompilableProvider Concat(this CompilableProvider left, CompilableProvider right) => new ConcatProvider(left, right); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Compilable provider. + /// instance. + public static CompilableProvider Union(this CompilableProvider left, CompilableProvider right) => new UnionProvider(left, right); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Lock mode. + /// Lock behavior + /// instance. + public static CompilableProvider Lock(this CompilableProvider source, LockMode lockMode, LockBehavior lockBehavior) + => new LockProvider(source, lockMode, lockBehavior); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Lock mode. + /// Lock behavior + /// instance. + public static CompilableProvider Lock(this CompilableProvider source, Func lockMode, Func lockBehavior) + => new LockProvider(source, lockMode, lockBehavior); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// Tag string + /// instance. + public static CompilableProvider Tag(this CompilableProvider source, string tag) => new TagProvider(source, tag); + + /// + /// Applies to the given source. + /// + /// Compilable provider. + /// instance. + public static CompilableProvider MakeVoid(this CompilableProvider source) => new VoidProvider(source.Header); public static CompilableProvider IndexHint(this CompilableProvider source, IndexInfo index) { diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/AliasProvider.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/AliasProvider.cs index 60593a884..6341969e4 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/AliasProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/AliasProvider.cs @@ -6,7 +6,7 @@ using System; using Xtensive.Collections; - +using Xtensive.Core; using Xtensive.Orm.Rse.Providers; namespace Xtensive.Orm.Rse.Providers @@ -46,8 +46,9 @@ protected override string ParametersToString() public AliasProvider(CompilableProvider source, string alias) : base(ProviderType.Alias, source) { + ArgumentException.ThrowIfNullOrEmpty(alias); Alias = alias; Initialize(); } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/ApplyProvider.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/ApplyProvider.cs index 4230cf662..0b90222a6 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/ApplyProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/ApplyProvider.cs @@ -78,7 +78,7 @@ public ApplyProvider(ApplyParameter applyParameter, CompilableProvider left, Com public ApplyProvider(ApplyParameter applyParameter, CompilableProvider left, CompilableProvider right, bool isInlined, ApplySequenceType applySequenceType, JoinType applyType) : base(ProviderType.Apply, left, right) { - ApplyParameter = applyParameter; + ApplyParameter = applyParameter ?? throw new ArgumentNullException(nameof(applyParameter)); IsInlined = isInlined; SequenceType = applySequenceType; ApplyType = applyType; diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/ContainsTableProvider.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/ContainsTableProvider.cs index 5c70569c0..d73ca9429 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/ContainsTableProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/ContainsTableProvider.cs @@ -52,7 +52,7 @@ public ContainsTableProvider(FullTextIndexInfo index, Func searchCriteria, string rankColumnName, IList targetColumns, Func topNByRank, bool fullFeatured) : base(ProviderType.ContainsTable) { - SearchCriteria = searchCriteria; + SearchCriteria = searchCriteria ?? throw new ArgumentNullException(nameof(searchCriteria)); FullFeatured = fullFeatured; PrimaryIndex = new IndexInfoRef(index.PrimaryIndex); TargetColumns = targetColumns.Select(tc => index.Columns.First(c => c.Column == tc)) diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/ExistenceProvider.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/ExistenceProvider.cs index f75c95170..e55705306 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/ExistenceProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/ExistenceProvider.cs @@ -4,9 +4,7 @@ // Created by: Alexis Kochetov // Created: 2009.03.20 -using System; -using System.Diagnostics; -using Xtensive.Collections; +using Xtensive.Core; using Xtensive.Reflection; using Xtensive.Tuples; using Tuple = Xtensive.Tuples.Tuple; @@ -44,8 +42,9 @@ protected override RecordSetHeader BuildHeader() public ExistenceProvider(CompilableProvider source, string existenceColumnName) : base(ProviderType.Existence, source) { + ArgumentException.ThrowIfNullOrEmpty(existenceColumnName); ExistenceColumnName = existenceColumnName; Initialize(); } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/FreeTextProvider.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/FreeTextProvider.cs index 99a76bcbd..20aba6d4e 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/FreeTextProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/FreeTextProvider.cs @@ -49,7 +49,7 @@ public FreeTextProvider( FullTextIndexInfo index, Func searchCriteria, string rankColumnName, Func topN, bool fullFeatured) : base(ProviderType.FreeText) { - SearchCriteria = searchCriteria; + SearchCriteria = searchCriteria ?? throw new ArgumentNullException(nameof(searchCriteria)); FullFeatured = fullFeatured; TopN = topN; PrimaryIndex = new IndexInfoRef(index.PrimaryIndex); diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/IncludeProvider.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/IncludeProvider.cs index 5f0ecfa8d..d57ba6046 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/IncludeProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/IncludeProvider.cs @@ -96,7 +96,7 @@ public IncludeProvider(CompilableProvider source, IncludeAlgorithm algorithm, bo ArgumentNullException.ThrowIfNull(filteredColumns); Algorithm = algorithm; IsInlined = isInlined; - FilterDataSource = filterDataSource; + FilterDataSource = filterDataSource ?? throw new ArgumentNullException(nameof(filterDataSource)); ResultColumnName = resultColumnName; FilteredColumns = filteredColumns; diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/LockProvider.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/LockProvider.cs index bb1b9c9f9..95f2e89af 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/LockProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/LockProvider.cs @@ -35,8 +35,8 @@ public sealed class LockProvider : UnaryProvider /// The property value. /// The mode of the lock to be acquired. /// The behavior of the lock. - public LockProvider(CompilableProvider source, LockMode lockMode, LockBehavior lockBehavior) : - base(ProviderType.Lock, source) + public LockProvider(CompilableProvider source, LockMode lockMode, LockBehavior lockBehavior) + : base(ProviderType.Lock, source) { LockMode = () => lockMode; LockBehavior = () => lockBehavior; @@ -49,11 +49,11 @@ public LockProvider(CompilableProvider source, LockMode lockMode, LockBehavior l /// The property value. /// The delegate returning the mode of the lock to be acquired. /// The delegate returning the behavior of the lock. - public LockProvider(CompilableProvider source, Func lockMode, Func lockBehavior) : - base(ProviderType.Lock, source) + public LockProvider(CompilableProvider source, Func lockMode, Func lockBehavior) + : base(ProviderType.Lock, source) { - LockMode = lockMode; - LockBehavior = lockBehavior; + LockMode = lockMode ?? throw new ArgumentNullException(nameof(lockMode)); + LockBehavior = lockBehavior ?? throw new ArgumentNullException(nameof(lockMode)); Initialize(); } } diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/OrderProviderBase.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/OrderProviderBase.cs index 524308a4d..61c760d57 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/OrderProviderBase.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/OrderProviderBase.cs @@ -97,7 +97,7 @@ protected override void Initialize() protected OrderProviderBase(ProviderType providerType, CompilableProvider source, DirectionCollection order) : base(providerType, source) { - Order = order; + Order = order ?? throw new ArgumentNullException(nameof(order)); } } } diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/PredicateJoinProvider.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/PredicateJoinProvider.cs index f128857d2..7f3abb06d 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/PredicateJoinProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/PredicateJoinProvider.cs @@ -45,7 +45,7 @@ public PredicateJoinProvider(CompilableProvider left, CompilableProvider right, Expression> predicate, JoinType joinType) : base(ProviderType.PredicateJoin, left, right) { - Predicate = predicate; + Predicate = predicate ?? throw new ArgumentNullException(nameof(predicate)); JoinType = joinType; Initialize(); } diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/RawProvider.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/RawProvider.cs index 00bac240f..2b0b27bbe 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/RawProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/RawProvider.cs @@ -66,8 +66,8 @@ protected override string ParametersToString() public RawProvider(RecordSetHeader header, Expression>> source) : base(ProviderType.Raw) { - Source = source; - this.header = header; + Source = source ?? throw new ArgumentNullException(nameof(source)); + this.header = header ?? throw new ArgumentNullException(nameof(header)); Initialize(); } } diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/StoreProvider.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/StoreProvider.cs index fd3485062..6d435c560 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/StoreProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/StoreProvider.cs @@ -57,7 +57,7 @@ public StoreProvider(RecordSetHeader header, string name) Name = name; - this.header = header; + this.header = header ?? throw new ArgumentNullException(nameof(header)); Initialize(); } @@ -91,7 +91,7 @@ public StoreProvider(CompilableProvider source) ArgumentNullException.ThrowIfNull(source); Name = Guid.NewGuid().ToString(); - Source = source; + Source = source ?? throw new ArgumentNullException(nameof(source)); header = source.Header; diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/UnaryProvider.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/UnaryProvider.cs index 84cda5e07..5014d4771 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/UnaryProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/UnaryProvider.cs @@ -4,6 +4,7 @@ // Created by: Alexey Kochetov // Created: 2008.07.22 +using System; using Xtensive.Collections; using Xtensive.Core; diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/VoidProvider.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/VoidProvider.cs index 14d648df0..480f83079 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/VoidProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/Compilable/VoidProvider.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2012 Xtensive LLC. +// Copyright (C) 2012 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Denis Krjuchkov diff --git a/Orm/Xtensive.Orm/Orm/Rse/Providers/ProviderVisitor.cs b/Orm/Xtensive.Orm/Orm/Rse/Providers/ProviderVisitor.cs index e5d851044..45d0c35e1 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Providers/ProviderVisitor.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Providers/ProviderVisitor.cs @@ -205,4 +205,4 @@ public abstract class ProviderVisitor /// internal protected abstract Provider VisitContainsTable(ContainsTableProvider provider); } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Orm/Rse/SystemColumn.cs b/Orm/Xtensive.Orm/Orm/Rse/SystemColumn.cs index f7d8bffde..9995e0796 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/SystemColumn.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/SystemColumn.cs @@ -16,13 +16,13 @@ namespace Xtensive.Orm.Rse public class SystemColumn : DerivedColumn { /// - public override Column Clone(ColNum newIndex) + public override SystemColumn Clone(ColNum newIndex) { return new SystemColumn(this, newIndex); } /// - public override Column Clone(string newName) + public override SystemColumn Clone(string newName) { return new SystemColumn(this, newName); } diff --git a/Orm/Xtensive.Orm/Orm/Rse/Transformation/ColumnMappingInspector.cs b/Orm/Xtensive.Orm/Orm/Rse/Transformation/ColumnMappingInspector.cs index bdcd9d61e..dcbe27fa9 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Transformation/ColumnMappingInspector.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Transformation/ColumnMappingInspector.cs @@ -336,7 +336,7 @@ internal protected override RowNumberProvider VisitRowNumber(RowNumberProvider p internal protected override CompilableProvider VisitStore(StoreProvider provider) { - if (!(provider.Source is CompilableProvider compilableSource)) { + if (provider.Source is not CompilableProvider compilableSource) { return provider; } @@ -443,18 +443,45 @@ private static List Merge(IEnumerable left, IEnumerable return resultList; } - private static List Merge(List leftMap, IEnumerable rightMap) + private static bool TryMergeFast(IEnumerable leftMap, IEnumerable rightMap, out List result) { - var preReturn = leftMap.Union(rightMap).ToList(leftMap.Count * 2); - preReturn.Sort(); - return preReturn; - } + Span usageMap = stackalloc bool[512]; + usageMap.Fill(false); + var uniqueCount = 0; + var biggestIndex = 0; - private static List Merge(List leftMap, IList rightMap) - { - var preReturn = leftMap.Union(rightMap).ToList(leftMap.Count + rightMap.Count); - preReturn.Sort(); - return preReturn; + // leftMap.Concat(rightMap) is slower! + foreach (var idx in leftMap) { + if (idx >= usageMap.Length) { + result = null; + return false; + } + if (!usageMap[idx]) { + uniqueCount++; + usageMap[idx] = true; + } + if (biggestIndex < idx) + biggestIndex = idx; + } + foreach (var idx in rightMap) { + if (idx >= usageMap.Length) { + result = null; + return false; + } + if (!usageMap[idx]) { + uniqueCount++; + usageMap[idx] = true; + } + if (biggestIndex < idx) + biggestIndex = idx; + } + var resultList = new List(uniqueCount); + for (int i = 0; i < biggestIndex + 1; i++) { + if (usageMap[i]) + resultList.Add(i); + } + result = resultList; + return true; } private static List MergeMappings(Provider originalLeft, IReadOnlyList leftMap, IReadOnlyList rightMap) diff --git a/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/ApplyFilterRewriter.cs b/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/ApplyFilterRewriter.cs index 62dce8af9..0777e9967 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/ApplyFilterRewriter.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/ApplyFilterRewriter.cs @@ -48,9 +48,9 @@ private void Initialize(Expression> predicate, { ArgumentNullException.ThrowIfNull(predicate); if (predicateColumns.Count == 0) - throw Exceptions.CollectionIsEmpty("predicateColumns"); + throw Exceptions.CollectionIsEmpty(nameof(predicateColumns)); if (currentColumns.Count == 0) - throw Exceptions.CollectionIsEmpty("currentColumns"); + throw Exceptions.CollectionIsEmpty(nameof(currentColumns)); sourceColumns = predicateColumns; targetColumns = currentColumns; } diff --git a/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/ApplyProviderCorrectorRewriter.cs b/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/ApplyProviderCorrectorRewriter.cs index 266b92dbc..596e00a06 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/ApplyProviderCorrectorRewriter.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/ApplyProviderCorrectorRewriter.cs @@ -196,7 +196,7 @@ internal protected override CompilableProvider VisitFilter(FilterProvider provid return predicateCollector.TryAdd(newProvider) ? source : newProvider; } - internal protected override CompilableProvider VisitAlias(AliasProvider provider) + internal protected override AliasProvider VisitAlias(AliasProvider provider) { var source = VisitCompilable(provider.Source); var newProvider = source!=provider.Source ? new AliasProvider(source, provider.Alias) : provider; @@ -259,7 +259,7 @@ internal protected override ExceptProvider VisitExcept(ExceptProvider provider) : provider; } - internal protected override CompilableProvider VisitConcat(ConcatProvider provider) + internal protected override ConcatProvider VisitConcat(ConcatProvider provider) { VisitBinaryProvider(provider, out var left, out var right); return left != provider.Left || right != provider.Right @@ -275,7 +275,7 @@ internal protected override UnionProvider VisitUnion(UnionProvider provider) : provider; } - internal protected override CompilableProvider VisitAggregate(AggregateProvider provider) + internal protected override AggregateProvider VisitAggregate(AggregateProvider provider) { var source = VisitCompilable(provider.Source); var newProvider = provider; diff --git a/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/CalculateRelatedExpressionRewriter.cs b/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/CalculateRelatedExpressionRewriter.cs index 61ece7b91..eac217653 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/CalculateRelatedExpressionRewriter.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/CalculateRelatedExpressionRewriter.cs @@ -10,6 +10,7 @@ using Xtensive.Orm.Internals; using Tuple = Xtensive.Tuples.Tuple; using ExpressionVisitor = Xtensive.Linq.ExpressionVisitor; +using System; namespace Xtensive.Orm.Rse.Transformation { diff --git a/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/OrderingRewriter.cs b/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/OrderingRewriter.cs index e85b8f52f..b2dd2d5b4 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/OrderingRewriter.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/OrderingRewriter.cs @@ -62,7 +62,7 @@ internal protected override CompilableProvider VisitSort(SortProvider provider) return source; } - internal protected override CompilableProvider VisitSelect(SelectProvider provider) + internal protected override SelectProvider VisitSelect(SelectProvider provider) { var result = provider; var source = VisitCompilable(provider.Source); @@ -93,7 +93,7 @@ internal protected override CompilableProvider VisitSelect(SelectProvider provid return result; } - internal protected override CompilableProvider VisitAggregate(AggregateProvider provider) + internal protected override AggregateProvider VisitAggregate(AggregateProvider provider) { var result = provider; var source = VisitCompilable(provider.Source); @@ -118,19 +118,19 @@ internal protected override CompilableProvider VisitAggregate(AggregateProvider return result; } - internal protected override CompilableProvider VisitIndex(IndexProvider provider) + internal protected override IndexProvider VisitIndex(IndexProvider provider) { sortOrder = new(); return provider; } - internal protected override CompilableProvider VisitFreeText(FreeTextProvider provider) + internal protected override FreeTextProvider VisitFreeText(FreeTextProvider provider) { sortOrder = new(); return provider; } - internal protected override CompilableProvider VisitContainsTable(ContainsTableProvider provider) + internal protected override ContainsTableProvider VisitContainsTable(ContainsTableProvider provider) { sortOrder = new(); return provider; @@ -142,7 +142,7 @@ internal protected override RawProvider VisitRaw(RawProvider provider) return provider; } - internal protected override CompilableProvider VisitStore(StoreProvider provider) + internal protected override StoreProvider VisitStore(StoreProvider provider) { sortOrder = new(); return provider; diff --git a/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/ParameterRewriter.cs b/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/ParameterRewriter.cs index 1c440ccfd..c614513f4 100644 --- a/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/ParameterRewriter.cs +++ b/Orm/Xtensive.Orm/Orm/Rse/Transformation/Internals/ParameterRewriter.cs @@ -4,6 +4,7 @@ // Created by: Alexander Nikolaev // Created: 2009.05.15 +using System; using System.Linq.Expressions; using Xtensive.Core; using Xtensive.Linq; diff --git a/Orm/Xtensive.Orm/Orm/Services/Old/DirectStateAccessor.cs b/Orm/Xtensive.Orm/Orm/Services/Old/DirectStateAccessor.cs index d1505b921..ff41c82a1 100644 --- a/Orm/Xtensive.Orm/Orm/Services/Old/DirectStateAccessor.cs +++ b/Orm/Xtensive.Orm/Orm/Services/Old/DirectStateAccessor.cs @@ -4,7 +4,7 @@ // Created by: Alex Yakunin // Created: 2010.01.14 -using Xtensive.Core; +using System; namespace Xtensive.Orm.Services { diff --git a/Orm/Xtensive.Orm/Orm/Services/QueryFormatter.cs b/Orm/Xtensive.Orm/Orm/Services/QueryFormatter.cs index dbe1c75a7..12bdf9bf4 100644 --- a/Orm/Xtensive.Orm/Orm/Services/QueryFormatter.cs +++ b/Orm/Xtensive.Orm/Orm/Services/QueryFormatter.cs @@ -4,6 +4,7 @@ // Created by: Dmitri Maximov // Created: 2011.03.02 +using System; using System.Collections.Generic; using System.Data.Common; using System.Linq; diff --git a/Orm/Xtensive.Orm/Orm/Session.Query.cs b/Orm/Xtensive.Orm/Orm/Session.Query.cs index 9cca13f93..23565e798 100644 --- a/Orm/Xtensive.Orm/Orm/Session.Query.cs +++ b/Orm/Xtensive.Orm/Orm/Session.Query.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2003-2010 Xtensive LLC. +// Copyright (C) 2003-2010 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Alexis Kochetov diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/CatalogCloner.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/CatalogCloner.cs index 54a2bfc81..b4b232f6c 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/CatalogCloner.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/CatalogCloner.cs @@ -32,7 +32,7 @@ public Catalog Clone(Catalog source, MappingResolver mappingResolver, string new private Dictionary CloneSchemas(Catalog newCatalog, Catalog sourceCatalog, MappingResolver mappingResolver) { - var schemaMap = new Dictionary(); + var schemaMap = new Dictionary(sourceCatalog.Schemas.Count); foreach (var schema in sourceCatalog.Schemas) { var complexName = mappingResolver.GetNodeName(newCatalog.Name, schema.Name, "Dummy"); var names = complexName.Split(NameElementSeparator); @@ -60,7 +60,7 @@ private void ClonePartitionFuctionsAndSchemas(Catalog newCatalog, Catalog source } foreach (var partitionSchema in source.PartitionSchemas) - newCatalog.CreatePartitionSchema(partitionSchema.Name, pfMap[partitionSchema.PartitionFunction], partitionSchema.Filegroups.ToArray()); + _ = newCatalog.CreatePartitionSchema(partitionSchema.Name, pfMap[partitionSchema.PartitionFunction], partitionSchema.Filegroups.ToArray()); } private void CloneSchemas(Catalog newCatalog, Catalog source, Dictionary schemaMap) @@ -111,7 +111,7 @@ private void CloneDomains(Schema newSchema, Schema sourceSchema, Dictionary table.TableColumns[el.Column.Name]).Cast().ToArray(); + if (newTable is Table table) + return sourceIndex.Columns.Select(el => table.TableColumns[el.Column.Name] as DataTableColumn).ToArray(); - var view = newTable as View; - if (view!=null) - return sourceIndex.Columns.Select(el => view.ViewColumns[el.Column.Name]).Cast().ToArray(); + if (newTable is View view) + return sourceIndex.Columns.Select(el => view.ViewColumns[el.Column.Name] as DataTableColumn).ToArray(); throw new ArgumentOutOfRangeException("newTable", Strings.ExUnexpectedTypeOfParameter); } private DataTableColumn[] GetNonKeyColumns(DataTable newTable, Index sourceIndex) { - var table = newTable as Table; - if (table!=null) - return sourceIndex.NonkeyColumns.Select(el => table.TableColumns[el.Name]).Cast().ToArray(); + if (newTable is Table table) + return sourceIndex.NonkeyColumns.Select(el => table.TableColumns[el.Name] as DataTableColumn).ToArray(); - var view = newTable as View; - if (view!=null) - return sourceIndex.NonkeyColumns.Select(el => view.ViewColumns[el.Name]).Cast().ToArray(); + if (newTable is View view) + return sourceIndex.NonkeyColumns.Select(el => view.ViewColumns[el.Name] as DataTableColumn).ToArray(); throw new ArgumentOutOfRangeException("newTable", Strings.ExUnexpectedTypeOfParameter); } private void CloneTableConstraint(Table newTable, TableConstraint sourceConstraint) { - var checkConstraint = sourceConstraint as CheckConstraint; - if (checkConstraint!=null) { + if (sourceConstraint is CheckConstraint checkConstraint) { var c = newTable.CreateCheckConstraint(checkConstraint.Name, checkConstraint.Condition.Clone()); CopyDbName(c, checkConstraint); return; } - var defaultConstraint = sourceConstraint as DefaultConstraint; - if (defaultConstraint!=null) { + if (sourceConstraint is DefaultConstraint defaultConstraint) { var c = newTable.CreateDefaultConstraint(defaultConstraint.Name, newTable.TableColumns[defaultConstraint.Column.Name]); c.NameIsStale = defaultConstraint.NameIsStale; CopyDbName(c, defaultConstraint); @@ -337,12 +329,10 @@ private void CloneTableConstraint(Table newTable, TableConstraint sourceConstrai return; } - var uniqueConstraint = sourceConstraint as UniqueConstraint; - if (uniqueConstraint!=null) { - var primaryKey = sourceConstraint as PrimaryKey; - if (primaryKey!=null) { + if (sourceConstraint is UniqueConstraint uniqueConstraint) { + if (sourceConstraint is PrimaryKey primaryKey) { var columns = primaryKey.Columns.Select(c => newTable.TableColumns[c.Name]).ToArray(); - var pk =newTable.CreatePrimaryKey(primaryKey.Name, columns); + var pk = newTable.CreatePrimaryKey(primaryKey.Name, columns); CopyDbName(pk, primaryKey); } else { @@ -352,13 +342,13 @@ private void CloneTableConstraint(Table newTable, TableConstraint sourceConstrai } return; } - throw new ArgumentOutOfRangeException("sourceConstraint", Strings.ExUnexpectedTypeOfParameter); + throw new ArgumentOutOfRangeException(nameof(sourceConstraint), Strings.ExUnexpectedTypeOfParameter); } private void ClonePartitionDescriptor(IPartitionable newObject, IPartitionable oldObject) { var oldPartitionDescriptor = oldObject.PartitionDescriptor; - if (oldPartitionDescriptor==null) + if (oldPartitionDescriptor is null) return; var column = GetPartitionColumn(newObject, oldPartitionDescriptor); @@ -372,41 +362,35 @@ private void ClonePartitionDescriptor(IPartitionable newObject, IPartitionable o private void ClonePartition(PartitionDescriptor newPartitionDescriptor, Partition oldPartition) { - var hashPartition = oldPartition as HashPartition; - if (hashPartition!=null) { + if (oldPartition is HashPartition hashPartition) { var newPartition = newPartitionDescriptor.CreateHashPartition(hashPartition.Filegroup); CopyDbName(oldPartition, newPartition); return; } - var listPartition = oldPartition as ListPartition; - if (listPartition!=null) { + if (oldPartition is ListPartition listPartition) { var newPartition = newPartitionDescriptor.CreateListPartition(listPartition.Filegroup, (string[]) listPartition.Values.Clone()); CopyDbName(oldPartition, newPartition); return; } - var rangePartition = oldPartition as RangePartition; - if (rangePartition!=null) { + if (oldPartition is RangePartition rangePartition) { var newPartition = newPartitionDescriptor.CreateRangePartition(rangePartition.Filegroup, rangePartition.Boundary); CopyDbName(oldPartition, newPartition); return; } - throw new ArgumentOutOfRangeException("oldPartition", Strings.ExUnexpectedTypeOfParameter); + throw new ArgumentOutOfRangeException(nameof(oldPartition), Strings.ExUnexpectedTypeOfParameter); } private TableColumn GetPartitionColumn(IPartitionable newObject, PartitionDescriptor oldPartitionDescriptor) { - var table = newObject as Table; - if (table!=null) + if (newObject is Table table) return table.TableColumns[oldPartitionDescriptor.Column.Name]; - var index = newObject as Index; - if (index!=null) { - var tableColumn = index.Columns[oldPartitionDescriptor.Column.Name].Column as TableColumn; - if (tableColumn!=null) + if (newObject is Index index) { + if (index.Columns[oldPartitionDescriptor.Column.Name].Column is TableColumn tableColumn) return tableColumn; throw new InvalidOperationException(Strings.ExUnableToGetTableColumnInstanceFromIndex); } - throw new ArgumentOutOfRangeException("newObject", Strings.ExUnexpectedTypeOfParameter); + throw new ArgumentOutOfRangeException(nameof(newObject), Strings.ExUnexpectedTypeOfParameter); } private void CopyDbName(Node newNode, Node sourceNode) diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/DomainModelConverter.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/DomainModelConverter.cs index 2682ec688..5741e6e8d 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/DomainModelConverter.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/DomainModelConverter.cs @@ -7,7 +7,6 @@ using System; using System.Collections.Generic; using System.Linq; -using Xtensive.Collections; using Xtensive.Core; using Xtensive.Modelling; using Xtensive.Orm.Building.Builders; @@ -69,10 +68,10 @@ public StorageModel Run() protected override IPathNode Visit(Orm.Model.Node node) { var indexInfo = node as IndexInfo; - if (indexInfo!=null && indexInfo.IsPrimary) { + if (indexInfo is not null && indexInfo.IsPrimary) { foreach (var table in CreateTables(indexInfo)) { currentTable = table; - var result = VisitPrimaryIndexInfo(indexInfo); + _ = VisitPrimaryIndexInfo(indexInfo); currentTable = null; } return null; @@ -82,10 +81,10 @@ protected override IPathNode Visit(Orm.Model.Node node) } /// - protected override IPathNode VisitDomainModel(DomainModel domainModel) + protected override StorageModel VisitDomainModel(DomainModel domainModel) { // Build tables, columns and primary indexes - foreach (var primaryIndex in domainModel.RealIndexes.Where(i => i.IsPrimary)) + foreach (var primaryIndex in domainModel.RealIndexes.Where(static i => i.IsPrimary)) _ = Visit(primaryIndex); // Build full-text indexes @@ -96,9 +95,10 @@ protected override IPathNode VisitDomainModel(DomainModel domainModel) var buildForeignKeys = BuildForeignKeys && providerInfo.Supports(ProviderFeatures.ForeignKeyConstraints); - if (buildForeignKeys) + if (buildForeignKeys) { foreach (var group in domainModel.Associations.Where(a => a.Ancestors.Count==0)) _ = Visit(group); + } // Build keys and sequences foreach (KeyInfo keyInfo in domainModel.Hierarchies.Select(h => h.Key)) @@ -113,17 +113,17 @@ protected override IPathNode VisitDomainModel(DomainModel domainModel) // Build hierarchy foreign keys var indexPairs = new Dictionary<(IndexInfo, IndexInfo), object>(); foreach (var type in domainModel.Types.Entities) { - if (type.Hierarchy==null || type.Hierarchy.InheritanceSchema==InheritanceSchema.ConcreteTable) + if (type.Hierarchy is null || type.Hierarchy.InheritanceSchema==InheritanceSchema.ConcreteTable) continue; if (type.Indexes.PrimaryIndex.IsVirtual) { - Dictionary typeOrder = type.Ancestors + var typeOrder = type.Ancestors .Append(type) - .Select((t, i) => (Type: t, Index: i)) - .ToDictionary(a => a.Type, a => a.Index); - List realPrimaryIndexes = type.Indexes.RealPrimaryIndexes + .Select(static (t, i) => (Type: t, Index: i)) + .ToDictionary(static a => a.Type, static a => a.Index, capacity: type.Ancestors.Count); + var realPrimaryIndexes = type.Indexes.RealPrimaryIndexes .OrderBy(index => typeOrder[index.ReflectedType]) - .ToList(); - for (int i = 0; i < realPrimaryIndexes.Count - 1; i++) { + .ToArray(type.Indexes.RealPrimaryIndexes.Count); + for (int i = 0, edge = realPrimaryIndexes.Length - 1; i < edge; i++) { if (realPrimaryIndexes[i]!=realPrimaryIndexes[i + 1]) { var pair = (realPrimaryIndexes[i], realPrimaryIndexes[i + 1]); indexPairs[pair] = null; @@ -137,9 +137,9 @@ protected override IPathNode VisitDomainModel(DomainModel domainModel) var referencingTable = targetModel.Tables[resolver.GetNodeName(referencingIndex.ReflectedType)]; var referencedTable = targetModel.Tables[resolver.GetNodeName(referencedIndex.ReflectedType)]; var storageReferencingIndex = FindIndex( - referencingTable, referencingIndex.KeyColumns.Select(ci => ci.Key.Name).ToList()); + referencingTable, referencingIndex.KeyColumns.Select(static ci => ci.Key.Name).ToArray()); - string foreignKeyName = nameBuilder.BuildHierarchyForeignKeyName(referencingIndex.ReflectedType, referencedIndex.ReflectedType); + var foreignKeyName = nameBuilder.BuildHierarchyForeignKeyName(referencingIndex.ReflectedType, referencedIndex.ReflectedType); CreateHierarchyForeignKey(referencingTable, referencedTable, storageReferencingIndex, foreignKeyName); } @@ -154,8 +154,8 @@ private void VisitIndexInfo(IndexInfo primaryIndex, IndexInfo index) var isClustered = index.IsClustered && providerInfo.Supports(ProviderFeatures.ClusteredIndexes); secondaryIndex.IsClustered = isClustered; foreach (KeyValuePair pair in index.KeyColumns) { - string columName = GetPrimaryIndexColumnName(primaryIndex, pair.Key); - StorageColumnInfo column = table.Columns[columName]; + var columName = GetPrimaryIndexColumnName(primaryIndex, pair.Key); + var column = table.Columns[columName]; _ = new KeyColumnRef(secondaryIndex, column, providerInfo.Supports(ProviderFeatures.KeyColumnSortOrder) ? pair.Value @@ -167,8 +167,8 @@ private void VisitIndexInfo(IndexInfo primaryIndex, IndexInfo index) // and simply ignore included columns for clustered indexes. if (providerInfo.Supports(ProviderFeatures.IncludedColumns) && !isClustered) { foreach (var includedColumn in index.IncludedColumns) { - string columName = GetPrimaryIndexColumnName(primaryIndex, includedColumn); - StorageColumnInfo column = table.Columns[columName]; + var columName = GetPrimaryIndexColumnName(primaryIndex, includedColumn); + var column = table.Columns[columName]; _ = new IncludedColumnRef(secondaryIndex, column); } } @@ -176,7 +176,7 @@ private void VisitIndexInfo(IndexInfo primaryIndex, IndexInfo index) } /// - protected override IPathNode VisitColumnInfo(ColumnInfo column) + protected override StorageColumnInfo VisitColumnInfo(ColumnInfo column) { var nonNullableType = column.ValueType; var nullableType = ToNullable(nonNullableType, column.IsNullable); @@ -214,7 +214,7 @@ protected override IPathNode VisitAssociationInfo(AssociationInfo association) if (association.OnTargetRemove==OnRemoveAction.None) return null; - if (association.AuxiliaryType==null && !association.OwnerField.IsEntitySet) { + if (association.AuxiliaryType is null && !association.OwnerField.IsEntitySet) { if (!IsValidForeignKeyTarget(association.TargetType)) return null; if (association.OwnerType.IsInterface) { @@ -229,16 +229,16 @@ protected override IPathNode VisitAssociationInfo(AssociationInfo association) } } } - else if (association.AuxiliaryType!=null && association.IsMaster) { + else if (association.AuxiliaryType is not null && association.IsMaster) { ProcessIndirectAssociation(association.AuxiliaryType); } return null; } /// - protected override IPathNode VisitKeyInfo(KeyInfo keyInfo) + protected override StorageSequenceInfo VisitKeyInfo(KeyInfo keyInfo) { - if (keyInfo.Sequence==null || !keyInfo.IsFirstAmongSimilarKeys) + if (keyInfo.Sequence is null || !keyInfo.IsFirstAmongSimilarKeys) return null; var sequenceInfo = keyInfo.Sequence; long increment = 1; @@ -260,7 +260,7 @@ protected override IPathNode VisitSequenceInfo(Orm.Model.SequenceInfo info) } /// - protected override IPathNode VisitFullTextIndexInfo(FullTextIndexInfo fullTextIndex) + protected override StorageFullTextIndexInfo VisitFullTextIndexInfo(FullTextIndexInfo fullTextIndex) { if (!providerInfo.Supports(ProviderFeatures.FullText)) { UpgradeLog.Warning(nameof(Strings.LogFullTextIndexesAreNotSupportedByCurrentStorageIgnoringIndexX), fullTextIndex.Name); @@ -274,7 +274,7 @@ protected override IPathNode VisitFullTextIndexInfo(FullTextIndexInfo fullTextIn var column = table.Columns[fullTextColumn.Name]; string typeColumn = null; if(providerInfo.Supports(ProviderFeatures.FullTextColumnDataTypeSpecification)) { - if (fullTextColumn.TypeColumn!=null) + if (fullTextColumn.TypeColumn is not null) typeColumn = table.Columns[fullTextColumn.TypeColumn.Name].Name; } else @@ -293,19 +293,19 @@ protected override IPathNode VisitFullTextIndexInfo(FullTextIndexInfo fullTextIn /// /// The index. /// Visit result. - private IPathNode VisitPrimaryIndexInfo(IndexInfo index) + private PrimaryIndexInfo VisitPrimaryIndexInfo(IndexInfo index) { foreach (var column in index.Columns) _ = Visit(column); // Support for mysql as primary indexes there always have name 'PRIMARY' - string name = providerInfo.ConstantPrimaryIndexName; + var name = providerInfo.ConstantPrimaryIndexName; if (string.IsNullOrEmpty(name)) name = index.MappingName; var primaryIndex = new PrimaryIndexInfo(currentTable, name); - foreach (KeyValuePair pair in index.KeyColumns) { - string columName = GetPrimaryIndexColumnName(index, pair.Key); + foreach (var pair in index.KeyColumns) { + var columName = GetPrimaryIndexColumnName(index, pair.Key); var column = currentTable.Columns[columName]; _ = new KeyColumnRef(primaryIndex, column, providerInfo.Supports(ProviderFeatures.KeyColumnSortOrder) @@ -315,24 +315,24 @@ private IPathNode VisitPrimaryIndexInfo(IndexInfo index) primaryIndex.PopulateValueColumns(); primaryIndex.IsClustered = index.IsClustered && providerInfo.Supports(ProviderFeatures.ClusteredIndexes); - foreach (var secondaryIndex in index.ReflectedType.Indexes.Where(i => i.IsSecondary && !i.IsVirtual)) + foreach (var secondaryIndex in index.ReflectedType.Indexes.Where(static i => i.IsSecondary && !i.IsVirtual)) VisitIndexInfo(index, secondaryIndex); return primaryIndex; } - private IEnumerable CreateTables(IndexInfo index) + private IReadOnlyList CreateTables(IndexInfo index) { - var result = new List(); var type = index.ReflectedType; - if (configuration.IsMultidatabase && type.UnderlyingType.Namespace==MetadataNamespace) { + if (configuration.IsMultidatabase && type.UnderlyingType.Namespace == MetadataNamespace) { + var parts = new List(sourceModel.Databases.Count); foreach (var db in sourceModel.Databases) { var name = resolver.GetNodeName(db.Name, type.MappingSchema, type.MappingName); - result.Add(new TableInfo(targetModel, name)); + parts.Add(new TableInfo(targetModel, name)); } + return parts; } else - result.Add(new TableInfo(targetModel, resolver.GetNodeName(type))); - return result; + return new[] { new TableInfo(targetModel, resolver.GetNodeName(type)) }; } #region Not supported @@ -371,7 +371,7 @@ protected override IPathNode VisitIndexInfo(IndexInfo index) private object GetColumnDefaultValue(ColumnInfo column, StorageTypeInfo typeInfo) { - if (column.DefaultValue!=null) + if (column.DefaultValue is not null) return column.DefaultValue; if (column.IsNullable) @@ -394,22 +394,29 @@ private string GetColumnDefaultSqlExpression(ColumnInfo column) private static StorageIndexInfo FindIndex(TableInfo table, ICollection keyColumns) { - var primaryKeyColumns = table.PrimaryIndex.KeyColumns.Select(cr => cr.Value.Name).ToList(); + var primaryIndex = table.PrimaryIndex; + var primaryKeyColumns = primaryIndex.KeyColumns.Select(ColumnNameSelector).ToList(primaryIndex.KeyColumns.Count); if (!primaryKeyColumns.Except(keyColumns).Union(keyColumns.Except(primaryKeyColumns)).Any()) return table.PrimaryIndex; foreach (SecondaryIndexInfo index in table.SecondaryIndexes) { - var secondaryKeyColumns = index.KeyColumns.Select(cr => cr.Value.Name).ToList(); + var secondaryKeyColumns = index.KeyColumns.Select(ColumnNameSelector).ToList(index.KeyColumns.Count); if (!secondaryKeyColumns.Except(keyColumns).Union(keyColumns.Except(secondaryKeyColumns)).Any()) return index; } return null; + + + static string ColumnNameSelector(KeyColumnRef cr) + { + return cr.Value.Name; + } } private TableInfo GetTable(TypeInfo type) { - if (type.Hierarchy==null || type.Hierarchy.InheritanceSchema!=InheritanceSchema.SingleTable) { + if (type.Hierarchy is null || type.Hierarchy.InheritanceSchema!=InheritanceSchema.SingleTable) { var name = resolver.GetNodeName(type); return targetModel.Tables.FirstOrDefault(t => t.Name==name); } @@ -433,7 +440,7 @@ private static string GetPrimaryIndexColumnName(IndexInfo primaryIndex, ColumnIn private static void CreateReferenceForeignKey(TableInfo referencingTable, TableInfo referencedTable, FieldInfo referencingField, string foreignKeyName) { - var foreignColumns = referencingField.Columns.Select(column => referencingTable.Columns[column.Name]).ToList(); + var foreignColumns = referencingField.Columns.Select(column => referencingTable.Columns[column.Name]).ToArray(); var foreignKey = new ForeignKeyInfo(referencingTable, foreignKeyName) { PrimaryKey = referencedTable.PrimaryIndex, OnRemoveAction = ReferentialAction.None, @@ -445,8 +452,7 @@ private static void CreateReferenceForeignKey(TableInfo referencingTable, TableI private static void CreateHierarchyForeignKey(TableInfo referencingTable, TableInfo referencedTable, StorageIndexInfo referencingIndex, string foreignKeyName) { - var foreignKey = new ForeignKeyInfo(referencingTable, foreignKeyName) - { + var foreignKey = new ForeignKeyInfo(referencingTable, foreignKeyName) { PrimaryKey = referencedTable.PrimaryIndex, OnRemoveAction = ReferentialAction.None, OnUpdateAction = ReferentialAction.None @@ -465,7 +471,7 @@ private void ProcessDirectAssociation(TypeInfo ownerType, FieldInfo ownerField, return; var referencingTable = GetTable(ownerType); var referencedTable = GetTable(targetType); - if (referencedTable==null || referencingTable==null) + if (referencedTable is null || referencingTable is null) return; var foreignKeyName = nameBuilder.BuildReferenceForeignKeyName(ownerType, ownerField, targetType); CreateReferenceForeignKey(referencingTable, referencedTable, ownerField, foreignKeyName); @@ -474,14 +480,14 @@ private void ProcessDirectAssociation(TypeInfo ownerType, FieldInfo ownerField, private void ProcessIndirectAssociation(TypeInfo auxiliaryType) { var referencingTable = GetTable(auxiliaryType); - if (referencingTable==null) + if (referencingTable is null) return; - foreach (var field in auxiliaryType.Fields.Where(fieldInfo => fieldInfo.IsEntity)) { + foreach (var field in auxiliaryType.Fields.Where(static fieldInfo => fieldInfo.IsEntity)) { var referencedType = sourceModel.Types[field.ValueType]; if (!IsValidForeignKeyTarget(referencedType) || !AreMappedToSameDatabase(auxiliaryType, referencedType)) continue; var referencedTable = GetTable(referencedType); - if (referencedTable==null) + if (referencedTable is null) continue; var foreignKeyName = nameBuilder.BuildReferenceForeignKeyName(auxiliaryType, field, referencedType); CreateReferenceForeignKey(referencingTable, referencedTable, field, foreignKeyName); @@ -495,17 +501,17 @@ private bool AreMappedToSameDatabase(TypeInfo type1, TypeInfo type2) private IEnumerable GetForeignKeyOwners(TypeInfo type) { - if (type.Hierarchy == null) + if (type.Hierarchy is null) yield break; yield return type; if (type.Hierarchy.InheritanceSchema == InheritanceSchema.ConcreteTable) - foreach (var descendant in type.AllDescendants.Where(static descendant => descendant.Indexes.PrimaryIndex != null)) + foreach (var descendant in type.AllDescendants.Where(static descendant => descendant.Indexes.PrimaryIndex is not null)) yield return descendant; } private static bool IsValidForeignKeyTarget(TypeInfo targetType) { - return targetType.Hierarchy != null && (targetType.Hierarchy.InheritanceSchema != InheritanceSchema.ConcreteTable || targetType.IsLeaf); + return targetType.Hierarchy is not null && (targetType.Hierarchy.InheritanceSchema != InheritanceSchema.ConcreteTable || targetType.IsLeaf); } #endregion @@ -522,7 +528,7 @@ private SecondaryIndexInfo CreateSecondaryIndex(TableInfo owningTable, string in { var index = new SecondaryIndexInfo(owningTable, indexName); - if (originalModelIndex.Filter!=null) { + if (originalModelIndex.Filter is not null) { if (providerInfo.Supports(ProviderFeatures.PartialIndexes)) index.Filter = new PartialIndexFilterInfo(compiler.Compile(handlers, originalModelIndex)); else @@ -561,7 +567,7 @@ private StoredFieldInfo GetExtractedStoredColumn(ColumnInfo column) var currentType = CurrentModelTypes.GetValueOrDefault(typeName); if(currentType==null) throw new InvalidOperationException(string.Format(Strings.ExUnableToFindTypeXInCurrentModel, typeName)); - var currentField = currentType.Fields.Flatten(f=>f.Fields, info => { }, true).FirstOrDefault(el => el.MappingName==column.Field.MappingName); + var currentField = currentType.Fields.Flatten(static f => f.Fields, info => { }, true).FirstOrDefault(el => el.MappingName==column.Field.MappingName); if (currentField==null) throw new InvalidOperationException(string.Format(Strings.UnableToFindColumnXInTypeYOfCurrentModel, column.Field.MappingName, typeName)); @@ -573,7 +579,7 @@ private StorageTypeInfo GetStorageTypeInfo(StorageTypeInfo typeInfo, StorageColu { if (!isUpgradingStage) return typeInfo; - if (extractedConnectedColumn==null) + if (extractedConnectedColumn is null) return typeInfo; var extractedTypeInfo = extractedConnectedColumn.Type; if (IsOnlyNullableChanged(typeInfo, extractedTypeInfo)) { diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/ExtractedModelBuilderFactory.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/ExtractedModelBuilderFactory.cs index cf6dad767..2ead36f6c 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/ExtractedModelBuilderFactory.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/ExtractedModelBuilderFactory.cs @@ -1,10 +1,10 @@ -// Copyright (C) 2016 Xtensive LLC. +// Copyright (C) 2016 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Alexey Kulakov // Created: 2016.02.23 -using Xtensive.Core; +using System; using Xtensive.Orm.Upgrade.Internals.Interfaces; namespace Xtensive.Orm.Upgrade.Internals diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/Metadata/ExtensionMetadata.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/Metadata/ExtensionMetadata.cs index fdc38d266..b1ed3feab 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/Metadata/ExtensionMetadata.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/Metadata/ExtensionMetadata.cs @@ -1,10 +1,10 @@ -// Copyright (C) 2012 Xtensive LLC. +// Copyright (C) 2012 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Denis Krjuchkov // Created: 2012.02.16 -using Xtensive.Core; +using System; namespace Xtensive.Orm.Upgrade; diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/Metadata/TypeMetadata.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/Metadata/TypeMetadata.cs index 3246e2162..3cce4f69b 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/Metadata/TypeMetadata.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/Metadata/TypeMetadata.cs @@ -4,6 +4,7 @@ // Created by: Denis Krjuchkov // Created: 2012.02.16 +using System; using Xtensive.Core; using Xtensive.Reflection; diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/NodeExtractedModelBuilder.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/NodeExtractedModelBuilder.cs index d1142e5d2..2c13d7ead 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/NodeExtractedModelBuilder.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/NodeExtractedModelBuilder.cs @@ -4,6 +4,7 @@ // Created by: Alexey Kulakov // Created: 2016.02.23 +using System; using System.Collections.Generic; using System.Linq; using Xtensive.Core; diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/SchemaComparer.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/SchemaComparer.cs index 5e2f17bae..12b43e1ba 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/SchemaComparer.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/SchemaComparer.cs @@ -103,7 +103,7 @@ public static SchemaComparisonResult Compare( createTableActions.Cast() .Concat(createColumnActions.Cast()) .Concat(columnTypeChangeActions.Cast()) - .ToList(); + .ToArray(createTableActions.Count + createColumnActions.Count + columnTypeChangeActions.Count); return new SchemaComparisonResult( comparisonStatus, columnTypeChangeActions.Count > 0, isCompatibleInLegacyMode, diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/SqlActionTranslator.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/SqlActionTranslator.cs index c024644bc..5c79d7b49 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/SqlActionTranslator.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/SqlActionTranslator.cs @@ -1410,13 +1410,13 @@ public SqlActionTranslator( sequenceQueryBuilder = handlers.SequenceQueryBuilder; typeIdColumnName = handlers.NameBuilder.TypeIdColumnName; - this.resolver = resolver; - this.sqlModel = sqlModel; - this.actions = actions; - this.sourceModel = sourceModel; - this.targetModel = targetModel; - this.enforceChangedColumns = enforceChangedColumns; - this.sqlExecutor = sqlExecutor; + this.resolver = resolver ?? throw new ArgumentNullException(nameof(resolver)); + this.sqlModel = sqlModel ?? throw new ArgumentNullException(nameof(sqlModel)); + this.actions = actions ?? throw new ArgumentNullException(nameof(actions)); + this.sourceModel = sourceModel ?? throw new ArgumentNullException(nameof(sourceModel)); + this.targetModel = targetModel ?? throw new ArgumentNullException(nameof(targetModel)); + this.enforceChangedColumns = enforceChangedColumns ?? throw new ArgumentNullException(nameof(enforceChangedColumns)); + this.sqlExecutor = sqlExecutor ?? throw new ArgumentNullException(nameof(sqlExecutor)); this.allowCreateConstraints = allowCreateConstraints; if (providerInfo.Supports(ProviderFeatures.Collations)) { diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/SqlModelConverter.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/SqlModelConverter.cs index 757dd93c6..b55a092c4 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/SqlModelConverter.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/SqlModelConverter.cs @@ -42,10 +42,11 @@ internal sealed class SqlModelConverter : SqlModelVisitor /// The storage model. public StorageModel Run() { - if (targetModel==null) { + if (targetModel is null) { targetModel = new StorageModel(); - foreach (var catalog in sourceModel.Catalogs) - VisitCatalog(catalog); + foreach (var catalog in sourceModel.Catalogs) { + _ = VisitCatalog(catalog); + } } return targetModel; @@ -58,14 +59,14 @@ protected override IPathNode VisitSchema(Schema schema) { // Build tables, columns and indexes. foreach (var table in schema.Tables) - Visit(table); + _ = Visit(table); // Build foreign keys. var foreignKeys = schema.Tables.SelectMany(t => t.TableConstraints.OfType()); foreach (var foreignKey in foreignKeys) - Visit(foreignKey); + _ = Visit(foreignKey); foreach (var sequence in schema.Sequences) - VisitSequence(sequence); + _ = VisitSequence(sequence); return null; } @@ -74,8 +75,7 @@ protected override IPathNode VisitSchema(Schema schema) protected override IPathNode Visit(Node node) { if (!providerInfo.Supports(ProviderFeatures.Sequences)) { - var table = node as Table; - if (table!=null && IsGeneratorTable(table)) + if (node is Table table && IsGeneratorTable(table)) return VisitGeneratorTable(table); } @@ -83,22 +83,22 @@ protected override IPathNode Visit(Node node) } /// - protected override IPathNode VisitTable(Table table) + protected override TableInfo VisitTable(Table table) { var tableInfo = new TableInfo(targetModel, resolver.GetNodeName(table)); currentTable = tableInfo; foreach (var column in table.TableColumns) - Visit(column); + _ = Visit(column); var primaryKey = table.TableConstraints .SingleOrDefault(constraint => constraint is PrimaryKey); - if (primaryKey!=null) - Visit(primaryKey); + if (primaryKey is not null) + _ = Visit(primaryKey); foreach (var index in table.Indexes) - Visit(index); + _ = Visit(index); currentTable = null; @@ -106,7 +106,7 @@ protected override IPathNode VisitTable(Table table) } /// - protected override IPathNode VisitTableColumn(TableColumn tableColumn) + protected override StorageColumnInfo VisitTableColumn(TableColumn tableColumn) { var tableInfo = currentTable; var typeInfo = ExtractType(tableColumn); @@ -115,7 +115,7 @@ protected override IPathNode VisitTableColumn(TableColumn tableColumn) } /// - protected override IPathNode VisitForeignKey(ForeignKey key) + protected override ForeignKeyInfo VisitForeignKey(ForeignKey key) { var referencingTable = targetModel.Tables[resolver.GetNodeName(key.Owner)]; var referencingColumns = new List(); @@ -131,21 +131,22 @@ protected override IPathNode VisitForeignKey(ForeignKey key) var referencedTable = targetModel.Tables[resolver.GetNodeName(key.ReferencedTable)]; foreignKeyInfo.PrimaryKey = referencedTable.PrimaryIndex; - foreach (var column in referencingColumns) - new ForeignKeyColumnRef(foreignKeyInfo, column); + foreach (var column in referencingColumns) { + _ = new ForeignKeyColumnRef(foreignKeyInfo, column); + } return foreignKeyInfo; } /// - protected override IPathNode VisitPrimaryKey(PrimaryKey key) + protected override PrimaryIndexInfo VisitPrimaryKey(PrimaryKey key) { var tableInfo = currentTable; - var primaryIndexInfo = new PrimaryIndexInfo(tableInfo, key.Name) {IsClustered = key.IsClustered}; + var primaryIndexInfo = new PrimaryIndexInfo(tableInfo, key.Name) { IsClustered = key.IsClustered }; foreach (var keyColumn in key.Columns) - new KeyColumnRef(primaryIndexInfo, tableInfo.Columns[keyColumn.Name], - Direction.Positive); + _ = new KeyColumnRef(primaryIndexInfo, tableInfo.Columns[keyColumn.Name]); + // TODO: Get direction for key columns primaryIndexInfo.PopulateValueColumns(); @@ -153,7 +154,7 @@ protected override IPathNode VisitPrimaryKey(PrimaryKey key) } /// - protected override IPathNode VisitFullTextIndex(FullTextIndex index) + protected override StorageFullTextIndexInfo VisitFullTextIndex(FullTextIndex index) { var tableInfo = currentTable; var name = index.Name.IsNullOrEmpty() @@ -165,16 +166,17 @@ protected override IPathNode VisitFullTextIndex(FullTextIndex index) }; foreach (var column in index.Columns) { var columnInfo = tableInfo.Columns[column.Column.Name]; - string typeColumn = null; - if (column.TypeColumn!=null) - typeColumn = tableInfo.Columns[column.TypeColumn.Name].Name; - new FullTextColumnRef(ftIndex, columnInfo, column.Languages.Single().Name, typeColumn); + var typeColumnName = (column.TypeColumn is not null) + ? tableInfo.Columns[column.TypeColumn.Name].Name + : null; + + _ = new FullTextColumnRef(ftIndex, columnInfo, column.Languages.Single().Name, typeColumnName); } return ftIndex; } /// - protected override IPathNode VisitIndex(Index index) + protected override SecondaryIndexInfo VisitIndex(Index index) { var tableInfo = currentTable; var secondaryIndexInfo = new SecondaryIndexInfo(tableInfo, index.Name) { @@ -185,13 +187,13 @@ protected override IPathNode VisitIndex(Index index) foreach (var keyColumn in index.Columns) { var columnInfo = tableInfo.Columns[keyColumn.Column.Name]; - new KeyColumnRef(secondaryIndexInfo, + _ = new KeyColumnRef(secondaryIndexInfo, columnInfo, keyColumn.Ascending ? Direction.Positive : Direction.Negative); } foreach (var valueColumn in index.NonkeyColumns) { var columnInfo = tableInfo.Columns[valueColumn.Name]; - new IncludedColumnRef(secondaryIndexInfo, columnInfo); + _ = new IncludedColumnRef(secondaryIndexInfo, columnInfo); } secondaryIndexInfo.PopulatePrimaryKeyColumns(); @@ -203,13 +205,13 @@ protected override IPathNode VisitIndex(Index index) { var tableName = resolver.GetNodeName(index.DataTable); var result = partialIndexMap.FindIndex(tableName, index.DbName); - return result == null - ? null - : new PartialIndexFilterInfo(result.Filter); + if (result is null) + return null; + return new PartialIndexFilterInfo(result.Filter); } /// - protected override IPathNode VisitSequence(Sequence sequence) + protected override StorageSequenceInfo VisitSequence(Sequence sequence) { var sequenceInfo = new StorageSequenceInfo(targetModel, resolver.GetNodeName(sequence)) { Increment = sequence.SequenceDescriptor.Increment.Value @@ -237,7 +239,7 @@ protected override IPathNode VisitCatalog(Catalog catalog) /// /// The generator table. /// Visit result. - private IPathNode VisitGeneratorTable(Table generatorTable) + private StorageSequenceInfo VisitGeneratorTable(Table generatorTable) { var idColumn = generatorTable.TableColumns[0]; var startValue = idColumn.SequenceDescriptor.StartValue; @@ -284,20 +286,14 @@ private StorageTypeInfo ExtractType(TableColumn column) /// Converted action. private ReferentialAction ConvertReferentialAction(Sql.ReferentialAction toConvert) { - switch (toConvert) { - case Sql.ReferentialAction.NoAction: - return ReferentialAction.None; - case Sql.ReferentialAction.Restrict: - return ReferentialAction.Restrict; - case Sql.ReferentialAction.Cascade: - return ReferentialAction.Cascade; - case Sql.ReferentialAction.SetNull: - return ReferentialAction.Clear; - case Sql.ReferentialAction.SetDefault: - return ReferentialAction.Default; - default: - return ReferentialAction.Default; - } + return toConvert switch { + Sql.ReferentialAction.NoAction => ReferentialAction.None, + Sql.ReferentialAction.Restrict => ReferentialAction.Restrict, + Sql.ReferentialAction.Cascade => ReferentialAction.Cascade, + Sql.ReferentialAction.SetNull => ReferentialAction.Clear, + Sql.ReferentialAction.SetDefault => ReferentialAction.Default, + _ => ReferentialAction.Default, + }; } /// @@ -307,18 +303,13 @@ private ReferentialAction ConvertReferentialAction(Sql.ReferentialAction toConve /// Converted mode. private FullTextChangeTrackingMode ConvertChangeTrackingMode(ChangeTrackingMode toConvert) { - switch (toConvert) { - case ChangeTrackingMode.Auto: - return FullTextChangeTrackingMode.Auto; - case ChangeTrackingMode.Manual: - return FullTextChangeTrackingMode.Manual; - case ChangeTrackingMode.Off: - return FullTextChangeTrackingMode.Off; - case ChangeTrackingMode.OffWithNoPopulation: - return FullTextChangeTrackingMode.OffWithNoPopulation; - default: - return FullTextChangeTrackingMode.Default; - } + return toConvert switch { + ChangeTrackingMode.Auto => FullTextChangeTrackingMode.Auto, + ChangeTrackingMode.Manual => FullTextChangeTrackingMode.Manual, + ChangeTrackingMode.Off => FullTextChangeTrackingMode.Off, + ChangeTrackingMode.OffWithNoPopulation => FullTextChangeTrackingMode.OffWithNoPopulation, + _ => FullTextChangeTrackingMode.Default, + }; } /// @@ -333,7 +324,7 @@ private bool IsGeneratorTable(Table table) { int columnNumber = providerInfo.Supports(ProviderFeatures.InsertDefaultValues) ? 1 : 2; return table.TableColumns.Count==columnNumber && - table.TableColumns[0].SequenceDescriptor!=null; + table.TableColumns[0].SequenceDescriptor is not null; } diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/TypeIdProvider.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/TypeIdProvider.cs index ab7f8c1ab..ffba1b6db 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/TypeIdProvider.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/TypeIdProvider.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2012-2020 Xtensive LLC. +// Copyright (C) 2012-2020 Xtensive LLC. // This code is distributed under MIT license terms. // See the License.txt file in the project root for more information. // Created by: Denis Krjuchkov diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/UpgradeActionSequenceBuilder.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/UpgradeActionSequenceBuilder.cs index e49895759..0a70f0ff2 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/UpgradeActionSequenceBuilder.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/UpgradeActionSequenceBuilder.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2012 Xtensive LLC. +// Copyright (C) 2012 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Denis Krjuchkov @@ -58,7 +58,7 @@ private static List SelectOutput(UpgradeActionSequence result, SqlUpgrad case SqlUpgradeStage.Cleanup: return result.CleanupCommands; default: - throw new ArgumentOutOfRangeException("stage"); + throw new ArgumentOutOfRangeException(nameof(stage)); } } diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/UpgradeHintsProcessingResult.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/UpgradeHintsProcessingResult.cs index 98552cdbb..c675e53f3 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/UpgradeHintsProcessingResult.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/UpgradeHintsProcessingResult.cs @@ -4,6 +4,7 @@ // Created by: Alexey Kulakov // Created: 2015.01.22 +using System; using System.Collections.Generic; using System.Linq; using Xtensive.Collections; diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/UpgradeHintsProcessor.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/UpgradeHintsProcessor.cs index 3f95d5165..80ad9a651 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Internals/UpgradeHintsProcessor.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Internals/UpgradeHintsProcessor.cs @@ -209,8 +209,6 @@ private void BuildTypeMapping(IReadOnlyDictionary rename currentNonConnectorTypes = GetNonConnectorTypes(currentModel); var newModelTypes = currentNonConnectorTypes.ToDictionary(type => type.UnderlyingType, currentModel.Types.Length); - //var renameLookup = renameTypeHints.ToDictionary(hint => hint.OldType, renameTypeHints.Count); - //var removeLookup = removeTypeHints.ToDictionary(hint => hint.Type, removeTypeHints.Count); // Types that are neither mapped nor removed. var suspects = new HashSet(); diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Model/PrimaryIndexInfo.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Model/PrimaryIndexInfo.cs index 5c6fb3122..189736999 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Model/PrimaryIndexInfo.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Model/PrimaryIndexInfo.cs @@ -45,11 +45,9 @@ protected override void ValidateState() base.ValidateState(); var tableColumns = Parent.Columns; - var keys = KeyColumns.Select(keyRef => keyRef.Value).ToList(); - var values = ValueColumns.Select(valueRef => valueRef.Value).ToList(); - var all = keys.Concat(values).ToList(); + var keys = KeyColumns.Select(keyRef => keyRef.Value).ToArray(KeyColumns.Count); - if (keys.Count==0) + if (keys.Length==0) ea.Execute(() => { throw new ValidationException(Strings.ExEmptyKeyColumnsCollection, Path); }); @@ -58,11 +56,13 @@ protected override void ValidateState() throw new ValidationException(Strings.ExPrimaryKeyColumnCanNotBeNullable, Path); }); - if (all.Count!=tableColumns.Count) + var values = ValueColumns.Select(valueRef => valueRef.Value).ToArray(ValueColumns.Count); + var allCount = keys.Length + values.Length; + if (allCount!=tableColumns.Count) ea.Execute(() => { throw new ValidationException(Strings.ExInvalidPrimaryKeyStructure, Path); }); - if (all.Zip(tableColumns, (column, tableColumn) => (column, tableColumn)).Any(p => p.Item1 != p.Item2)) + if (keys.Concat(values).Zip(tableColumns, (column, tableColumn) => (column, tableColumn)).Any(p => p.Item1 != p.Item2)) ea.Execute(() => { throw new ValidationException(Strings.ExInvalidPrimaryKeyStructure, Path); }); diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Model/SecondaryIndexInfo.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Model/SecondaryIndexInfo.cs index 79419afe4..3450785ee 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Model/SecondaryIndexInfo.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Model/SecondaryIndexInfo.cs @@ -67,8 +67,8 @@ protected override void ValidateState() ea.Execute(base.ValidateState); // Secondary key columns: empty set, duplicates - var keyColumns = KeyColumns.Select(valueRef => valueRef.Value).ToList(); - if (keyColumns.Count==0) + var keyColumns = KeyColumns.Select(valueRef => valueRef.Value).ToArray(KeyColumns.Count); + if (keyColumns.Length==0) ea.Execute(() => { throw new ValidationException(Strings.ExEmptyKeyColumnsCollection, Path); }); diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/Model/StorageFullTextIndexInfo.cs b/Orm/Xtensive.Orm/Orm/Upgrade/Model/StorageFullTextIndexInfo.cs index c2b19636f..b683a05b4 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/Model/StorageFullTextIndexInfo.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/Model/StorageFullTextIndexInfo.cs @@ -61,9 +61,8 @@ protected override void ValidateState() base.ValidateState(); var tableColumns = Parent.Columns; - var columns = Columns.Select(keyRef => keyRef.Value).ToList(); - if (columns.Count == 0) { + if (Columns.Select(keyRef => keyRef.Value).Any()) { ea.Execute(() => { throw new ValidationException(Strings.ExEmptyColumnsCollection, Path); }); diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/SystemUpgradeHandler.cs b/Orm/Xtensive.Orm/Orm/Upgrade/SystemUpgradeHandler.cs index 4de4612d0..897ab4bae 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/SystemUpgradeHandler.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/SystemUpgradeHandler.cs @@ -192,9 +192,13 @@ private Dictionary BuildMetadata(Domain domain, TypeIdRegis var database = group.Key; var metadata = group.Value; Func filter = t => t.MappingDatabase==database; - var types = model.Types.Where(filter).ToList(); + var types = new List(model.Types.Count); + var assemblies = new HashSet(); + foreach (var databaseType in model.Types.Where(filter)) { + types.Add(databaseType); + _ = assemblies.Add(databaseType.UnderlyingType.Assembly); + } var typeMetadata = GetTypeMetadata(types, registry); - var assemblies = types.Select(t => t.UnderlyingType.Assembly).ToHashSet(); var assemblyMetadata = GetAssemblyMetadata(assemblies); var storedModel = model.ToStoredModel(registry, filter); // Since we support storage nodes, stored domain model and real model of a node diff --git a/Orm/Xtensive.Orm/Orm/Upgrade/UpgradingDomainBuilder.cs b/Orm/Xtensive.Orm/Orm/Upgrade/UpgradingDomainBuilder.cs index d0ffe39ed..627b4711c 100644 --- a/Orm/Xtensive.Orm/Orm/Upgrade/UpgradingDomainBuilder.cs +++ b/Orm/Xtensive.Orm/Orm/Upgrade/UpgradingDomainBuilder.cs @@ -168,16 +168,48 @@ private async Task RunAsync(CancellationToken token = default) private void CompleteUpgradeTransaction() { var connection = context.Services.Connection; - if (connection.ActiveTransaction is not null) { - context.Services.StorageDriver.CommitTransaction(null, connection, true); + var driver = context.Services.StorageDriver; + + if (connection.ActiveTransaction == null) { + return; + } + + try { + driver.CommitTransaction(null, connection); + } + catch { + // If transaction has become broken during commit its rollback leads to new exception + // which will overwrite the original one. + // Check for active transaction should work because on exception within + // driver.Commit it is set to NULL. + if (connection.ActiveTransaction != null) { + driver.RollbackTransaction(null, connection); + } + throw; } } private async ValueTask CompleteUpgradeTransactionAsync(CancellationToken token) { var connection = context.Services.Connection; - if (connection.ActiveTransaction is not null) { - await context.Services.StorageDriver.CommitTransactionAsync(null, connection, true, token); + var driver = context.Services.StorageDriver; + + if (connection.ActiveTransaction == null) { + return; + } + + try { + await driver.CommitTransactionAsync(null, connection, token: token); + } + catch { + // If transaction has become broken during commit its rollback leads to new exception + // which will overwrite the original one. + // Check for active transaction should work because on exception within + // driver.Commit it is set to NULL. + if (connection.ActiveTransaction != null) { + await driver.RollbackTransactionAsync(null, connection, token); + } + throw; } } diff --git a/Orm/Xtensive.Orm/Orm/Validation/EntityErrorInfo.cs b/Orm/Xtensive.Orm/Orm/Validation/EntityErrorInfo.cs index 80f584605..85b16abc2 100644 --- a/Orm/Xtensive.Orm/Orm/Validation/EntityErrorInfo.cs +++ b/Orm/Xtensive.Orm/Orm/Validation/EntityErrorInfo.cs @@ -1,9 +1,10 @@ -// Copyright (C) 2013-2020 Xtensive LLC. +// Copyright (C) 2013-2020 Xtensive LLC. // This code is distributed under MIT license terms. // See the License.txt file in the project root for more information. // Created by: Denis Krjuchkov // Created: 2013.09.09 +using System; using System.Collections.Generic; using Xtensive.Core; diff --git a/Orm/Xtensive.Orm/Orm/Validation/ValidationResult.cs b/Orm/Xtensive.Orm/Orm/Validation/ValidationResult.cs index cb89c3a57..5cdb23690 100644 --- a/Orm/Xtensive.Orm/Orm/Validation/ValidationResult.cs +++ b/Orm/Xtensive.Orm/Orm/Validation/ValidationResult.cs @@ -1,3 +1,4 @@ +using System; using Xtensive.Core; using Xtensive.Orm.Model; diff --git a/Orm/Xtensive.Orm/Orm/VersionCapturer.cs b/Orm/Xtensive.Orm/Orm/VersionCapturer.cs index 2364f377d..d0826d8eb 100644 --- a/Orm/Xtensive.Orm/Orm/VersionCapturer.cs +++ b/Orm/Xtensive.Orm/Orm/VersionCapturer.cs @@ -130,8 +130,7 @@ public static VersionCapturer Attach(Session session, VersionSet versions) private VersionCapturer(Session session, VersionSet versions) : base(session) { - ArgumentNullException.ThrowIfNull(versions); - Versions = versions; + Versions = versions ?? throw new ArgumentNullException(nameof(versions)); AttachEventHandlers(); } diff --git a/Orm/Xtensive.Orm/Reflection/MethodHelper.cs b/Orm/Xtensive.Orm/Reflection/MethodHelper.cs index 4ed670219..f1d5b0e32 100644 --- a/Orm/Xtensive.Orm/Reflection/MethodHelper.cs +++ b/Orm/Xtensive.Orm/Reflection/MethodHelper.cs @@ -106,6 +106,11 @@ public static ConstructorInfo GetConstructorEx(this Type type, BindingFlags bind if (parameterTypes.All(o => o is not null)) { return type.GetConstructor(bindingFlags, null, parameterTypes, null); } + else if (parameterTypes.All(o => o is Type)) { + return type.GetConstructor(bindingFlags, null, + parameterTypes.ToArray(), null); + } + ConstructorInfo lastMatch = null; foreach (var ci in type.GetConstructors(bindingFlags)) { diff --git a/Orm/Xtensive.Orm/Reflection/WellKnown.QueryableExtensions.cs b/Orm/Xtensive.Orm/Reflection/WellKnown.QueryableExtensions.cs index 23dc01dd3..bacdb26b6 100644 --- a/Orm/Xtensive.Orm/Reflection/WellKnown.QueryableExtensions.cs +++ b/Orm/Xtensive.Orm/Reflection/WellKnown.QueryableExtensions.cs @@ -13,6 +13,8 @@ public static class QueryableExtensions { public const string Count = nameof(Orm.QueryableExtensions.Count); public const string LeftOuterJoin = nameof(Orm.QueryableExtensions.LeftOuterJoin); + public const string LeftJoin = nameof(Orm.QueryableExtensions.LeftJoin); + public const string LeftJoinEx = nameof(Orm.QueryableExtensions.LeftJoinEx); public const string Lock = nameof(Orm.QueryableExtensions.Lock); public const string Take = nameof(Orm.QueryableExtensions.Take); public const string Skip = nameof(Orm.QueryableExtensions.Skip); diff --git a/Orm/Xtensive.Orm/Sorting/NodeConnection.cs b/Orm/Xtensive.Orm/Sorting/NodeConnection.cs index cc317f0c3..64e7f9fbe 100644 --- a/Orm/Xtensive.Orm/Sorting/NodeConnection.cs +++ b/Orm/Xtensive.Orm/Sorting/NodeConnection.cs @@ -83,8 +83,8 @@ public NodeConnection(Node source, Node(1); Traverse(root, joins); - List tables = new(); - List joinTypes = new(); - List conditions = new(); + var tables = new List(); + var joinTypes = new List(joins.Count); + var conditions = new List(joins.Count); foreach (var item in joins) { - var left = item.Left; - if (!(left is SqlJoinedTable)) - tables.Add(left); - var right = item.Right; - if (!(right is SqlJoinedTable)) - tables.Add(right); + if (item.Left is not SqlJoinedTable) + tables.Add(item.Left); + if (item.Right is not SqlJoinedTable) + tables.Add(item.Right); joinTypes.Add(item.JoinType); conditions.Add(item.Expression); } var pivot = tables[0]; tables.RemoveAt(0); - return new(pivot, tables, joinTypes, conditions); + return new JoinSequence(pivot, tables, joinTypes, conditions); } private static void Traverse(SqlJoinedTable root, List output) { var joinExpression = root.JoinExpression; - if (joinExpression.Left is SqlJoinedTable joinedLeft) { + var left = joinExpression.Left; + if (left is SqlJoinedTable joinedLeft) Traverse(joinedLeft, output); - } output.Add(joinExpression); - if (joinExpression.Right is SqlJoinedTable joinedRight) { + var right = root.JoinExpression.Right; + if (right is SqlJoinedTable joinedRight) Traverse(joinedRight, output); - } } } -} \ No newline at end of file +} diff --git a/Orm/Xtensive.Orm/Sql/Ddl/Actions/SqlAlterIdentityInfo.cs b/Orm/Xtensive.Orm/Sql/Ddl/Actions/SqlAlterIdentityInfo.cs index 5a901ff69..a7f7db158 100644 --- a/Orm/Xtensive.Orm/Sql/Ddl/Actions/SqlAlterIdentityInfo.cs +++ b/Orm/Xtensive.Orm/Sql/Ddl/Actions/SqlAlterIdentityInfo.cs @@ -15,7 +15,8 @@ public class SqlAlterIdentityInfo : SqlAction public SqlAlterIdentityInfoOptions InfoOption { get; set; } internal override SqlAlterIdentityInfo Clone(SqlNodeCloneContext context) => - context.GetOrAdd(this, static (t, c) => new(t.Column, t.SequenceDescriptor.Clone(), t.InfoOption)); + context.GetOrAdd(this, static (t, c) => + new SqlAlterIdentityInfo(t.Column, t.SequenceDescriptor.Clone(), t.InfoOption)); internal SqlAlterIdentityInfo(TableColumn column, SequenceDescriptor sequenceDescriptor, SqlAlterIdentityInfoOptions infoOption) { diff --git a/Orm/Xtensive.Orm/Sql/Ddl/SqlAlterSequence.cs b/Orm/Xtensive.Orm/Sql/Ddl/SqlAlterSequence.cs index 3a245b591..ce3fc9cd4 100644 --- a/Orm/Xtensive.Orm/Sql/Ddl/SqlAlterSequence.cs +++ b/Orm/Xtensive.Orm/Sql/Ddl/SqlAlterSequence.cs @@ -26,7 +26,7 @@ public SqlAlterIdentityInfoOptions InfoOption internal override SqlAlterSequence Clone(SqlNodeCloneContext context) => context.GetOrAdd(this, static (t, c) => - new(t.sequence, t.sequenceDescriptor.Clone(), t.infoOption)); + new SqlAlterSequence(t.sequence, t.sequenceDescriptor.Clone(), t.infoOption)); public override void AcceptVisitor(ISqlVisitor visitor) { diff --git a/Orm/Xtensive.Orm/Sql/Dml/Collections/SqlInsertValuesCollection.cs b/Orm/Xtensive.Orm/Sql/Dml/Collections/SqlInsertValuesCollection.cs index 6881321ea..884487dff 100644 --- a/Orm/Xtensive.Orm/Sql/Dml/Collections/SqlInsertValuesCollection.cs +++ b/Orm/Xtensive.Orm/Sql/Dml/Collections/SqlInsertValuesCollection.cs @@ -65,7 +65,7 @@ public void Add(Dictionary row) else { //re-arrange values to be the same order //and also make sure all columns exist - var rowList = new List(); + var rowList = new List(columns.Count); foreach (var column in columns) { if (row.TryGetValue(column, out var value)) { rowList.Add(value); diff --git a/Orm/Xtensive.Orm/Sql/Dml/Expressions/SqlArray{T}.cs b/Orm/Xtensive.Orm/Sql/Dml/Expressions/SqlArray{T}.cs index 9cccade88..b189f10bc 100644 --- a/Orm/Xtensive.Orm/Sql/Dml/Expressions/SqlArray{T}.cs +++ b/Orm/Xtensive.Orm/Sql/Dml/Expressions/SqlArray{T}.cs @@ -27,7 +27,7 @@ public class SqlArray : SqlArray public override object[] GetValues() { - return Values.Cast().ToArray(); + return Values.Cast().ToArray(Values.Length); } public static implicit operator SqlArray(T[] value) @@ -55,7 +55,7 @@ internal SqlArray(T[] values) // do not remove, they used by reflection internal SqlArray(List values) { - Values = values.Cast().ToArray(); + Values = values.Cast().ToArray(values.Count); } internal SqlArray(object[] values) diff --git a/Orm/Xtensive.Orm/Sql/Dml/Expressions/SqlCursor.cs b/Orm/Xtensive.Orm/Sql/Dml/Expressions/SqlCursor.cs index add06bf6c..18db83464 100644 --- a/Orm/Xtensive.Orm/Sql/Dml/Expressions/SqlCursor.cs +++ b/Orm/Xtensive.Orm/Sql/Dml/Expressions/SqlCursor.cs @@ -126,14 +126,14 @@ public SqlFetch Fetch(SqlFetchOption option, SqlExpression rowCount, params ISql { if (rowCount is not null) { if (option != SqlFetchOption.Absolute && option != SqlFetchOption.Relative) - throw new ArgumentException(Strings.ExInvalidUsageOfTheRowCountArgument, "rowCount"); + throw new ArgumentException(Strings.ExInvalidUsageOfTheRowCountArgument, nameof(rowCount)); SqlValidator.EnsureIsArithmeticExpression(rowCount); } else if (option == SqlFetchOption.Absolute || option == SqlFetchOption.Relative) - throw new ArgumentException(Strings.ExInvalidUsageOfTheOrientationArgument, "option"); + throw new ArgumentException(Strings.ExInvalidUsageOfTheOrientationArgument, nameof(option)); if (target != null) for (int i = 0, l = target.Length; i < l; i++) - ArgumentNullException.ThrowIfNull(target[i], "target"); + ArgumentNullException.ThrowIfNull(target[i], $"target[{i}]"); return new SqlFetch(option, rowCount, this, target); } diff --git a/Orm/Xtensive.Orm/Sql/Dml/Expressions/SqlExpressionList.cs b/Orm/Xtensive.Orm/Sql/Dml/Expressions/SqlExpressionList.cs index c8dd2b440..d540ca3bd 100644 --- a/Orm/Xtensive.Orm/Sql/Dml/Expressions/SqlExpressionList.cs +++ b/Orm/Xtensive.Orm/Sql/Dml/Expressions/SqlExpressionList.cs @@ -4,6 +4,7 @@ // Created by: Dmitri Maximov // Created: 2009.09.01 +using System; using System.Collections; using System.Collections.Generic; using Xtensive.Core; diff --git a/Orm/Xtensive.Orm/Sql/Dml/Hints/SqlForceJoinOrderHint.cs b/Orm/Xtensive.Orm/Sql/Dml/Hints/SqlForceJoinOrderHint.cs index b09bee197..6c7b89b39 100644 --- a/Orm/Xtensive.Orm/Sql/Dml/Hints/SqlForceJoinOrderHint.cs +++ b/Orm/Xtensive.Orm/Sql/Dml/Hints/SqlForceJoinOrderHint.cs @@ -19,7 +19,7 @@ public class SqlForceJoinOrderHint : SqlHint internal override SqlForceJoinOrderHint Clone(SqlNodeCloneContext context) => context.GetOrAdd(this, static (t, c) => - new(t.Tables?.Select(table => (SqlTable) table.Clone()).ToArray())); + new SqlForceJoinOrderHint(t.Tables?.Select(table => (SqlTable) table.Clone()).ToArray())); public override void AcceptVisitor(ISqlVisitor visitor) { diff --git a/Orm/Xtensive.Orm/Sql/Dml/SqlTable.cs b/Orm/Xtensive.Orm/Sql/Dml/SqlTable.cs index ad33aa675..bcdbe2b54 100644 --- a/Orm/Xtensive.Orm/Sql/Dml/SqlTable.cs +++ b/Orm/Xtensive.Orm/Sql/Dml/SqlTable.cs @@ -83,9 +83,9 @@ public virtual SqlJoinedTable InnerJoin(SqlTable right) return InnerJoin(right, null); } - public virtual SqlJoinedTable LeftOuterJoin(SqlTable right) + public virtual SqlJoinedTable LeftJoinEx(SqlTable right) { - return LeftOuterJoin(right, null); + return LeftJoinEx(right, null); } public virtual SqlJoinedTable RightOuterJoin(SqlTable right) @@ -103,7 +103,7 @@ public virtual SqlJoinedTable InnerJoin(SqlTable right, SqlExpression expression return SqlDml.Join(SqlJoinType.InnerJoin, this, right, expression); } - public virtual SqlJoinedTable LeftOuterJoin(SqlTable right, SqlExpression expression) + public virtual SqlJoinedTable LeftJoinEx(SqlTable right, SqlExpression expression) { return SqlDml.Join(SqlJoinType.LeftOuterJoin, this, right, expression); } diff --git a/Orm/Xtensive.Orm/Sql/Info/ServerInfo.cs b/Orm/Xtensive.Orm/Sql/Info/ServerInfo.cs index 20351e173..45a9ee190 100644 --- a/Orm/Xtensive.Orm/Sql/Info/ServerInfo.cs +++ b/Orm/Xtensive.Orm/Sql/Info/ServerInfo.cs @@ -2,6 +2,7 @@ // All rights reserved. // For conditions of distribution and use, see license. +using System; using Xtensive.Core; namespace Xtensive.Sql.Info diff --git a/Orm/Xtensive.Orm/Sql/Model/Domain.cs b/Orm/Xtensive.Orm/Sql/Model/Domain.cs index 7aa9fc9c4..148b10a01 100644 --- a/Orm/Xtensive.Orm/Sql/Model/Domain.cs +++ b/Orm/Xtensive.Orm/Sql/Model/Domain.cs @@ -79,10 +79,7 @@ public Collation Collation /// Gets the constraints. /// /// The constraints. - public PairedNodeCollection DomainConstraints - { - get { return constraints; } - } + public PairedNodeCollection DomainConstraints => constraints; #region IConstrainable members diff --git a/Orm/Xtensive.Orm/Sql/Model/PairedNodeCollection.cs b/Orm/Xtensive.Orm/Sql/Model/PairedNodeCollection.cs index 2ffc503b5..9da009b3c 100644 --- a/Orm/Xtensive.Orm/Sql/Model/PairedNodeCollection.cs +++ b/Orm/Xtensive.Orm/Sql/Model/PairedNodeCollection.cs @@ -106,7 +106,7 @@ public PairedNodeCollection(TOwner owner, string property, int capacity, IEquali ArgumentException.ThrowIfNullOrEmpty(property); ArgumentNullException.ThrowIfNull(equalityComparer); - this.owner = owner; + this.owner = owner ?? throw new ArgumentNullException(nameof(owner)); this.property = property; } diff --git a/Orm/Xtensive.Orm/Sql/Model/SequenceDescriptor.cs b/Orm/Xtensive.Orm/Sql/Model/SequenceDescriptor.cs index 7c871bae7..a8479f613 100644 --- a/Orm/Xtensive.Orm/Sql/Model/SequenceDescriptor.cs +++ b/Orm/Xtensive.Orm/Sql/Model/SequenceDescriptor.cs @@ -131,16 +131,22 @@ public bool? IsCyclic } } - + #region IClonable Members + + /// + /// Creates a new object that is a copy of the current instance. + /// + /// A new object that is a copy of this instance. + public SequenceDescriptor Clone() => new SequenceDescriptor(owner, startValue, increment, maxValue, minValue, isCyclic); + /// ///Creates a new object that is a copy of the current instance. /// /// ///A new object that is a copy of this instance. /// - public SequenceDescriptor Clone() => new(owner, startValue, increment, maxValue, minValue, isCyclic); object ICloneable.Clone() => Clone(); #endregion diff --git a/Orm/Xtensive.Orm/Sql/SqlDdl.cs b/Orm/Xtensive.Orm/Sql/SqlDdl.cs index 6b54bfd16..be7b7d186 100644 --- a/Orm/Xtensive.Orm/Sql/SqlDdl.cs +++ b/Orm/Xtensive.Orm/Sql/SqlDdl.cs @@ -342,18 +342,17 @@ public static SqlAlterDomain Alter(Domain domain, SqlAction action) else if (constraint.Domain!=null && constraint.Domain!=domain) throw new ArgumentException(Strings.ExConstraintBelongsToOtherDomain, "action"); } - else if (action is SqlDropConstraint) { - DomainConstraint constraint = ((SqlDropConstraint)action).Constraint as DomainConstraint; - if (constraint==null) - throw new ArgumentException(Strings.ExInvalidConstraintType, "action"); - else if (constraint.Domain!=null && constraint.Domain!=domain) - throw new ArgumentException(Strings.ExConstraintBelongsToOtherDomain, "action"); + else if (action is SqlDropConstraint dropConstraint) { + if (dropConstraint.Constraint is not DomainConstraint domainConstraint) + throw new ArgumentException(Strings.ExInvalidConstraintType, nameof(action)); + else if (domainConstraint.Domain!=null && domainConstraint.Domain!=domain) + throw new ArgumentException(Strings.ExConstraintBelongsToOtherDomain, nameof(action)); } - else if (action is SqlSetDefault && ((SqlSetDefault)action).Column!=null || - action is SqlDropDefault && ((SqlDropDefault)action).Column!=null) - throw new ArgumentException(Strings.ExInvalidActionType, "action"); + else if (action is SqlSetDefault setDefaultAction && setDefaultAction.Column!=null || + action is SqlDropDefault dropDefaultAction && dropDefaultAction.Column!=null) + throw new ArgumentException(Strings.ExInvalidActionType, nameof(action)); else if (action is SqlAddColumn || action is SqlDropColumn || action is SqlAlterIdentityInfo) - throw new ArgumentException(Strings.ExInvalidActionType, "action"); + throw new ArgumentException(Strings.ExInvalidActionType, nameof(action)); return new SqlAlterDomain(domain, action); } @@ -441,6 +440,7 @@ public static SqlSetDefault SetDefault(SqlExpression defaulValue) public static SqlDropDefault DropDefault(TableColumn column) { + ArgumentNullException.ThrowIfNull(column); return new SqlDropDefault(column); } diff --git a/Orm/Xtensive.Orm/Sql/SqlDml.cs b/Orm/Xtensive.Orm/Sql/SqlDml.cs index 70d0ac806..2ae028466 100644 --- a/Orm/Xtensive.Orm/Sql/SqlDml.cs +++ b/Orm/Xtensive.Orm/Sql/SqlDml.cs @@ -146,8 +146,8 @@ public static SqlBinary Modulo(SqlExpression left, SqlExpression right) public static SqlArray Array(IEnumerable values) { - var valueList = values.ToList(); - if (valueList.Count==0) + var valueList = values.ToArray(); + if (valueList.Length==0) return Array(System.Array.Empty()); var itemType = valueList[0].GetType(); foreach (var t in values.Select(value => value.GetType())) { @@ -1020,7 +1020,7 @@ public static SqlFunctionCall Coalesce( expressions[0] = left; expressions[1] = right; for (int i = 0; i !t.AllSchemas)) { // extracting all the schemes we need - var schemasToExtract = tasksForCatalog.Select(t => t.Schema).ToArray(); + var schemasToExtract = tasksForCatalog.Select(static t => t.Schema).ToArray(); var catalog = BuildExtractor(connection) .ExtractSchemes(catalogName, schemasToExtract); CleanSchemas(catalog, schemasToExtract); diff --git a/Orm/Xtensive.Orm/Sql/SqlDriverFactory.cs b/Orm/Xtensive.Orm/Sql/SqlDriverFactory.cs index d79e689eb..eb0a9c52a 100644 --- a/Orm/Xtensive.Orm/Sql/SqlDriverFactory.cs +++ b/Orm/Xtensive.Orm/Sql/SqlDriverFactory.cs @@ -4,6 +4,7 @@ // Created by: Denis Krjuchkov // Created: 2009.06.23 +using System; using System.Data.Common; using System.Threading; using System.Threading.Tasks; diff --git a/Orm/Xtensive.Orm/Sql/SqlExtractionTask.cs b/Orm/Xtensive.Orm/Sql/SqlExtractionTask.cs index b5eae9383..6dddf8ef1 100644 --- a/Orm/Xtensive.Orm/Sql/SqlExtractionTask.cs +++ b/Orm/Xtensive.Orm/Sql/SqlExtractionTask.cs @@ -1,3 +1,4 @@ +using System; using Xtensive.Core; using Xtensive.Sql.Model; diff --git a/Orm/Xtensive.Orm/Sql/ValueTypeMapping/TypeMappingRegistryBuilder.cs b/Orm/Xtensive.Orm/Sql/ValueTypeMapping/TypeMappingRegistryBuilder.cs index 262e1d219..0bb6645f1 100644 --- a/Orm/Xtensive.Orm/Sql/ValueTypeMapping/TypeMappingRegistryBuilder.cs +++ b/Orm/Xtensive.Orm/Sql/ValueTypeMapping/TypeMappingRegistryBuilder.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2012 Xtensive LLC. +// Copyright (C) 2012 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Denis Krjuchkov diff --git a/Orm/Xtensive.Orm/Tuples/DifferentialTuple.cs b/Orm/Xtensive.Orm/Tuples/DifferentialTuple.cs index 98947b239..fcd775ee3 100644 --- a/Orm/Xtensive.Orm/Tuples/DifferentialTuple.cs +++ b/Orm/Xtensive.Orm/Tuples/DifferentialTuple.cs @@ -170,14 +170,19 @@ public override void SetValue(int fieldIndex, object fieldValue) #region CreateNew, Clone, Reset methods /// - public override Tuple CreateNew() + public override DifferentialTuple CreateNew() { return new DifferentialTuple(origin.CreateNew()); } /// - public override DifferentialTuple Clone() => - new(origin.Clone(), difference?.Clone(), backupedDifference?.Clone()); + public override DifferentialTuple Clone() + { + return new DifferentialTuple( + origin.Clone(), + difference==null ? null : difference.Clone(), + backupedDifference==null ? null : (DifferentialTuple) backupedDifference.Clone()); + } /// /// Resets all the changes in by re-creating it. diff --git a/Orm/Xtensive.Orm/Tuples/Packed/PackedTuple.cs b/Orm/Xtensive.Orm/Tuples/Packed/PackedTuple.cs index f20f086b4..7ae708d75 100644 --- a/Orm/Xtensive.Orm/Tuples/Packed/PackedTuple.cs +++ b/Orm/Xtensive.Orm/Tuples/Packed/PackedTuple.cs @@ -22,12 +22,12 @@ public override TupleDescriptor Descriptor get { return PackedDescriptor; } } - public override Tuple Clone() + public override PackedTuple Clone() { return new PackedTuple(this); } - public override Tuple CreateNew() + public override PackedTuple CreateNew() { return new PackedTuple(PackedDescriptor); } diff --git a/Orm/Xtensive.Orm/Tuples/Transform/Internals/MapTransformTuple.cs b/Orm/Xtensive.Orm/Tuples/Transform/Internals/MapTransformTuple.cs index 4617592b7..d22874e15 100644 --- a/Orm/Xtensive.Orm/Tuples/Transform/Internals/MapTransformTuple.cs +++ b/Orm/Xtensive.Orm/Tuples/Transform/Internals/MapTransformTuple.cs @@ -81,7 +81,7 @@ public MapTransformTuple(MapTransform transform, params Tuple[] sources) { ArgumentNullException.ThrowIfNull(sources, "tuples"); // Other checks are omitted: this transform should be fast, so delayed errors are ok - this.tuples = sources; + this.tuples = sources ?? throw new ArgumentNullException(nameof(sources)); } } } diff --git a/Orm/Xtensive.Orm/Tuples/Tuple.cs b/Orm/Xtensive.Orm/Tuples/Tuple.cs index 1bbf6e7d5..e6e1201d9 100644 --- a/Orm/Xtensive.Orm/Tuples/Tuple.cs +++ b/Orm/Xtensive.Orm/Tuples/Tuple.cs @@ -254,7 +254,7 @@ public static RegularTuple Create(params Type[] fieldTypes) public static RegularTuple Create(TupleDescriptor descriptor) => descriptor != default ? new PackedTuple(descriptor) - : throw new ArgumentNullException("descriptor"); + : throw new ArgumentNullException(nameof(descriptor)); #endregion diff --git a/Orm/Xtensive.Orm/Tuples/TupleFormatExtensions.cs b/Orm/Xtensive.Orm/Tuples/TupleFormatExtensions.cs index 89d7d6dc7..a42988858 100644 --- a/Orm/Xtensive.Orm/Tuples/TupleFormatExtensions.cs +++ b/Orm/Xtensive.Orm/Tuples/TupleFormatExtensions.cs @@ -71,7 +71,7 @@ public static string Format(this Tuple source) /// can't be parsed to a with specified . public static Tuple Parse(this TupleDescriptor descriptor, string source) { - ArgumentNullException.ThrowIfNull(descriptor); + ArgumentValidator.EnsureArgumentIsNotDefault(descriptor, nameof(descriptor)); var target = Tuple.Create(descriptor); var count = target.Count; var sources = source.RevertibleSplit(Escape, Comma).ToArray(); diff --git a/Orm/Xtensive.Orm/Tuples/TupleUpdater.cs b/Orm/Xtensive.Orm/Tuples/TupleUpdater.cs index 60eb875ad..3b2a0ddf6 100644 --- a/Orm/Xtensive.Orm/Tuples/TupleUpdater.cs +++ b/Orm/Xtensive.Orm/Tuples/TupleUpdater.cs @@ -1,4 +1,4 @@ -// Copyright (C) 2003-2010 Xtensive LLC. +// Copyright (C) 2003-2010 Xtensive LLC. // All rights reserved. // For conditions of distribution and use, see license. // Created by: Alexander Nikolaev