Compare commits
4 Commits
release/2.
...
debug-2-15
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
b812417d86 | ||
|
|
ed35069dd0 | ||
|
|
7b1a7f8bf6 | ||
|
|
49d25761a3 |
5
.github/workflows/diff.yaml
vendored
5
.github/workflows/diff.yaml
vendored
@@ -365,11 +365,6 @@ jobs:
|
||||
cmake -DCMAKE_BUILD_TYPE=RelWithDebInfo ..
|
||||
make -j$THREADS memgraph
|
||||
|
||||
- name: Refresh Jepsen Cluster
|
||||
run: |
|
||||
cd tests/jepsen
|
||||
./run.sh cluster-refresh
|
||||
|
||||
- name: Run Jepsen tests
|
||||
run: |
|
||||
cd tests/jepsen
|
||||
|
||||
300
.github/workflows/release_debian10.yaml
vendored
300
.github/workflows/release_debian10.yaml
vendored
@@ -1,7 +1,4 @@
|
||||
name: Release Debian 10
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.ref_name }}
|
||||
cancel-in-progress: true
|
||||
|
||||
on:
|
||||
workflow_dispatch:
|
||||
@@ -13,30 +10,23 @@ on:
|
||||
options:
|
||||
- Release
|
||||
- RelWithDebInfo
|
||||
push:
|
||||
branches:
|
||||
- "release/**"
|
||||
tags:
|
||||
- "v*.*.*-rc*"
|
||||
- "v*.*-rc*"
|
||||
|
||||
schedule:
|
||||
- cron: "0 22 * * *"
|
||||
|
||||
env:
|
||||
THREADS: 24
|
||||
MEMGRAPH_ENTERPRISE_LICENSE: ${{ secrets.MEMGRAPH_ENTERPRISE_LICENSE }}
|
||||
MEMGRAPH_ORGANIZATION_NAME: ${{ secrets.MEMGRAPH_ORGANIZATION_NAME }}
|
||||
BUILD_TYPE: ${{ github.event.inputs.build_type || 'Release' }}
|
||||
|
||||
jobs:
|
||||
community_build:
|
||||
name: "Community build"
|
||||
runs-on: [self-hosted, Linux, X64, Debian10]
|
||||
timeout-minutes: 60
|
||||
env:
|
||||
THREADS: 24
|
||||
MEMGRAPH_ENTERPRISE_LICENSE: ${{ secrets.MEMGRAPH_ENTERPRISE_LICENSE }}
|
||||
MEMGRAPH_ORGANIZATION_NAME: ${{ secrets.MEMGRAPH_ORGANIZATION_NAME }}
|
||||
timeout-minutes: 960
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
@@ -50,6 +40,10 @@ jobs:
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Set default build_type to Release
|
||||
INPUT_BUILD_TYPE=${{ github.event.inputs.build_type }}
|
||||
BUILD_TYPE=${INPUT_BUILD_TYPE:-"Release"}
|
||||
|
||||
# Build community binaries.
|
||||
cd build
|
||||
cmake -DCMAKE_BUILD_TYPE=$BUILD_TYPE -DMG_ENTERPRISE=OFF ..
|
||||
@@ -71,11 +65,10 @@ jobs:
|
||||
THREADS: 24
|
||||
MEMGRAPH_ENTERPRISE_LICENSE: ${{ secrets.MEMGRAPH_ENTERPRISE_LICENSE }}
|
||||
MEMGRAPH_ORGANIZATION_NAME: ${{ secrets.MEMGRAPH_ORGANIZATION_NAME }}
|
||||
timeout-minutes: 60
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
@@ -117,19 +110,22 @@ jobs:
|
||||
tar -czf code_coverage.tar.gz coverage.json html report.json summary.rmu
|
||||
|
||||
- name: Save code coverage
|
||||
uses: actions/upload-artifact@v4
|
||||
uses: actions/upload-artifact@v3
|
||||
with:
|
||||
name: "Code coverage(Coverage build)"
|
||||
name: "Code coverage"
|
||||
path: tools/github/generated/code_coverage.tar.gz
|
||||
|
||||
debug_build:
|
||||
name: "Debug build"
|
||||
runs-on: [self-hosted, Linux, X64, Debian10]
|
||||
timeout-minutes: 60
|
||||
env:
|
||||
THREADS: 24
|
||||
MEMGRAPH_ENTERPRISE_LICENSE: ${{ secrets.MEMGRAPH_ENTERPRISE_LICENSE }}
|
||||
MEMGRAPH_ORGANIZATION_NAME: ${{ secrets.MEMGRAPH_ORGANIZATION_NAME }}
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
@@ -161,6 +157,10 @@ jobs:
|
||||
run: |
|
||||
./tests/drivers/run.sh
|
||||
|
||||
- name: Run integration tests
|
||||
run: |
|
||||
tests/integration/run.sh
|
||||
|
||||
- name: Run cppcheck and clang-format
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
@@ -171,49 +171,23 @@ jobs:
|
||||
./cppcheck_and_clang_format diff
|
||||
|
||||
- name: Save cppcheck and clang-format errors
|
||||
uses: actions/upload-artifact@v4
|
||||
uses: actions/upload-artifact@v3
|
||||
with:
|
||||
name: "Code coverage(Debug build)"
|
||||
name: "Code coverage"
|
||||
path: tools/github/cppcheck_and_clang_format.txt
|
||||
|
||||
debug_integration_test:
|
||||
name: "Debug integration tests"
|
||||
runs-on: [self-hosted, Linux, X64, Debian10]
|
||||
timeout-minutes: 60
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Build debug binaries
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Build debug binaries.
|
||||
cd build
|
||||
cmake ..
|
||||
make -j$THREADS
|
||||
|
||||
- name: Run integration tests
|
||||
run: |
|
||||
tests/integration/run.sh
|
||||
|
||||
release_build:
|
||||
name: "Release build"
|
||||
runs-on: [self-hosted, Linux, X64, Debian10]
|
||||
timeout-minutes: 60
|
||||
runs-on: [self-hosted, Linux, X64, Debian10, nightcrawler]
|
||||
env:
|
||||
THREADS: 24
|
||||
MEMGRAPH_ENTERPRISE_LICENSE: ${{ secrets.MEMGRAPH_ENTERPRISE_LICENSE }}
|
||||
MEMGRAPH_ORGANIZATION_NAME: ${{ secrets.MEMGRAPH_ORGANIZATION_NAME }}
|
||||
timeout-minutes: 960
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
@@ -229,209 +203,26 @@ jobs:
|
||||
|
||||
# Build release binaries.
|
||||
cd build
|
||||
cmake -DCMAKE_BUILD_TYPE=$BUILD_TYPE ..
|
||||
cmake -DCMAKE_BUILD_TYPE=Debug ..
|
||||
make -j$THREADS
|
||||
|
||||
- name: Create enterprise DEB package
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
|
||||
cd build
|
||||
|
||||
# create mgconsole
|
||||
# we use the -B to force the build
|
||||
make -j$THREADS -B mgconsole
|
||||
|
||||
# Create enterprise DEB package.
|
||||
mkdir output && cd output
|
||||
cpack -G DEB --config ../CPackConfig.cmake
|
||||
|
||||
- name: Save enterprise DEB package
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: "Enterprise DEB package"
|
||||
path: build/output/memgraph*.deb
|
||||
|
||||
- name: Run GQL Behave tests
|
||||
run: |
|
||||
cd tests
|
||||
./setup.sh /opt/toolchain-v4/activate
|
||||
cd gql_behave
|
||||
./continuous_integration
|
||||
|
||||
- name: Save quality assurance status
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: "GQL Behave Status"
|
||||
path: |
|
||||
tests/gql_behave/gql_behave_status.csv
|
||||
tests/gql_behave/gql_behave_status.html
|
||||
|
||||
- name: Run unit tests
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
|
||||
# Run unit tests.
|
||||
cd build
|
||||
ctest -R memgraph__unit --output-on-failure
|
||||
|
||||
release_benchmark_tests:
|
||||
name: "Release Benchmark Tests"
|
||||
runs-on: [self-hosted, Linux, X64, Debian10]
|
||||
timeout-minutes: 60
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Build release binaries
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Build release binaries
|
||||
cd build
|
||||
cmake -DCMAKE_BUILD_TYPE=$BUILD_TYPE ..
|
||||
make -j$THREADS
|
||||
|
||||
- name: Run micro benchmark tests
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
|
||||
# Run micro benchmark tests.
|
||||
cd build
|
||||
# The `eval` benchmark needs a large stack limit.
|
||||
ulimit -s 262144
|
||||
ctest -R memgraph__benchmark -V
|
||||
|
||||
- name: Run macro benchmark tests
|
||||
run: |
|
||||
cd tests/macro_benchmark
|
||||
./harness QuerySuite MemgraphRunner \
|
||||
--groups aggregation 1000_create unwind_create dense_expand match \
|
||||
--no-strict
|
||||
|
||||
- name: Run parallel macro benchmark tests
|
||||
run: |
|
||||
cd tests/macro_benchmark
|
||||
./harness QueryParallelSuite MemgraphRunner \
|
||||
--groups aggregation_parallel create_parallel bfs_parallel \
|
||||
--num-database-workers 9 --num-clients-workers 30 \
|
||||
--no-strict
|
||||
|
||||
release_e2e_test:
|
||||
name: "Release End-to-end Test"
|
||||
runs-on: [self-hosted, Linux, X64, Debian10]
|
||||
timeout-minutes: 60
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Build release binaries
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Build release binaries
|
||||
cd build
|
||||
cmake -DCMAKE_BUILD_TYPE=$BUILD_TYPE ..
|
||||
make -j$THREADS
|
||||
|
||||
- name: Ensure Kafka and Pulsar are up
|
||||
run: |
|
||||
cd tests/e2e/streams/kafka
|
||||
docker-compose up -d
|
||||
cd ../pulsar
|
||||
docker-compose up -d
|
||||
|
||||
- name: Run e2e tests
|
||||
run: |
|
||||
cd tests
|
||||
./setup.sh /opt/toolchain-v4/activate
|
||||
source ve3/bin/activate_e2e
|
||||
cd e2e
|
||||
./run.sh
|
||||
|
||||
- name: Ensure Kafka and Pulsar are down
|
||||
if: always()
|
||||
run: |
|
||||
cd tests/e2e/streams/kafka
|
||||
docker-compose down
|
||||
cd ../pulsar
|
||||
docker-compose down
|
||||
|
||||
release_durability_stress_tests:
|
||||
name: "Release durability and stress tests"
|
||||
runs-on: [self-hosted, Linux, X64, Debian10]
|
||||
timeout-minutes: 60
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Build release binaries
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Build release binaries.
|
||||
cd build
|
||||
cmake -DCMAKE_BUILD_TYPE=$BUILD_TYPE ..
|
||||
make -j$THREADS
|
||||
|
||||
- name: Run stress test (plain)
|
||||
- name: Run stress test (large)
|
||||
run: |
|
||||
cd tests/stress
|
||||
./continuous_integration
|
||||
|
||||
- name: Run stress test (SSL)
|
||||
run: |
|
||||
cd tests/stress
|
||||
./continuous_integration --use-ssl
|
||||
|
||||
- name: Run durability test (plain)
|
||||
run: |
|
||||
cd tests/stress
|
||||
source ve3/bin/activate
|
||||
python3 durability --num-steps 5
|
||||
|
||||
- name: Run durability test (large)
|
||||
run: |
|
||||
cd tests/stress
|
||||
source ve3/bin/activate
|
||||
python3 durability --num-steps 20
|
||||
./continuous_integration --large-dataset
|
||||
|
||||
release_jepsen_test:
|
||||
name: "Release Jepsen Test"
|
||||
runs-on: [self-hosted, Linux, X64, Debian10, JepsenControl]
|
||||
env:
|
||||
THREADS: 24
|
||||
MEMGRAPH_ENTERPRISE_LICENSE: ${{ secrets.MEMGRAPH_ENTERPRISE_LICENSE }}
|
||||
MEMGRAPH_ORGANIZATION_NAME: ${{ secrets.MEMGRAPH_ORGANIZATION_NAME }}
|
||||
timeout-minutes: 60
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
@@ -444,23 +235,22 @@ jobs:
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Set default build_type to Release
|
||||
INPUT_BUILD_TYPE=${{ github.event.inputs.build_type }}
|
||||
BUILD_TYPE=${INPUT_BUILD_TYPE:-"Release"}
|
||||
|
||||
# Build only memgraph release binary.
|
||||
cd build
|
||||
cmake -DCMAKE_BUILD_TYPE=$BUILD_TYPE ..
|
||||
make -j$THREADS memgraph
|
||||
|
||||
- name: Refresh Jepsen Cluster
|
||||
run: |
|
||||
cd tests/jepsen
|
||||
./run.sh cluster-refresh
|
||||
|
||||
- name: Run Jepsen tests
|
||||
run: |
|
||||
cd tests/jepsen
|
||||
./run.sh test-all-individually --binary ../../build/memgraph --ignore-run-stdout-logs --ignore-run-stderr-logs
|
||||
|
||||
- name: Save Jepsen report
|
||||
uses: actions/upload-artifact@v4
|
||||
uses: actions/upload-artifact@v3
|
||||
if: ${{ always() }}
|
||||
with:
|
||||
name: "Jepsen Report"
|
||||
|
||||
209
.github/workflows/release_ubuntu2004.yaml
vendored
209
.github/workflows/release_ubuntu2004.yaml
vendored
@@ -1,7 +1,4 @@
|
||||
name: Release Ubuntu 20.04
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.ref_name }}
|
||||
cancel-in-progress: true
|
||||
|
||||
on:
|
||||
workflow_dispatch:
|
||||
@@ -13,30 +10,23 @@ on:
|
||||
options:
|
||||
- Release
|
||||
- RelWithDebInfo
|
||||
push:
|
||||
branches:
|
||||
- "release/**"
|
||||
tags:
|
||||
- "v*.*.*-rc*"
|
||||
- "v*.*-rc*"
|
||||
|
||||
schedule:
|
||||
- cron: "0 22 * * *"
|
||||
|
||||
env:
|
||||
THREADS: 24
|
||||
MEMGRAPH_ENTERPRISE_LICENSE: ${{ secrets.MEMGRAPH_ENTERPRISE_LICENSE }}
|
||||
MEMGRAPH_ORGANIZATION_NAME: ${{ secrets.MEMGRAPH_ORGANIZATION_NAME }}
|
||||
BUILD_TYPE: ${{ github.event.inputs.build_type || 'Release' }}
|
||||
|
||||
jobs:
|
||||
community_build:
|
||||
name: "Community build"
|
||||
runs-on: [self-hosted, Linux, X64, Ubuntu20.04]
|
||||
timeout-minutes: 60
|
||||
env:
|
||||
THREADS: 24
|
||||
MEMGRAPH_ENTERPRISE_LICENSE: ${{ secrets.MEMGRAPH_ENTERPRISE_LICENSE }}
|
||||
MEMGRAPH_ORGANIZATION_NAME: ${{ secrets.MEMGRAPH_ORGANIZATION_NAME }}
|
||||
timeout-minutes: 960
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
@@ -50,6 +40,10 @@ jobs:
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Set default build_type to Release
|
||||
INPUT_BUILD_TYPE=${{ github.event.inputs.build_type }}
|
||||
BUILD_TYPE=${INPUT_BUILD_TYPE:-"Release"}
|
||||
|
||||
# Build community binaries.
|
||||
cd build
|
||||
cmake -DCMAKE_BUILD_TYPE=$BUILD_TYPE -DMG_ENTERPRISE=OFF ..
|
||||
@@ -67,11 +61,14 @@ jobs:
|
||||
coverage_build:
|
||||
name: "Coverage build"
|
||||
runs-on: [self-hosted, Linux, X64, Ubuntu20.04]
|
||||
timeout-minutes: 60
|
||||
env:
|
||||
THREADS: 24
|
||||
MEMGRAPH_ENTERPRISE_LICENSE: ${{ secrets.MEMGRAPH_ENTERPRISE_LICENSE }}
|
||||
MEMGRAPH_ORGANIZATION_NAME: ${{ secrets.MEMGRAPH_ORGANIZATION_NAME }}
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
@@ -113,19 +110,22 @@ jobs:
|
||||
tar -czf code_coverage.tar.gz coverage.json html report.json summary.rmu
|
||||
|
||||
- name: Save code coverage
|
||||
uses: actions/upload-artifact@v4
|
||||
uses: actions/upload-artifact@v3
|
||||
with:
|
||||
name: "Code coverage(Coverage build)"
|
||||
name: "Code coverage"
|
||||
path: tools/github/generated/code_coverage.tar.gz
|
||||
|
||||
debug_build:
|
||||
name: "Debug build"
|
||||
runs-on: [self-hosted, Linux, X64, Ubuntu20.04]
|
||||
timeout-minutes: 60
|
||||
env:
|
||||
THREADS: 24
|
||||
MEMGRAPH_ENTERPRISE_LICENSE: ${{ secrets.MEMGRAPH_ENTERPRISE_LICENSE }}
|
||||
MEMGRAPH_ORGANIZATION_NAME: ${{ secrets.MEMGRAPH_ORGANIZATION_NAME }}
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
@@ -157,6 +157,10 @@ jobs:
|
||||
run: |
|
||||
./tests/drivers/run.sh
|
||||
|
||||
- name: Run integration tests
|
||||
run: |
|
||||
tests/integration/run.sh
|
||||
|
||||
- name: Run cppcheck and clang-format
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
@@ -167,49 +171,23 @@ jobs:
|
||||
./cppcheck_and_clang_format diff
|
||||
|
||||
- name: Save cppcheck and clang-format errors
|
||||
uses: actions/upload-artifact@v4
|
||||
uses: actions/upload-artifact@v3
|
||||
with:
|
||||
name: "Code coverage(Debug build)"
|
||||
name: "Code coverage"
|
||||
path: tools/github/cppcheck_and_clang_format.txt
|
||||
|
||||
debug_integration_test:
|
||||
name: "Debug integration tests"
|
||||
runs-on: [self-hosted, Linux, X64, Ubuntu20.04]
|
||||
timeout-minutes: 60
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Build debug binaries
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Build debug binaries.
|
||||
cd build
|
||||
cmake ..
|
||||
make -j$THREADS
|
||||
|
||||
- name: Run integration tests
|
||||
run: |
|
||||
tests/integration/run.sh
|
||||
|
||||
release_build:
|
||||
name: "Release build"
|
||||
runs-on: [self-hosted, Linux, X64, Ubuntu20.04]
|
||||
timeout-minutes: 60
|
||||
env:
|
||||
THREADS: 24
|
||||
MEMGRAPH_ENTERPRISE_LICENSE: ${{ secrets.MEMGRAPH_ENTERPRISE_LICENSE }}
|
||||
MEMGRAPH_ORGANIZATION_NAME: ${{ secrets.MEMGRAPH_ORGANIZATION_NAME }}
|
||||
timeout-minutes: 960
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
uses: actions/checkout@v3
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
@@ -223,6 +201,10 @@ jobs:
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Set default build_type to Release
|
||||
INPUT_BUILD_TYPE=${{ github.event.inputs.build_type }}
|
||||
BUILD_TYPE=${INPUT_BUILD_TYPE:-"Release"}
|
||||
|
||||
# Build release binaries.
|
||||
cd build
|
||||
cmake -DCMAKE_BUILD_TYPE=$BUILD_TYPE ..
|
||||
@@ -244,60 +226,11 @@ jobs:
|
||||
cpack -G DEB --config ../CPackConfig.cmake
|
||||
|
||||
- name: Save enterprise DEB package
|
||||
uses: actions/upload-artifact@v4
|
||||
uses: actions/upload-artifact@v3
|
||||
with:
|
||||
name: "Enterprise DEB package"
|
||||
path: build/output/memgraph*.deb
|
||||
|
||||
- name: Run GQL Behave tests
|
||||
run: |
|
||||
cd tests
|
||||
./setup.sh /opt/toolchain-v4/activate
|
||||
cd gql_behave
|
||||
./continuous_integration
|
||||
|
||||
- name: Save quality assurance status
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: "GQL Behave Status"
|
||||
path: |
|
||||
tests/gql_behave/gql_behave_status.csv
|
||||
tests/gql_behave/gql_behave_status.html
|
||||
|
||||
- name: Run unit tests
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
|
||||
# Run unit tests.
|
||||
cd build
|
||||
ctest -R memgraph__unit --output-on-failure
|
||||
|
||||
release_benchmark_tests:
|
||||
name: "Release Benchmark Tests"
|
||||
runs-on: [self-hosted, Linux, X64, Ubuntu20.04]
|
||||
timeout-minutes: 60
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Build release binaries
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Build release binaries
|
||||
cd build
|
||||
cmake -DCMAKE_BUILD_TYPE=$BUILD_TYPE ..
|
||||
make -j$THREADS
|
||||
|
||||
- name: Run micro benchmark tests
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
@@ -324,30 +257,29 @@ jobs:
|
||||
--num-database-workers 9 --num-clients-workers 30 \
|
||||
--no-strict
|
||||
|
||||
release_e2e_test:
|
||||
name: "Release End-to-end Test"
|
||||
runs-on: [self-hosted, Linux, X64, Ubuntu20.04]
|
||||
timeout-minutes: 60
|
||||
- name: Run GQL Behave tests
|
||||
run: |
|
||||
cd tests
|
||||
./setup.sh /opt/toolchain-v4/activate
|
||||
cd gql_behave
|
||||
./continuous_integration
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
- name: Save quality assurance status
|
||||
uses: actions/upload-artifact@v3
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
fetch-depth: 0
|
||||
name: "GQL Behave Status"
|
||||
path: |
|
||||
tests/gql_behave/gql_behave_status.csv
|
||||
tests/gql_behave/gql_behave_status.html
|
||||
|
||||
- name: Build release binaries
|
||||
- name: Run unit tests
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Build release binaries
|
||||
# Run unit tests.
|
||||
cd build
|
||||
cmake -DCMAKE_BUILD_TYPE=$BUILD_TYPE ..
|
||||
make -j$THREADS
|
||||
ctest -R memgraph__unit --output-on-failure
|
||||
|
||||
- name: Ensure Kafka and Pulsar are up
|
||||
run: |
|
||||
@@ -372,32 +304,6 @@ jobs:
|
||||
cd ../pulsar
|
||||
docker-compose down
|
||||
|
||||
release_durability_stress_tests:
|
||||
name: "Release durability and stress tests"
|
||||
runs-on: [self-hosted, Linux, X64, Ubuntu20.04]
|
||||
timeout-minutes: 60
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Build release binaries
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Build release binaries.
|
||||
cd build
|
||||
cmake -DCMAKE_BUILD_TYPE=$BUILD_TYPE ..
|
||||
make -j$THREADS
|
||||
|
||||
- name: Run stress test (plain)
|
||||
run: |
|
||||
cd tests/stress
|
||||
@@ -408,6 +314,11 @@ jobs:
|
||||
cd tests/stress
|
||||
./continuous_integration --use-ssl
|
||||
|
||||
- name: Run stress test (large)
|
||||
run: |
|
||||
cd tests/stress
|
||||
./continuous_integration --large-dataset
|
||||
|
||||
- name: Run durability test (plain)
|
||||
run: |
|
||||
cd tests/stress
|
||||
|
||||
68
.github/workflows/stress_test_large.yaml
vendored
68
.github/workflows/stress_test_large.yaml
vendored
@@ -1,68 +0,0 @@
|
||||
name: Stress test large
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.ref_name }}
|
||||
cancel-in-progress: true
|
||||
|
||||
on:
|
||||
workflow_dispatch:
|
||||
inputs:
|
||||
build_type:
|
||||
type: choice
|
||||
description: "Memgraph Build type. Default value is Release."
|
||||
default: 'Release'
|
||||
options:
|
||||
- Release
|
||||
- RelWithDebInfo
|
||||
push:
|
||||
tags:
|
||||
- "v*.*.*-rc*"
|
||||
- "v*.*-rc*"
|
||||
schedule:
|
||||
- cron: "0 22 * * *"
|
||||
|
||||
env:
|
||||
THREADS: 24
|
||||
MEMGRAPH_ENTERPRISE_LICENSE: ${{ secrets.MEMGRAPH_ENTERPRISE_LICENSE }}
|
||||
MEMGRAPH_ORGANIZATION_NAME: ${{ secrets.MEMGRAPH_ORGANIZATION_NAME }}
|
||||
BUILD_TYPE: ${{ github.event.inputs.build_type || 'Release' }}
|
||||
|
||||
jobs:
|
||||
stress_test_large:
|
||||
name: "Stress test large"
|
||||
timeout-minutes: 720
|
||||
strategy:
|
||||
matrix:
|
||||
os: [Debian10, Ubuntu20.04]
|
||||
extra: [BigMemory, Gen8]
|
||||
exclude:
|
||||
- os: Debian10
|
||||
extra: Gen8
|
||||
- os: Ubuntu20.04
|
||||
extra: BigMemory
|
||||
runs-on: [self-hosted, Linux, X64, "${{ matrix.os }}", "${{ matrix.extra }}"]
|
||||
|
||||
steps:
|
||||
- name: Set up repository
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
# Number of commits to fetch. `0` indicates all history for all
|
||||
# branches and tags. (default: 1)
|
||||
fetch-depth: 0
|
||||
|
||||
- name: Build release binaries
|
||||
run: |
|
||||
# Activate toolchain.
|
||||
source /opt/toolchain-v4/activate
|
||||
|
||||
# Initialize dependencies.
|
||||
./init
|
||||
|
||||
# Build release binaries.
|
||||
cd build
|
||||
cmake -DCMAKE_BUILD_TYPE=$BUILD_TYPE ..
|
||||
make -j$THREADS
|
||||
|
||||
- name: Run stress test (large)
|
||||
run: |
|
||||
cd tests/stress
|
||||
./continuous_integration --large-dataset
|
||||
@@ -1,34 +0,0 @@
|
||||
# NuRaft ADR
|
||||
|
||||
**Author**
|
||||
Marko Budiselic (github.com/gitbuda)
|
||||
|
||||
**Status**
|
||||
PROPOSED
|
||||
|
||||
**Date**
|
||||
January 10, 2024
|
||||
|
||||
**Problem**
|
||||
|
||||
In order to enhance Memgraph to have High Availability features as requested by
|
||||
customers, we want to have reliable coordinators backed by RAFT consensus algorithm. Implementing
|
||||
RAFT to be correct and performant is a very challenging task. Skillful Memgraph
|
||||
engineers already tried 3 times and failed to deliver in a reasonable timeframe
|
||||
all three times (approximately 4 person-weeks of engineering work each time).
|
||||
|
||||
**Criteria**
|
||||
|
||||
- easy integration with our C++ codebase
|
||||
- heavily tested in production environments
|
||||
- implementation of performance optimizations on top of the canonical Raft
|
||||
implementation
|
||||
|
||||
**Decision**
|
||||
|
||||
There are a few, robust C++ implementations of Raft but as a part of other
|
||||
projects or bigger libraries. **We select
|
||||
[NuRaft](https://github.com/eBay/NuRaft)** because it focuses on delivering
|
||||
Raft without bloatware, and it's used by
|
||||
[Clickhouse](https://github.com/ClickHouse/ClickHouse) (an comparable peer to
|
||||
Memgraph, a very well-established product).
|
||||
@@ -64,7 +64,7 @@ option(MG_ENTERPRISE "Build Memgraph Enterprise Edition" ON)
|
||||
# Set the current version here to override the automatic version detection. The
|
||||
# version must be specified as `X.Y.Z`. Primarily used when building new patch
|
||||
# versions.
|
||||
set(MEMGRAPH_OVERRIDE_VERSION "2.14.1")
|
||||
set(MEMGRAPH_OVERRIDE_VERSION "")
|
||||
|
||||
# Custom suffix that this version should have. The suffix can be any arbitrary
|
||||
# string. Primarily used when building a version for a specific customer.
|
||||
|
||||
@@ -36,7 +36,7 @@ ADDITIONAL USE GRANT: You may use the Licensed Work in accordance with the
|
||||
3. using the Licensed Work to create a work or solution
|
||||
which competes (or might reasonably be expected to
|
||||
compete) with the Licensed Work.
|
||||
CHANGE DATE: 2028-21-01
|
||||
CHANGE DATE: 2027-08-12
|
||||
CHANGE LICENSE: Apache License, Version 2.0
|
||||
|
||||
For information about alternative licensing arrangements, please visit: https://memgraph.com/legal.
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
// Copyright 2024 Memgraph Ltd.
|
||||
// Copyright 2022 Memgraph Ltd.
|
||||
//
|
||||
// Use of this software is governed by the Business Source License
|
||||
// included in the file licenses/BSL.txt; by using this file, you agree to be bound by the terms of the Business Source
|
||||
@@ -92,7 +92,7 @@ void RegisterLicenseSettings(LicenseChecker &license_checker, utils::Settings &s
|
||||
// NOLINTNEXTLINE(cppcoreguidelines-avoid-non-const-global-variables)
|
||||
LicenseChecker global_license_checker;
|
||||
|
||||
LicenseChecker::~LicenseChecker() { Finalize(); }
|
||||
LicenseChecker::~LicenseChecker() { scheduler_.Stop(); }
|
||||
|
||||
std::pair<std::string, std::string> LicenseChecker::ExtractLicenseInfo(const utils::Settings &settings) const {
|
||||
if (license_info_override_) {
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
// Copyright 2024 Memgraph Ltd.
|
||||
// Copyright 2022 Memgraph Ltd.
|
||||
//
|
||||
// Use of this software is governed by the Business Source License
|
||||
// included in the file licenses/BSL.txt; by using this file, you agree to be bound by the terms of the Business Source
|
||||
@@ -89,8 +89,6 @@ struct LicenseChecker {
|
||||
|
||||
utils::Synchronized<std::optional<LicenseInfo>, utils::SpinLock> &GetLicenseInfo();
|
||||
|
||||
void Finalize() { scheduler_.Stop(); }
|
||||
|
||||
private:
|
||||
std::pair<std::string, std::string> ExtractLicenseInfo(const utils::Settings &settings) const;
|
||||
void RevalidateLicense(const utils::Settings &settings);
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
// Copyright 2024 Memgraph Ltd.
|
||||
// Copyright 2023 Memgraph Ltd.
|
||||
//
|
||||
// Use of this software is governed by the Business Source License
|
||||
// included in the file licenses/BSL.txt; by using this file, you agree to be bound by the terms of the Business Source
|
||||
@@ -257,8 +257,6 @@ int main(int argc, char **argv) {
|
||||
// register all runtime settings
|
||||
memgraph::license::RegisterLicenseSettings(memgraph::license::global_license_checker,
|
||||
memgraph::utils::global_settings);
|
||||
memgraph::utils::OnScopeExit global_license_finalizer([] { memgraph::license::global_license_checker.Finalize(); });
|
||||
|
||||
memgraph::flags::run_time::Initialize();
|
||||
|
||||
memgraph::license::global_license_checker.CheckEnvLicense();
|
||||
@@ -548,7 +546,6 @@ int main(int argc, char **argv) {
|
||||
|
||||
memgraph::query::procedure::gModuleRegistry.UnloadAllModules();
|
||||
|
||||
python_gc_scheduler.Stop();
|
||||
Py_END_ALLOW_THREADS;
|
||||
// Shutdown Python
|
||||
Py_Finalize();
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
// Copyright 2024 Memgraph Ltd.
|
||||
// Copyright 2022 Memgraph Ltd.
|
||||
//
|
||||
// Use of this software is governed by the Business Source License
|
||||
// included in the file licenses/BSL.txt; by using this file, you agree to be bound by the terms of the Business Source
|
||||
@@ -114,17 +114,12 @@ class Path {
|
||||
/** Expands the path with the given vertex. */
|
||||
void Expand(const VertexAccessor &vertex) {
|
||||
DMG_ASSERT(vertices_.size() == edges_.size(), "Illegal path construction order");
|
||||
DMG_ASSERT(edges_.empty() || (!edges_.empty() && (edges_.back().To().Gid() == vertex.Gid() ||
|
||||
edges_.back().From().Gid() == vertex.Gid())),
|
||||
"Illegal path construction order");
|
||||
vertices_.emplace_back(vertex);
|
||||
}
|
||||
|
||||
/** Expands the path with the given edge. */
|
||||
void Expand(const EdgeAccessor &edge) {
|
||||
DMG_ASSERT(vertices_.size() - 1 == edges_.size(), "Illegal path construction order");
|
||||
DMG_ASSERT(vertices_.back().Gid() == edge.From().Gid() || vertices_.back().Gid() == edge.To().Gid(),
|
||||
"Illegal path construction order");
|
||||
edges_.emplace_back(edge);
|
||||
}
|
||||
|
||||
@@ -135,14 +130,6 @@ class Path {
|
||||
Expand(others...);
|
||||
}
|
||||
|
||||
void Shrink() {
|
||||
DMG_ASSERT(!vertices_.empty(), "Vertices should not be empty in the path before shrink.");
|
||||
vertices_.pop_back();
|
||||
if (!edges_.empty()) {
|
||||
edges_.pop_back();
|
||||
}
|
||||
}
|
||||
|
||||
/** Returns the number of expansions (edges) in this path. */
|
||||
auto size() const { return edges_.size(); }
|
||||
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
// Copyright 2024 Memgraph Ltd.
|
||||
// Copyright 2023 Memgraph Ltd.
|
||||
//
|
||||
// Use of this software is governed by the Business Source License
|
||||
// included in the file licenses/BSL.txt; by using this file, you agree to be bound by the terms of the Business Source
|
||||
@@ -1057,8 +1057,7 @@ class ExpandVariableCursor : public Cursor {
|
||||
if (!self_.common_.existing_node) {
|
||||
frame[self_.common_.node_symbol] = start_vertex;
|
||||
return true;
|
||||
}
|
||||
if (CheckExistingNode(start_vertex, self_.common_.node_symbol, frame)) {
|
||||
} else if (CheckExistingNode(start_vertex, self_.common_.node_symbol, frame)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@@ -1244,10 +1243,6 @@ class ExpandVariableCursor : public Cursor {
|
||||
MG_ASSERT(frame[self_.filter_lambda_.accumulated_path_symbol.value()].IsPath(),
|
||||
"Accumulated path must be path");
|
||||
Path &accumulated_path = frame[self_.filter_lambda_.accumulated_path_symbol.value()].ValuePath();
|
||||
// Shrink the accumulated path including current level if necessary
|
||||
while (accumulated_path.size() >= edges_on_frame.size()) {
|
||||
accumulated_path.Shrink();
|
||||
}
|
||||
accumulated_path.Expand(current_edge.first);
|
||||
accumulated_path.Expand(current_vertex);
|
||||
}
|
||||
@@ -1265,9 +1260,10 @@ class ExpandVariableCursor : public Cursor {
|
||||
if (self_.common_.existing_node && !CheckExistingNode(current_vertex, self_.common_.node_symbol, frame)) continue;
|
||||
|
||||
// We only yield true if we satisfy the lower bound.
|
||||
if (static_cast<int64_t>(edges_on_frame.size()) >= lower_bound_) {
|
||||
if (static_cast<int64_t>(edges_on_frame.size()) >= lower_bound_)
|
||||
return true;
|
||||
}
|
||||
else
|
||||
continue;
|
||||
}
|
||||
}
|
||||
};
|
||||
@@ -1531,8 +1527,8 @@ class SingleSourceShortestPathCursor : public query::plan::Cursor {
|
||||
: self_(self),
|
||||
input_cursor_(self_.input()->MakeCursor(mem)),
|
||||
processed_(mem),
|
||||
to_visit_next_(mem),
|
||||
to_visit_current_(mem) {
|
||||
to_visit_current_(mem),
|
||||
to_visit_next_(mem) {
|
||||
MG_ASSERT(!self_.common_.existing_node,
|
||||
"Single source shortest path algorithm "
|
||||
"should not be used when `existing_node` "
|
||||
@@ -1562,14 +1558,12 @@ class SingleSourceShortestPathCursor : public query::plan::Cursor {
|
||||
#endif
|
||||
frame[self_.filter_lambda_.inner_edge_symbol] = edge;
|
||||
frame[self_.filter_lambda_.inner_node_symbol] = vertex;
|
||||
std::optional<Path> curr_acc_path = std::nullopt;
|
||||
if (self_.filter_lambda_.accumulated_path_symbol) {
|
||||
MG_ASSERT(frame[self_.filter_lambda_.accumulated_path_symbol.value()].IsPath(),
|
||||
"Accumulated path must have Path type");
|
||||
Path &accumulated_path = frame[self_.filter_lambda_.accumulated_path_symbol.value()].ValuePath();
|
||||
accumulated_path.Expand(edge);
|
||||
accumulated_path.Expand(vertex);
|
||||
curr_acc_path = accumulated_path;
|
||||
}
|
||||
|
||||
if (self_.filter_lambda_.expression) {
|
||||
@@ -1584,33 +1578,21 @@ class SingleSourceShortestPathCursor : public query::plan::Cursor {
|
||||
throw QueryRuntimeException("Expansion condition must evaluate to boolean or null.");
|
||||
}
|
||||
}
|
||||
to_visit_next_.emplace_back(edge, vertex, std::move(curr_acc_path));
|
||||
to_visit_next_.emplace_back(edge, vertex);
|
||||
processed_.emplace(vertex, edge);
|
||||
};
|
||||
|
||||
auto restore_frame_state_after_expansion = [this, &frame]() {
|
||||
if (self_.filter_lambda_.accumulated_path_symbol) {
|
||||
frame[self_.filter_lambda_.accumulated_path_symbol.value()].ValuePath().Shrink();
|
||||
}
|
||||
};
|
||||
|
||||
// populates the to_visit_next_ structure with expansions
|
||||
// from the given vertex. skips expansions that don't satisfy
|
||||
// the "where" condition.
|
||||
auto expand_from_vertex = [this, &expand_pair, &restore_frame_state_after_expansion](const auto &vertex) {
|
||||
auto expand_from_vertex = [this, &expand_pair](const auto &vertex) {
|
||||
if (self_.common_.direction != EdgeAtom::Direction::IN) {
|
||||
auto out_edges = UnwrapEdgesResult(vertex.OutEdges(storage::View::OLD, self_.common_.edge_types)).edges;
|
||||
for (const auto &edge : out_edges) {
|
||||
expand_pair(edge, edge.To());
|
||||
restore_frame_state_after_expansion();
|
||||
}
|
||||
for (const auto &edge : out_edges) expand_pair(edge, edge.To());
|
||||
}
|
||||
if (self_.common_.direction != EdgeAtom::Direction::OUT) {
|
||||
auto in_edges = UnwrapEdgesResult(vertex.InEdges(storage::View::OLD, self_.common_.edge_types)).edges;
|
||||
for (const auto &edge : in_edges) {
|
||||
expand_pair(edge, edge.From());
|
||||
restore_frame_state_after_expansion();
|
||||
}
|
||||
for (const auto &edge : in_edges) expand_pair(edge, edge.From());
|
||||
}
|
||||
};
|
||||
|
||||
@@ -1656,14 +1638,14 @@ class SingleSourceShortestPathCursor : public query::plan::Cursor {
|
||||
}
|
||||
|
||||
// take the next expansion from the queue
|
||||
auto [curr_edge, curr_vertex, curr_acc_path] = to_visit_current_.back();
|
||||
auto expansion = to_visit_current_.back();
|
||||
to_visit_current_.pop_back();
|
||||
|
||||
// create the frame value for the edges
|
||||
auto *pull_memory = context.evaluation_context.memory;
|
||||
utils::pmr::vector<TypedValue> edge_list(pull_memory);
|
||||
edge_list.emplace_back(curr_edge);
|
||||
auto last_vertex = curr_vertex;
|
||||
edge_list.emplace_back(expansion.first);
|
||||
auto last_vertex = expansion.second;
|
||||
while (true) {
|
||||
const EdgeAccessor &last_edge = edge_list.back().ValueEdge();
|
||||
last_vertex = last_edge.From() == last_vertex ? last_edge.To() : last_edge.From();
|
||||
@@ -1675,17 +1657,11 @@ class SingleSourceShortestPathCursor : public query::plan::Cursor {
|
||||
}
|
||||
|
||||
// expand only if what we've just expanded is less then max depth
|
||||
if (static_cast<int64_t>(edge_list.size()) < upper_bound_) {
|
||||
if (self_.filter_lambda_.accumulated_path_symbol) {
|
||||
MG_ASSERT(curr_acc_path.has_value(), "Expected non-null accumulated path");
|
||||
frame[self_.filter_lambda_.accumulated_path_symbol.value()] = std::move(curr_acc_path.value());
|
||||
}
|
||||
expand_from_vertex(curr_vertex);
|
||||
}
|
||||
if (static_cast<int64_t>(edge_list.size()) < upper_bound_) expand_from_vertex(expansion.second);
|
||||
|
||||
if (static_cast<int64_t>(edge_list.size()) < lower_bound_) continue;
|
||||
|
||||
frame[self_.common_.node_symbol] = curr_vertex;
|
||||
frame[self_.common_.node_symbol] = expansion.second;
|
||||
|
||||
// place edges on the frame in the correct order
|
||||
std::reverse(edge_list.begin(), edge_list.end());
|
||||
@@ -1717,9 +1693,9 @@ class SingleSourceShortestPathCursor : public query::plan::Cursor {
|
||||
// edge because the root does not get expanded from anything.
|
||||
// contains visited vertices as well as those scheduled to be visited.
|
||||
utils::pmr::unordered_map<VertexAccessor, std::optional<EdgeAccessor>> processed_;
|
||||
// edge, vertex we have yet to visit, for current and next depth and their accumulated paths
|
||||
utils::pmr::vector<std::tuple<EdgeAccessor, VertexAccessor, std::optional<Path>>> to_visit_next_;
|
||||
utils::pmr::vector<std::tuple<EdgeAccessor, VertexAccessor, std::optional<Path>>> to_visit_current_;
|
||||
// edge/vertex pairs we have yet to visit, for current and next depth
|
||||
utils::pmr::vector<std::pair<EdgeAccessor, VertexAccessor>> to_visit_current_;
|
||||
utils::pmr::vector<std::pair<EdgeAccessor, VertexAccessor>> to_visit_next_;
|
||||
};
|
||||
|
||||
namespace {
|
||||
@@ -1792,7 +1768,6 @@ class ExpandWeightedShortestPathCursor : public query::plan::Cursor {
|
||||
|
||||
ExpressionEvaluator evaluator(&frame, context.symbol_table, context.evaluation_context, context.db_accessor,
|
||||
storage::View::OLD);
|
||||
|
||||
auto create_state = [this](const VertexAccessor &vertex, int64_t depth) {
|
||||
return std::make_pair(vertex, upper_bound_set_ ? depth : 0);
|
||||
};
|
||||
@@ -1816,7 +1791,6 @@ class ExpandWeightedShortestPathCursor : public query::plan::Cursor {
|
||||
frame[self_.weight_lambda_->inner_node_symbol] = vertex;
|
||||
TypedValue next_weight = CalculateNextWeight(self_.weight_lambda_, total_weight, evaluator);
|
||||
|
||||
std::optional<Path> curr_acc_path = std::nullopt;
|
||||
if (self_.filter_lambda_.expression) {
|
||||
frame[self_.filter_lambda_.inner_edge_symbol] = edge;
|
||||
frame[self_.filter_lambda_.inner_node_symbol] = vertex;
|
||||
@@ -1826,7 +1800,6 @@ class ExpandWeightedShortestPathCursor : public query::plan::Cursor {
|
||||
Path &accumulated_path = frame[self_.filter_lambda_.accumulated_path_symbol.value()].ValuePath();
|
||||
accumulated_path.Expand(edge);
|
||||
accumulated_path.Expand(vertex);
|
||||
curr_acc_path = accumulated_path;
|
||||
|
||||
if (self_.filter_lambda_.accumulated_weight_symbol) {
|
||||
frame[self_.filter_lambda_.accumulated_weight_symbol.value()] = next_weight;
|
||||
@@ -1842,32 +1815,24 @@ class ExpandWeightedShortestPathCursor : public query::plan::Cursor {
|
||||
if (found_it != total_cost_.end() && (found_it->second.IsNull() || (found_it->second <= next_weight).ValueBool()))
|
||||
return;
|
||||
|
||||
pq_.emplace(next_weight, depth + 1, vertex, edge, curr_acc_path);
|
||||
};
|
||||
|
||||
auto restore_frame_state_after_expansion = [this, &frame]() {
|
||||
if (self_.filter_lambda_.accumulated_path_symbol) {
|
||||
frame[self_.filter_lambda_.accumulated_path_symbol.value()].ValuePath().Shrink();
|
||||
}
|
||||
pq_.emplace(next_weight, depth + 1, vertex, edge);
|
||||
};
|
||||
|
||||
// Populates the priority queue structure with expansions
|
||||
// from the given vertex. skips expansions that don't satisfy
|
||||
// the "where" condition.
|
||||
auto expand_from_vertex = [this, &expand_pair, &restore_frame_state_after_expansion](
|
||||
const VertexAccessor &vertex, const TypedValue &weight, int64_t depth) {
|
||||
auto expand_from_vertex = [this, &expand_pair](const VertexAccessor &vertex, const TypedValue &weight,
|
||||
int64_t depth) {
|
||||
if (self_.common_.direction != EdgeAtom::Direction::IN) {
|
||||
auto out_edges = UnwrapEdgesResult(vertex.OutEdges(storage::View::OLD, self_.common_.edge_types)).edges;
|
||||
for (const auto &edge : out_edges) {
|
||||
expand_pair(edge, edge.To(), weight, depth);
|
||||
restore_frame_state_after_expansion();
|
||||
}
|
||||
}
|
||||
if (self_.common_.direction != EdgeAtom::Direction::OUT) {
|
||||
auto in_edges = UnwrapEdgesResult(vertex.InEdges(storage::View::OLD, self_.common_.edge_types)).edges;
|
||||
for (const auto &edge : in_edges) {
|
||||
expand_pair(edge, edge.From(), weight, depth);
|
||||
restore_frame_state_after_expansion();
|
||||
}
|
||||
}
|
||||
};
|
||||
@@ -1885,12 +1850,9 @@ class ExpandWeightedShortestPathCursor : public query::plan::Cursor {
|
||||
// Skip expansion for such nodes.
|
||||
if (node.IsNull()) continue;
|
||||
}
|
||||
|
||||
std::optional<Path> curr_acc_path;
|
||||
if (self_.filter_lambda_.accumulated_path_symbol) {
|
||||
// Add initial vertex of path to the accumulated path
|
||||
curr_acc_path = Path(vertex);
|
||||
frame[self_.filter_lambda_.accumulated_path_symbol.value()] = curr_acc_path.value();
|
||||
frame[self_.filter_lambda_.accumulated_path_symbol.value()] = Path(vertex);
|
||||
}
|
||||
if (self_.upper_bound_) {
|
||||
upper_bound_ = EvaluateInt(&evaluator, self_.upper_bound_, "Max depth in weighted shortest path expansion");
|
||||
@@ -1914,7 +1876,7 @@ class ExpandWeightedShortestPathCursor : public query::plan::Cursor {
|
||||
total_cost_.clear();
|
||||
yielded_vertices_.clear();
|
||||
|
||||
pq_.emplace(current_weight, 0, vertex, std::nullopt, curr_acc_path);
|
||||
pq_.emplace(current_weight, 0, vertex, std::nullopt);
|
||||
// We are adding the starting vertex to the set of yielded vertices
|
||||
// because we don't want to yield paths that end with the starting
|
||||
// vertex.
|
||||
@@ -1923,7 +1885,7 @@ class ExpandWeightedShortestPathCursor : public query::plan::Cursor {
|
||||
|
||||
while (!pq_.empty()) {
|
||||
AbortCheck(context);
|
||||
auto [current_weight, current_depth, current_vertex, current_edge, curr_acc_path] = pq_.top();
|
||||
auto [current_weight, current_depth, current_vertex, current_edge] = pq_.top();
|
||||
pq_.pop();
|
||||
|
||||
auto current_state = create_state(current_vertex, current_depth);
|
||||
@@ -1936,12 +1898,7 @@ class ExpandWeightedShortestPathCursor : public query::plan::Cursor {
|
||||
total_cost_.emplace(current_state, current_weight);
|
||||
|
||||
// Expand only if what we've just expanded is less than max depth.
|
||||
if (current_depth < upper_bound_) {
|
||||
if (self_.filter_lambda_.accumulated_path_symbol) {
|
||||
frame[self_.filter_lambda_.accumulated_path_symbol.value()] = std::move(curr_acc_path.value());
|
||||
}
|
||||
expand_from_vertex(current_vertex, current_weight, current_depth);
|
||||
}
|
||||
if (current_depth < upper_bound_) expand_from_vertex(current_vertex, current_weight, current_depth);
|
||||
|
||||
// If we yielded a path for a vertex already, make the expansion but
|
||||
// don't return the path again.
|
||||
@@ -1964,12 +1921,12 @@ class ExpandWeightedShortestPathCursor : public query::plan::Cursor {
|
||||
// Place destination node on the frame, handle existence flag.
|
||||
if (self_.common_.existing_node) {
|
||||
const auto &node = frame[self_.common_.node_symbol];
|
||||
if ((node != TypedValue(current_vertex, pull_memory)).ValueBool()) {
|
||||
if ((node != TypedValue(current_vertex, pull_memory)).ValueBool())
|
||||
continue;
|
||||
}
|
||||
// Prevent expanding other paths, because we found the
|
||||
// shortest to existing node.
|
||||
ClearQueue();
|
||||
else
|
||||
// Prevent expanding other paths, because we found the
|
||||
// shortest to existing node.
|
||||
ClearQueue();
|
||||
} else {
|
||||
frame[self_.common_.node_symbol] = current_vertex;
|
||||
}
|
||||
@@ -2022,9 +1979,8 @@ class ExpandWeightedShortestPathCursor : public query::plan::Cursor {
|
||||
// Priority queue comparator. Keep lowest weight on top of the queue.
|
||||
class PriorityQueueComparator {
|
||||
public:
|
||||
bool operator()(
|
||||
const std::tuple<TypedValue, int64_t, VertexAccessor, std::optional<EdgeAccessor>, std::optional<Path>> &lhs,
|
||||
const std::tuple<TypedValue, int64_t, VertexAccessor, std::optional<EdgeAccessor>, std::optional<Path>> &rhs) {
|
||||
bool operator()(const std::tuple<TypedValue, int64_t, VertexAccessor, std::optional<EdgeAccessor>> &lhs,
|
||||
const std::tuple<TypedValue, int64_t, VertexAccessor, std::optional<EdgeAccessor>> &rhs) {
|
||||
const auto &lhs_weight = std::get<0>(lhs);
|
||||
const auto &rhs_weight = std::get<0>(rhs);
|
||||
// Null defines minimum value for all types
|
||||
@@ -2041,9 +1997,8 @@ class ExpandWeightedShortestPathCursor : public query::plan::Cursor {
|
||||
}
|
||||
};
|
||||
|
||||
std::priority_queue<std::tuple<TypedValue, int64_t, VertexAccessor, std::optional<EdgeAccessor>, std::optional<Path>>,
|
||||
utils::pmr::vector<std::tuple<TypedValue, int64_t, VertexAccessor, std::optional<EdgeAccessor>,
|
||||
std::optional<Path>>>,
|
||||
std::priority_queue<std::tuple<TypedValue, int64_t, VertexAccessor, std::optional<EdgeAccessor>>,
|
||||
utils::pmr::vector<std::tuple<TypedValue, int64_t, VertexAccessor, std::optional<EdgeAccessor>>>,
|
||||
PriorityQueueComparator>
|
||||
pq_;
|
||||
|
||||
@@ -2069,9 +2024,6 @@ class ExpandAllShortestPathsCursor : public query::plan::Cursor {
|
||||
|
||||
ExpressionEvaluator evaluator(&frame, context.symbol_table, context.evaluation_context, context.db_accessor,
|
||||
storage::View::OLD);
|
||||
|
||||
auto *memory = context.evaluation_context.memory;
|
||||
|
||||
auto create_state = [this](const VertexAccessor &vertex, int64_t depth) {
|
||||
return std::make_pair(vertex, upper_bound_set_ ? depth : 0);
|
||||
};
|
||||
@@ -2089,7 +2041,6 @@ class ExpandAllShortestPathsCursor : public query::plan::Cursor {
|
||||
TypedValue next_weight = CalculateNextWeight(self_.weight_lambda_, total_weight, evaluator);
|
||||
|
||||
// If filter expression exists, evaluate filter
|
||||
std::optional<Path> curr_acc_path = std::nullopt;
|
||||
if (self_.filter_lambda_.expression) {
|
||||
frame[self_.filter_lambda_.inner_edge_symbol] = edge;
|
||||
frame[self_.filter_lambda_.inner_node_symbol] = next_vertex;
|
||||
@@ -2099,7 +2050,6 @@ class ExpandAllShortestPathsCursor : public query::plan::Cursor {
|
||||
Path &accumulated_path = frame[self_.filter_lambda_.accumulated_path_symbol.value()].ValuePath();
|
||||
accumulated_path.Expand(edge);
|
||||
accumulated_path.Expand(next_vertex);
|
||||
curr_acc_path = accumulated_path;
|
||||
|
||||
if (self_.filter_lambda_.accumulated_weight_symbol) {
|
||||
frame[self_.filter_lambda_.accumulated_weight_symbol.value()] = next_weight;
|
||||
@@ -2126,20 +2076,14 @@ class ExpandAllShortestPathsCursor : public query::plan::Cursor {
|
||||
}
|
||||
|
||||
DirectedEdge directed_edge = {edge, direction, next_weight};
|
||||
pq_.emplace(next_weight, depth + 1, next_vertex, directed_edge, curr_acc_path);
|
||||
};
|
||||
|
||||
auto restore_frame_state_after_expansion = [this, &frame]() {
|
||||
if (self_.filter_lambda_.accumulated_path_symbol) {
|
||||
frame[self_.filter_lambda_.accumulated_path_symbol.value()].ValuePath().Shrink();
|
||||
}
|
||||
pq_.emplace(next_weight, depth + 1, next_vertex, directed_edge);
|
||||
};
|
||||
|
||||
// Populates the priority queue structure with expansions
|
||||
// from the given vertex. skips expansions that don't satisfy
|
||||
// the "where" condition.
|
||||
auto expand_from_vertex = [this, &expand_vertex, &context, &restore_frame_state_after_expansion](
|
||||
const VertexAccessor &vertex, const TypedValue &weight, int64_t depth) {
|
||||
auto expand_from_vertex = [this, &expand_vertex, &context](const VertexAccessor &vertex, const TypedValue &weight,
|
||||
int64_t depth) {
|
||||
if (self_.common_.direction != EdgeAtom::Direction::IN) {
|
||||
auto out_edges = UnwrapEdgesResult(vertex.OutEdges(storage::View::OLD, self_.common_.edge_types)).edges;
|
||||
for (const auto &edge : out_edges) {
|
||||
@@ -2152,7 +2096,6 @@ class ExpandAllShortestPathsCursor : public query::plan::Cursor {
|
||||
}
|
||||
#endif
|
||||
expand_vertex(edge, EdgeAtom::Direction::OUT, weight, depth);
|
||||
restore_frame_state_after_expansion();
|
||||
}
|
||||
}
|
||||
if (self_.common_.direction != EdgeAtom::Direction::OUT) {
|
||||
@@ -2167,12 +2110,12 @@ class ExpandAllShortestPathsCursor : public query::plan::Cursor {
|
||||
}
|
||||
#endif
|
||||
expand_vertex(edge, EdgeAtom::Direction::IN, weight, depth);
|
||||
restore_frame_state_after_expansion();
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
std::optional<VertexAccessor> start_vertex;
|
||||
auto *memory = context.evaluation_context.memory;
|
||||
|
||||
auto create_path = [this, &frame, &memory]() {
|
||||
auto ¤t_level = traversal_stack_.back();
|
||||
@@ -2224,11 +2167,11 @@ class ExpandAllShortestPathsCursor : public query::plan::Cursor {
|
||||
return true;
|
||||
};
|
||||
|
||||
auto create_DFS_traversal_tree = [this, &context, &memory, &frame, &create_state, &expand_from_vertex]() {
|
||||
auto create_DFS_traversal_tree = [this, &context, &memory, &create_state, &expand_from_vertex]() {
|
||||
while (!pq_.empty()) {
|
||||
AbortCheck(context);
|
||||
|
||||
auto [current_weight, current_depth, current_vertex, directed_edge, acc_path] = pq_.top();
|
||||
const auto [current_weight, current_depth, current_vertex, directed_edge] = pq_.top();
|
||||
pq_.pop();
|
||||
|
||||
const auto &[current_edge, direction, weight] = directed_edge;
|
||||
@@ -2240,10 +2183,6 @@ class ExpandAllShortestPathsCursor : public query::plan::Cursor {
|
||||
} else {
|
||||
total_cost_.emplace(current_state, current_weight);
|
||||
if (current_depth < upper_bound_) {
|
||||
if (self_.filter_lambda_.accumulated_path_symbol) {
|
||||
DMG_ASSERT(acc_path.has_value(), "Path must be already filled in AllShortestPath DFS traversals");
|
||||
frame[self_.filter_lambda_.accumulated_path_symbol.value()] = std::move(acc_path.value());
|
||||
}
|
||||
expand_from_vertex(current_vertex, current_weight, current_depth);
|
||||
}
|
||||
}
|
||||
@@ -2376,8 +2315,8 @@ class ExpandAllShortestPathsCursor : public query::plan::Cursor {
|
||||
// Priority queue comparator. Keep lowest weight on top of the queue.
|
||||
class PriorityQueueComparator {
|
||||
public:
|
||||
bool operator()(const std::tuple<TypedValue, int64_t, VertexAccessor, DirectedEdge, std::optional<Path>> &lhs,
|
||||
const std::tuple<TypedValue, int64_t, VertexAccessor, DirectedEdge, std::optional<Path>> &rhs) {
|
||||
bool operator()(const std::tuple<TypedValue, int64_t, VertexAccessor, DirectedEdge> &lhs,
|
||||
const std::tuple<TypedValue, int64_t, VertexAccessor, DirectedEdge> &rhs) {
|
||||
const auto &lhs_weight = std::get<0>(lhs);
|
||||
const auto &rhs_weight = std::get<0>(rhs);
|
||||
// Null defines minimum value for all types
|
||||
@@ -2396,10 +2335,9 @@ class ExpandAllShortestPathsCursor : public query::plan::Cursor {
|
||||
|
||||
// Priority queue - core element of the algorithm.
|
||||
// Stores: {weight, depth, next vertex, edge and direction}
|
||||
std::priority_queue<
|
||||
std::tuple<TypedValue, int64_t, VertexAccessor, DirectedEdge, std::optional<Path>>,
|
||||
utils::pmr::vector<std::tuple<TypedValue, int64_t, VertexAccessor, DirectedEdge, std::optional<Path>>>,
|
||||
PriorityQueueComparator>
|
||||
std::priority_queue<std::tuple<TypedValue, int64_t, VertexAccessor, DirectedEdge>,
|
||||
utils::pmr::vector<std::tuple<TypedValue, int64_t, VertexAccessor, DirectedEdge>>,
|
||||
PriorityQueueComparator>
|
||||
pq_;
|
||||
|
||||
void ClearQueue() {
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
// Copyright 2024 Memgraph Ltd.
|
||||
// Copyright 2023 Memgraph Ltd.
|
||||
//
|
||||
// Use of this software is governed by the Business Source License
|
||||
// included in the file licenses/BSL.txt; by using this file, you agree to be bound by the terms of the Business Source
|
||||
@@ -868,10 +868,7 @@ py::Object MgpListToPyTuple(mgp_list *list, PyObject *py_graph) {
|
||||
}
|
||||
|
||||
void PyCollectGarbage() {
|
||||
// NOTE: No need to call _Py_IsFinalizing(), we ensure
|
||||
// Python GC thread is stopped before Py_Finalize() is called
|
||||
// in memgraph.cpp
|
||||
if (!Py_IsInitialized()) {
|
||||
if (!Py_IsInitialized() || _Py_IsFinalizing()) {
|
||||
// Calling EnsureGIL will crash the program if this is true.
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -37,7 +37,7 @@ $binary_dir/memgraph \
|
||||
--bolt-cert-file="" \
|
||||
--log-file=$tmpdir/logs/memgarph.log \
|
||||
--also-log-to-stderr \
|
||||
--log-level ERROR &
|
||||
--log-level TRACE &
|
||||
pid=$!
|
||||
wait_for_server 7687
|
||||
|
||||
|
||||
@@ -33,7 +33,7 @@ $binary_dir/memgraph \
|
||||
--bolt-cert-file="" \
|
||||
--log-file=$tmpdir/logs/memgarph.log \
|
||||
--also-log-to-stderr \
|
||||
--log-level ERROR &
|
||||
--log-level TRACE &
|
||||
pid=$!
|
||||
wait_for_server 7687
|
||||
|
||||
|
||||
@@ -762,16 +762,6 @@ Feature: Match
|
||||
| path |
|
||||
| <(:label1 {id: 1})-[:type2 {id: 10}]->(:label3 {id: 3})> |
|
||||
|
||||
Scenario: Test DFS variable expand using IN edges with filter by edge type1
|
||||
Given graph "graph_edges"
|
||||
When executing query:
|
||||
"""
|
||||
MATCH path=(:label3)<-[* (e, n, p | NOT(type(e)='type1' AND type(last(relationships(p))) = 'type1'))]-(:label1) RETURN path;
|
||||
"""
|
||||
Then the result should be:
|
||||
| path |
|
||||
| <(:label3 {id: 3})<-[:type2 {id: 10}]-(:label1 {id: 1})> |
|
||||
|
||||
Scenario: Test DFS variable expand with filter by edge type2
|
||||
Given graph "graph_edges"
|
||||
When executing query:
|
||||
@@ -782,16 +772,6 @@ Feature: Match
|
||||
| path |
|
||||
| <(:label1 {id: 1})-[:type1 {id: 1}]->(:label2 {id: 2})-[:type1 {id: 2}]->(:label3 {id: 3})> |
|
||||
|
||||
Scenario: Test DFS variable expand using IN edges with filter by edge type2
|
||||
Given graph "graph_edges"
|
||||
When executing query:
|
||||
"""
|
||||
MATCH path=(:label3)<-[* (e, n, p | NOT(type(e)='type2' AND type(last(relationships(p))) = 'type2'))]-(:label1) RETURN path;
|
||||
"""
|
||||
Then the result should be:
|
||||
| path |
|
||||
| <(:label3 {id: 3})<-[:type1 {id: 2}]-(:label2 {id: 2})<-[:type1 {id: 1}]-(:label1 {id: 1})> |
|
||||
|
||||
Scenario: Using path indentifier from CREATE in MERGE
|
||||
Given an empty graph
|
||||
And having executed:
|
||||
|
||||
@@ -205,7 +205,11 @@ Feature: All Shortest Path
|
||||
| 20.3 |
|
||||
|
||||
Scenario: Test match AllShortest with accumulated path filtered by order of ids
|
||||
Given graph "graph_edges"
|
||||
Given an empty graph
|
||||
And having executed:
|
||||
"""
|
||||
CREATE (:label1 {id: 1})-[:type1 {id:1}]->(:label2 {id: 2})-[:type1 {id: 2}]->(:label3 {id: 3})-[:type1 {id: 3}]->(:label4 {id: 4});
|
||||
"""
|
||||
When executing query:
|
||||
"""
|
||||
MATCH pth=(:label1)-[*ALLSHORTEST (r, n | r.id) total_weight (e,n,p | e.id > 0 and (nodes(p)[-1]).id > (nodes(p)[-2]).id)]->(:label4) RETURN pth, total_weight;
|
||||
@@ -214,16 +218,6 @@ Feature: All Shortest Path
|
||||
| pth | total_weight |
|
||||
| <(:label1{id:1})-[:type1{id:1}]->(:label2{id:2})-[:type1{id:2}]->(:label3{id:3})-[:type1{id:3}]->(:label4{id:4})> | 6 |
|
||||
|
||||
Scenario: Test match AllShortest using IN edges with accumulated path filtered by order of ids
|
||||
Given graph "graph_edges"
|
||||
When executing query:
|
||||
"""
|
||||
MATCH pth=(:label4)<-[*ALLSHORTEST (r, n | r.id) total_weight (e,n,p | e.id > 0 and (nodes(p)[-1]).id < (nodes(p)[-2]).id)]-(:label1) RETURN pth, total_weight;
|
||||
"""
|
||||
Then the result should be:
|
||||
| pth | total_weight |
|
||||
| <(:label4{id:4})<-[:type1{id:3}]-(:label3{id:3})<-[:type1{id:2}]-(:label2{id:2})<-[:type1{id:1}]-(:label1{id:1})> | 6 |
|
||||
|
||||
Scenario: Test match AllShortest with accumulated path filtered by edge type1
|
||||
Given graph "graph_edges"
|
||||
When executing query:
|
||||
|
||||
@@ -136,42 +136,6 @@ Feature: Bfs
|
||||
| pth |
|
||||
| <(:label1{id:1})-[:type1{id:1}]->(:label2{id:2})-[:type1{id:2}]->(:label3{id:3})> |
|
||||
|
||||
Scenario: Test BFS variable expand using IN edges with filter by last edge type of accumulated path
|
||||
Given graph "graph_edges"
|
||||
When executing query:
|
||||
"""
|
||||
MATCH pth=(:label3)<-[*BFS (e,n,p | type(relationships(p)[-1]) = 'type1')]-(:label1) return pth;
|
||||
"""
|
||||
Then the result should be:
|
||||
| pth |
|
||||
| <(:label3 {id: 3})<-[:type1 {id: 2}]-(:label2 {id: 2})<-[:type1 {id: 1}]-(:label1 {id: 1})> |
|
||||
|
||||
Scenario: Test BFS variable expand using IN edges with filter by number of vertices in the accumulated path
|
||||
Given graph "graph_edges"
|
||||
When executing query:
|
||||
"""
|
||||
MATCH p=(n)<-[*BFS (r, n, p | size(nodes(p)) > 0)]-(m {id:1}) return p;
|
||||
"""
|
||||
Then the result should be:
|
||||
| p |
|
||||
| <(:label2 {id: 2})<-[:type1 {id: 1}]-(:label1 {id: 1})> |
|
||||
| <(:label3 {id: 3})<-[:type2 {id: 10}]-(:label1 {id: 1})> |
|
||||
| <(:label4 {id: 4})<-[:type1 {id: 3}]-(:label3 {id: 3})<-[:type2 {id: 10}]-(:label1 {id: 1})> |
|
||||
| <(:label5 {id: 5})<-[:type3 {id: 20}]-(:label1 {id: 1})> |
|
||||
|
||||
Scenario: Test BFS variable expand using IN edges with filter by id of vertices but accumulated path is not used
|
||||
Given graph "graph_edges"
|
||||
When executing query:
|
||||
"""
|
||||
MATCH p=(n)<-[*BFS (r, n, p | r.id > 0)]-(m {id:1}) return p;
|
||||
"""
|
||||
Then the result should be:
|
||||
| p |
|
||||
| <(:label2 {id: 2})<-[:type1 {id: 1}]-(:label1 {id: 1})> |
|
||||
| <(:label3 {id: 3})<-[:type2 {id: 10}]-(:label1 {id: 1})> |
|
||||
| <(:label4 {id: 4})<-[:type1 {id: 3}]-(:label3 {id: 3})<-[:type2 {id: 10}]-(:label1 {id: 1})> |
|
||||
| <(:label5 {id: 5})<-[:type3 {id: 20}]-(:label1 {id: 1})> |
|
||||
|
||||
Scenario: Test BFS variable expand with restict filter by last edge type of accumulated path
|
||||
Given an empty graph
|
||||
And having executed:
|
||||
|
||||
@@ -170,20 +170,6 @@ Feature: Weighted Shortest Path
|
||||
| pth | total_weight |
|
||||
| <(:label1{id:1})-[:type1{id:1}]->(:label2{id:2})-[:type1{id:2}]->(:label3{id:3})-[:type1{id:3}]->(:label4{id:4})> | 6 |
|
||||
|
||||
Scenario: Test match wShortest using IN edges with accumulated path filtered by order of ids
|
||||
Given an empty graph
|
||||
And having executed:
|
||||
"""
|
||||
CREATE (:label1 {id: 1})-[:type1 {id:1}]->(:label2 {id: 2})-[:type1 {id: 2}]->(:label3 {id: 3})-[:type1 {id: 3}]->(:label4 {id: 4});
|
||||
"""
|
||||
When executing query:
|
||||
"""
|
||||
MATCH pth=(:label4)<-[*WSHORTEST (r, n | r.id) total_weight (e,n,p | e.id > 0 and (nodes(p)[-1]).id < (nodes(p)[-2]).id)]-(:label1) RETURN pth, total_weight;
|
||||
"""
|
||||
Then the result should be:
|
||||
| pth | total_weight |
|
||||
| <(:label4{id:4})<-[:type1{id:3}]-(:label3{id:3})<-[:type1{id:2}]-(:label2{id:2})<-[:type1{id:1}]-(:label1{id:1})> | 6 |
|
||||
|
||||
Scenario: Test match wShortest with accumulated path filtered by edge type1
|
||||
Given graph "graph_edges"
|
||||
When executing query:
|
||||
|
||||
@@ -1,3 +1,2 @@
|
||||
CREATE (:label1 {id: 1})-[:type1 {id:1}]->(:label2 {id: 2})-[:type1 {id: 2}]->(:label3 {id: 3})-[:type1 {id: 3}]->(:label4 {id: 4});
|
||||
MATCH (n :label1), (m :label3) CREATE (n)-[:type2 {id: 10}]->(m);
|
||||
MATCH (n :label1) CREATE (n)-[:type3 {id: 20}]->(:label5 { id: 5 });
|
||||
|
||||
@@ -24,7 +24,7 @@ PRINT_CONTEXT() {
|
||||
|
||||
HELP_EXIT() {
|
||||
echo ""
|
||||
echo "HELP: $0 help|cluster-up|cluster-refresh|cluster-cleanup|cluster-dealloc|mgbuild|test|test-all-individually [args]"
|
||||
echo "HELP: $0 help|cluster-up|cluster-cleanup|cluster-dealloc|mgbuild|test|test-all-individually [args]"
|
||||
echo ""
|
||||
echo " test args --binary MEMGRAPH_BINARY_PATH"
|
||||
echo " --ignore-run-stdout-logs Ignore lein run stdout logs."
|
||||
@@ -184,37 +184,6 @@ PROCESS_RESULTS() {
|
||||
INFO "Result processing (printing and packing) DONE."
|
||||
}
|
||||
|
||||
CLUSTER_UP() {
|
||||
PRINT_CONTEXT
|
||||
"$script_dir/jepsen/docker/bin/up" --daemon
|
||||
sleep 10
|
||||
# Ensure all SSH connections between Jepsen containers work
|
||||
for node in $(docker ps --filter name=jepsen* --filter status=running --format "{{.Names}}"); do
|
||||
if [ "$node" == "jepsen-control" ]; then
|
||||
continue
|
||||
fi
|
||||
node_hostname="${node##jepsen-}"
|
||||
docker exec jepsen-control bash -c "ssh -oStrictHostKeyChecking=no -t $node_hostname exit"
|
||||
done
|
||||
}
|
||||
|
||||
CLUSTER_DEALLOC() {
|
||||
ps=$(docker ps --filter name=jepsen* --filter status=running -q)
|
||||
if [[ ! -z ${ps} ]]; then
|
||||
echo "Killing ${ps}"
|
||||
docker rm -f ${ps}
|
||||
imgs=$(docker images "jepsen*" -q)
|
||||
if [[ ! -z ${imgs} ]]; then
|
||||
echo "Removing ${imgs}"
|
||||
docker images "jepsen*" -q | xargs docker image rmi -f
|
||||
else
|
||||
echo "No Jepsen images detected!"
|
||||
fi
|
||||
else
|
||||
echo "No Jepsen containers detected!"
|
||||
fi
|
||||
}
|
||||
|
||||
# Initialize testing context by copying source/binary files. Inside CI,
|
||||
# Memgraph is tested on a single machine cluster based on Docker containers.
|
||||
# Once these tests will be part of the official Jepsen repo, the majority of
|
||||
@@ -227,16 +196,8 @@ case $1 in
|
||||
# the current cluster is broken because it relies on the folder. That can
|
||||
# happen easiliy because the jepsen folder is git ignored.
|
||||
cluster-up)
|
||||
CLUSTER_UP
|
||||
;;
|
||||
|
||||
cluster-refresh)
|
||||
CLUSTER_DEALLOC
|
||||
CLUSTER_UP
|
||||
;;
|
||||
|
||||
cluster-dealloc)
|
||||
CLUSTER_DEALLOC
|
||||
PRINT_CONTEXT
|
||||
"$script_dir/jepsen/docker/bin/up" --daemon
|
||||
;;
|
||||
|
||||
cluster-cleanup)
|
||||
@@ -251,6 +212,23 @@ case $1 in
|
||||
done
|
||||
;;
|
||||
|
||||
cluster-dealloc)
|
||||
ps=$(docker ps --filter name=jepsen* --filter status=running -q)
|
||||
if [[ ! -z ${ps} ]]; then
|
||||
echo "Killing ${ps}"
|
||||
docker rm -f ${ps}
|
||||
imgs=$(docker images "jepsen*" -q)
|
||||
if [[ ! -z ${imgs} ]]; then
|
||||
echo "Removing ${imgs}"
|
||||
docker images "jepsen*" -q | xargs docker image rmi -f
|
||||
else
|
||||
echo "No Jepsen images detected!"
|
||||
fi
|
||||
else
|
||||
echo "No Jepsen containers detected!"
|
||||
fi
|
||||
;;
|
||||
|
||||
mgbuild)
|
||||
PRINT_CONTEXT
|
||||
echo ""
|
||||
|
||||
@@ -93,9 +93,11 @@ def start_memgraph(args: Args, memgraph_options: List[str]) -> Popen:
|
||||
"--storage-recover-on-startup=false",
|
||||
"--query-execution-timeout-sec=1200",
|
||||
"--bolt-server-name-for-init=Neo4j/",
|
||||
"--log-level=TRACE",
|
||||
"--also-log-to-stderr=true",
|
||||
] + memgraph_options
|
||||
if not args.verbose:
|
||||
cmd += ["--log-level", "WARNING"]
|
||||
# if not args.verbose:
|
||||
# cmd += ["--log-level", "WARNING"]
|
||||
if args.log_file:
|
||||
cmd += ["--log-file", args.log_file]
|
||||
if args.data_directory:
|
||||
@@ -145,10 +147,15 @@ def run_test(args: Args, test: str, options: List[str], timeout: int, mode: Data
|
||||
+ options
|
||||
)
|
||||
start = time.time()
|
||||
ret_test = subprocess.run(cmd, cwd=SCRIPT_DIR, timeout=timeout * 60)
|
||||
ret_test = subprocess.run(cmd, cwd=SCRIPT_DIR, timeout=timeout * 60, capture_output=True)
|
||||
|
||||
if ret_test.returncode != 0:
|
||||
raise Exception("Test '{}' binary returned non-zero ({})!".format(test, ret_test.returncode))
|
||||
# raise Exception("Test '{}' binary returned non-zero ({})!".format(test, ret_test.returncode))
|
||||
raise Exception(
|
||||
"Test '{}' binary returned non-zero ({}). Stdout: {}. Stderr: {}!".format(
|
||||
test, ret_test.returncode, ret_test.stdout, ret_test.stderr
|
||||
)
|
||||
)
|
||||
|
||||
runtime = time.time() - start
|
||||
print(" Done after {:.3f} seconds".format(runtime))
|
||||
|
||||
Reference in New Issue
Block a user