Skip to content
Snippets Groups Projects

Compare revisions

Changes are shown as if the source revision was being merged into the target revision. Learn more about comparing revisions.

Source

Select target project
No results found

Target

Select target project
  • parity/mirrors/polkadot-sdk
1 result
Show changes
Commits on Source (1047)
Showing
with 529 additions and 300 deletions
......@@ -8,3 +8,9 @@ rustdocflags = [
# Needed for musl builds so user doesn't have to install musl-tools.
CC_x86_64_unknown_linux_musl = { value = ".cargo/musl-gcc", force = true, relative = true }
CXX_x86_64_unknown_linux_musl = { value = ".cargo/musl-g++", force = true, relative = true }
CARGO_WORKSPACE_ROOT_DIR = { value = "", relative = true }
SQLX_OFFLINE = "true"
[net]
retry = 5
# git-fetch-with-cli = true # commented because there is a risk that a runner can be banned by github
......@@ -18,21 +18,23 @@ accept = [
"429",
]
exclude_path = ["./target"]
exclude_path = [
"./prdoc",
"./target",
]
exclude = [
# Place holders (no need to fix these):
"http://visitme/",
"https://visitme/",
# TODO <https://github.com/paritytech/polkadot-sdk/issues/134>
# TODO meta issue: <https://github.com/paritytech/polkadot-sdk/issues/134>
"https://docs.substrate.io/main-docs/build/custom-rpc/#public-rpcs",
"https://docs.substrate.io/rustdocs/latest/sp_api/macro.decl_runtime_apis.html",
"https://github.com/ipfs/js-ipfs-bitswap/blob/",
"https://github.com/paritytech/polkadot-sdk/substrate/frame/timestamp",
"https://github.com/paritytech/substrate/frame/fast-unstake",
"https://github.com/zkcrypto/bls12_381/blob/e224ad4ea1babfc582ccd751c2bf128611d10936/src/test-data/mod.rs",
"https://polkadot-try-runtime-node.parity-chains.parity.io/",
"https://polkadot.network/the-path-of-a-parachain-block/",
"https://research.web3.foundation/en/latest/polkadot/NPoS/3.%20Balancing.html",
"https://research.web3.foundation/en/latest/polkadot/Token%20Economics.html#inflation-model",
......@@ -41,16 +43,24 @@ exclude = [
"https://research.web3.foundation/en/latest/polkadot/overview/2-token-economics.html#inflation-model",
"https://research.web3.foundation/en/latest/polkadot/slashing/npos.html",
"https://rpc.polkadot.io/",
"https://try-runtime.polkadot.io/",
"https://w3f.github.io/parachain-implementers-guide/node/approval/approval-distribution.html",
"https://w3f.github.io/parachain-implementers-guide/node/index.html",
"https://w3f.github.io/parachain-implementers-guide/protocol-chain-selection.html",
"https://w3f.github.io/parachain-implementers-guide/runtime/session_info.html",
# Behind a captcha (code 403):
"https://chainlist.org/chain/*",
"https://iohk.io/en/blog/posts/2023/11/03/partner-chains-are-coming-to-cardano/",
"https://polymesh.network",
"https://www.reddit.com/r/rust/comments/3spfh1/does_collect_allocate_more_than_once_while/",
# 403 rate limited:
"https://etherscan.io/block/11090290",
"https://subscan.io/",
"https://substrate.stackexchange.com/.*",
# Exclude strings which contain templates like {} and {:?}
"%7B%7D",
"%7B:\\?}",
]
......@@ -21,7 +21,6 @@ retries = 5
# The number of threads to run tests with. Supported values are either an integer or
# the string "num-cpus". Can be overridden through the `--test-threads` option.
# test-threads = "num-cpus"
test-threads = 20
# The number of threads required for each test. This is generally used in overrides to
......@@ -124,3 +123,10 @@ serial-integration = { max-threads = 1 }
[[profile.default.overrides]]
filter = 'test(/(^ui$|_ui|ui_)/)'
test-group = 'serial-integration'
# Running eth-rpc tests sequentially
# These tests rely on a shared resource (the RPC and Node)
# and would cause race conditions due to transaction nonces if run in parallel.
[[profile.default.overrides]]
filter = 'package(pallet-revive-eth-rpc) and test(/^tests::/)'
test-group = 'serial-integration'
......@@ -6,6 +6,7 @@ exclude = [
"cumulus/zombienet/**",
"polkadot/node/malus/integrationtests/**",
"polkadot/zombienet_tests/**",
"substrate/client/transaction-pool/tests/zombienet/**",
"substrate/zombienet/**",
"target/**",
]
......@@ -14,7 +15,7 @@ exclude = [
[formatting]
reorder_arrays = true
inline_table_expand = false
array_auto_expand = false
array_auto_expand = true
array_auto_collapse = false
indent_string = " " # tab
......@@ -40,3 +41,10 @@ keys = ["workspace.dependencies"]
[rule.formatting]
reorder_keys = true
[[rule]]
include = ["**/Cargo.toml"]
keys = ["build-dependencies", "dependencies", "dev-dependencies"]
[rule.formatting]
reorder_keys = true
......@@ -26,4 +26,4 @@ project_name = "$CI_PROJECT_PATH"
type = "gcs"
[storage.gcs]
bucketName = "parity-ci-forklift"
bucketName = "parity-ci-forklift-regional"
......@@ -64,7 +64,8 @@
/substrate/primitives/merkle-mountain-range/ @acatangiu
# Contracts
/substrate/frame/contracts/ @athei @paritytech/docs-audit
/substrate/frame/contracts/ @paritytech/smart-contracts @paritytech/docs-audit
/substrate/frame/revive/ @paritytech/smart-contracts @paritytech/docs-audit
# NPoS and election
/substrate/frame/election-provider-multi-phase/ @paritytech/staking-core @paritytech/docs-audit
......
name: "build and push image"
inputs:
dockerfile:
description: "dockerfile to build"
required: true
image-name:
description: ""
required: true
outputs:
branch:
description: "Branch name for the PR"
value: ${{ steps.branch.outputs.branch }}
runs:
using: "composite"
steps:
# gcloud
# https://github.com/paritytech/ci_cd/wiki/GitHub:-Push-Docker-image-to-GCP-Registry
- name: "Set up Cloud SDK"
uses: "google-github-actions/setup-gcloud@v2"
- name: "gcloud info"
shell: bash
run: "gcloud info"
- name: "Auth in gcloud registry"
shell: bash
run: "gcloud auth configure-docker europe-docker.pkg.dev --quiet"
- name: build
shell: bash
env:
ZOMBIENET_IMAGE: "docker.io/paritytech/zombienet:v1.3.105"
run: |
export DOCKER_IMAGES_VERSION=${{ github.event.pull_request.head.sha }}
if [[ ${{ github.event_name }} == "merge_group" ]]; then export DOCKER_IMAGES_VERSION="${GITHUB_SHA::8}"; fi
docker build \
--build-arg VCS_REF="${GITHUB_SHA}" \
--build-arg BUILD_DATE="$(date -u '+%Y-%m-%dT%H:%M:%SZ')" \
--build-arg IMAGE_NAME="${{ inputs.image-name }}" \
--build-arg ZOMBIENET_IMAGE="${ZOMBIENET_IMAGE}" \
-t "${{ inputs.image-name }}:$DOCKER_IMAGES_VERSION" \
-f ${{ inputs.dockerfile }} \
.
docker push "${{ inputs.image-name }}:$DOCKER_IMAGES_VERSION"
name: 'cargo check runtimes'
description: 'Runs `cargo check` for every directory in provided root.'
inputs:
root:
description: "Root directory. Expected to contain several cargo packages inside."
required: true
runs:
using: "composite"
steps:
- name: Check
shell: bash
run: |
mkdir -p ~/.forklift
cp .forklift/config.toml ~/.forklift/config.toml
cd ${{ inputs.root }}
for directory in $(echo */); do
echo "_____Running cargo check for ${directory} ______";
cd ${directory};
pwd;
SKIP_WASM_BUILD=1 forklift cargo check --locked;
cd ..;
done
name: 'install gh'
description: 'Install the gh cli in a debian based distro and switches to the PR branch.'
name: "install gh"
description: "Install the gh cli in a debian based distro and switches to the PR branch."
inputs:
pr-number:
description: "Number of the PR"
......@@ -9,28 +9,20 @@ inputs:
required: true
outputs:
branch:
description: 'Branch name for the PR'
description: "Branch name for the PR"
value: ${{ steps.branch.outputs.branch }}
runs:
using: "composite"
steps:
- name: Instal gh cli
shell: bash
# Here it would get the script from previous step
run: |
(type -p wget >/dev/null || (apt update && apt-get install wget -y))
mkdir -p -m 755 /etc/apt/keyrings
wget -qO- https://cli.github.com/packages/githubcli-archive-keyring.gpg | tee /etc/apt/keyrings/githubcli-archive-keyring.gpg > /dev/null
chmod go+r /etc/apt/keyrings/githubcli-archive-keyring.gpg
echo "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/githubcli-archive-keyring.gpg] https://cli.github.com/packages stable main" | tee /etc/apt/sources.list.d/github-cli.list > /dev/null
apt update
apt install gh -y
git config --global --add safe.directory '*'
- run: gh pr checkout ${{ inputs.pr-number }}
shell: bash
env:
GITHUB_TOKEN: ${{ inputs.GH_TOKEN }}
- name: Export branch name
shell: bash
run: echo "branch=$(git rev-parse --abbrev-ref HEAD)" >> "$GITHUB_OUTPUT"
id: branch
- name: Set up git
shell: bash
# Here it would get the script from previous step
run: git config --global --add safe.directory '*'
- run: gh pr checkout ${{ inputs.pr-number }}
shell: bash
env:
GITHUB_TOKEN: ${{ inputs.GH_TOKEN }}
- name: Export branch name
shell: bash
run: echo "branch=$(git rev-parse --abbrev-ref HEAD)" >> "$GITHUB_OUTPUT"
id: branch
name: "stop all workflows"
description: "Action stops all workflows in a PR to save compute resources."
inputs:
app-id:
description: "App id"
required: true
app-key:
description: "App token"
required: true
runs:
using: "composite"
steps:
- name: Worfklow stopper - Generate token
uses: actions/create-github-app-token@v1
id: app-token
with:
app-id: ${{ inputs.app-id }}
private-key: ${{ inputs.app-key }}
owner: "paritytech"
repositories: "workflow-stopper"
- name: Workflow stopper - Stop all workflows
uses: octokit/request-action@v2.x
with:
route: POST /repos/paritytech/workflow-stopper/actions/workflows/stopper.yml/dispatches
ref: main
inputs: '${{ format(''{{ "github_sha": "{0}", "github_repository": "{1}", "github_ref_name": "{2}", "github_workflow_id": "{3}", "github_job_name": "{4}" }}'', github.event.pull_request.head.sha, github.repository, github.ref_name, github.run_id, github.job) }}'
env:
GITHUB_TOKEN: ${{ steps.app-token.outputs.token }}
......@@ -6,4 +6,10 @@ coverage:
project:
default:
target: 1.0
threshold: 2.0
\ No newline at end of file
threshold: 2.0
comment:
behavior: new
fixes:
- "/__w/polkadot-sdk/polkadot-sdk/::"
\ No newline at end of file
.github/command-screnshot.png

30.8 KiB

# Running commands
Command bot has been migrated, it is no longer a comment parser and now it is a GitHub action that works as a [`workflow_dispatch`](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#workflow_dispatch) event.
## How to run an action
To run an action, you need to go to the [_actions tab_](https://github.com/paritytech/polkadot-sdk/actions) and pick the one you desire to run.
The current available command actions are:
- [Command FMT](https://github.com/paritytech/polkadot-sdk/actions/workflows/command-fmt.yml)
- [Command Update UI](https://github.com/paritytech/polkadot-sdk/actions/workflows/command-update-ui.yml)
- [Command Sync](https://github.com/paritytech/polkadot-sdk/actions/workflows/command-sync.yml)
- [Command Bench](https://github.com/paritytech/polkadot-sdk/actions/workflows/command-bench.yml)
- [Command Bench All](https://github.com/paritytech/polkadot-sdk/actions/workflows/command-bench-all.yml)
- [Command Bench Overhead](https://github.com/paritytech/polkadot-sdk/actions/workflows/command-bench-overhead.yml)
You need to select the action, and click on the dropdown that says: `Run workflow`. It is located in the upper right.
If this dropdown is not visible, you may not have permission to run the action. Contact IT for help.
![command screenshot](command-screnshot.png)
Each command will have the same two required values, but it could have more.
GitHub's official documentation: [Manually running a workflow](https://docs.github.com/en/actions/using-workflows/manually-running-a-workflow)
#### Running from CLI
You can use [`gh cli`](https://cli.github.com/) to run the commands too. Refers to the [`gh workflow run`](https://cli.github.com/manual/gh_workflow_run) section from the documentation for more information.
### Number of the Pull Request
The number of the pull request. Required so the action can fetch the correct branch and comment if it fails.
## Action configurations
### FMT
For FMT you only need the PR number.
You can use the following [`gh cli`](https://cli.github.com/) inside the repo:
```bash
gh workflow run command-fmt.yml -f pr=1000
```
### Update UI
For Update UI you only need the PR number.
You can use the following [`gh cli`](https://cli.github.com/) inside the repo:
```bash
gh workflow run command-update-ui.yml -f pr=1000
```
### Bench
Runs `benchmark pallet` or `benchmark overhead` against your PR and commits back updated weights.
Posible combinations based on the `benchmark` dropdown.
- `substrate-pallet`: Pallet Benchmark for Substrate for specific pallet
- Requires `Subcommand` to be `pallet`
- Requires `Runtime` to be `dev`
- Requires field `Pallet` to have an input that applies to `^([a-z_]+)([:]{2}[a-z_]+)?$`
- Requires `Target Directory` to be `substrate`
- `polkadot-pallet`: Pallet Benchmark for Polkadot for specific pallet
- Requires `Subcommand` to be one of the following:
- `pallet`
- `xcm`
- Requires `Runtime` to be one of the following:
- `rococo`
- `westend`
- Requires field `Pallet` to have an input that applies to `^([a-z_]+)([:]{2}[a-z_]+)?$`
- Requires `Target Directory` to be `polkadot`
- `cumulus-assets`: Pallet Benchmark for Cumulus assets
- Requires `Subcommand` to be one of the following:
- `pallet`
- `xcm`
- Requires `Runtime` to be one of the following:
- `asset-hub-westend`
- `asset-hub-rococo`
- Requires field `Pallet` to have an input that applies to `^([a-z_]+)([:]{2}[a-z_]+)?$`
- Requires `Runtime Dir` to be `assets`
- Requires `Target Directory` to be `cumulus`
- `cumulus-collectives`: Pallet Benchmark for Cumulus collectives
- Requires `Subcommand` to be one of the following:
- `pallet`
- `xcm`
- Requires `Runtime` to be `collectives-westend`
- Requires field `Pallet` to have an input that applies to `^([a-z_]+)([:]{2}[a-z_]+)?$`
- Requires `Runtime Dir` to be `collectives`
- Requires `Target Directory` to be `cumulus`
- `cumulus-coretime`: Pallet Benchmark for Cumulus coretime
- Requires `Subcommand` to be one of the following:
- `pallet`
- `xcm`
- Requires `Runtime` to be one of the following:
- `coretime-rococo`
- `coretime-westend`
- Requires field `Pallet` to have an input that applies to `^([a-z_]+)([:]{2}[a-z_]+)?$`
- Requires `Runtime Dir` to be `coretime`
- Requires `Target Directory` to be `cumulus`
- `cumulus-bridge-hubs`: Pallet Benchmark for Cumulus bridge-hubs
- Requires `Subcommand` to be one of the following:
- `pallet`
- `xcm`
- Requires `Runtime` to be one of the following:
- `bridge-hub-rococo`
- `bridge-hub-westend`
- Requires field `Pallet` to have an input that applies to `^([a-z_]+)([:]{2}[a-z_]+)?$`
- Requires `Runtime Dir` to be `bridge-hub`
- Requires `Target Directory` to be `cumulus`
- `cumulus-contracts`: Pallet Benchmark for Cumulus contracts
- Requires `Subcommand` to be one of the following:
- `pallet`
- `xcm`
- Requires `Runtime` to be one `contracts-rococo`
- Requires field `Pallet` to have an input that applies to `^([a-z_]+)([:]{2}[a-z_]+)?$`
- Requires `Runtime Dir` to be `contracts`
- Requires `Target Directory` to be `cumulus`
- `cumulus-glutton`: Pallet Benchmark for Cumulus glutton
- Requires `Subcommand` to be `pallet`
- Requires `Runtime` to be one of the following:
- `glutton-westend`
- `glutton-westend-dev-1300`
- Requires field `Pallet` to have an input that applies to `^([a-z_]+)([:]{2}[a-z_]+)?$`
- Requires `Runtime Dir` to be `glutton`
- Requires `Target Directory` to be `cumulus`
- `cumulus-starters`: Pallet Benchmark for Cumulus starters
- Requires `Subcommand` to be one of the following:
- `pallet`
- `xcm`
- Requires `Runtime` to be one of the following:
- `seedling`
- `shell`
- Requires field `Pallet` to have an input that applies to `^([a-z_]+)([:]{2}[a-z_]+)?$`
- Requires `Runtime Dir` to be `starters`
- Requires `Target Directory` to be `cumulus`
- `cumulus-people`: Pallet Benchmark for Cumulus people
- Requires `Subcommand` to be one of the following:
- `pallet`
- `xcm`
- Requires `Runtime` to be one of the following:
- `people-westend`
- `people-rococo`
- Requires field `Pallet` to have an input that applies to `^([a-z_]+)([:]{2}[a-z_]+)?$`
- Requires `Runtime Dir` to be `people`
- Requires `Target Directory` to be `cumulus`
- `cumulus-testing`: Pallet Benchmark for Cumulus testing
- Requires `Subcommand` to be one of the following:
- `pallet`
- `xcm`
- Requires `Runtime` to be one of the following:
- `penpal`
- `rococo-parachain`
- Requires field `Pallet` to have an input that applies to `^([a-z_]+)([:]{2}[a-z_]+)?$`
- Requires `Runtime Dir` to be `testing`
- Requires `Target Directory` to be `cumulus`
You can use the following [`gh cli`](https://cli.github.com/) inside the repo:
```bash
gh workflow run command-bench.yml -f pr=1000 -f benchmark=polkadot-pallet -f subcommand=pallet -f runtime=rococo -f pallet=pallet_name -f target_dir=polkadot
```
### Bench-all
This is a wrapper to run `bench` for all pallets.
Posible combinations based on the `benchmark` dropdown.
- `pallet`: Benchmark for Substrate/Polkadot/Cumulus/Trappist for specific pallet
- Requires field `Pallet` to have an input that applies to `^([a-z_]+)([:]{2}[a-z_]+)?$`
- `substrate`: Pallet + Overhead + Machine Benchmark for Substrate for all pallets
- Requires `Target Directory` to be `substrate`
- `polkadot`: Pallet + Overhead Benchmark for Polkadot
- Requires `Runtime` to be one of the following:
- `rococo`
- `westend`
- Requires `Target Directory` to be `polkadot`
- `cumulus`: Pallet Benchmark for Cumulus
- Requires `Runtime` to be one of the following:
- `rococo`
- `westend`
- `asset-hub-kusama`
- `asset-hub-polkadot`
- `asset-hub-rococo`
- `asset-hub-westend`
- `bridge-hub-kusama`
- `bridge-hub-polkadot`
- `bridge-hub-rococo`
- `bridge-hub-westend`
- `collectives-polkadot`
- `collectives-westend`
- `coretime-rococo`
- `coretime-westend`
- `contracts-rococo`
- `glutton-kusama`
- `glutton-westend`
- `people-rococo`
- `people-westend`
- Requires `Target Directory` to be `cumulus`
You can use the following [`gh cli`](https://cli.github.com/) inside the repo:
```bash
gh workflow run command-bench-all.yml -f pr=1000 -f benchmark=pallet -f pallet=pallet_name -f target_dir=polkadot -f runtime=rococo
```
### Bench-overhead
Run benchmarks overhead and commit back results to PR.
Posible combinations based on the `benchmark` dropdown.
- `default`: Runs `benchmark overhead` and commits back to PR the updated `extrinsic_weights.rs` files
- Requires `Runtime` to be one of the following:
- `rococo`
- `westend`
- Requires `Target directory` to be `polkadot`
- `substrate`: Runs `benchmark overhead` and commits back to PR the updated `extrinsic_weights.rs` files
- Requires `Target directory` to be `substrate`
- `cumulus`: Runs `benchmark overhead` and commits back to PR the updated `extrinsic_weights.rs` files
- Requires `Runtime` to be one of the following:
- `asset-hub-rococo`
- `asset-hub-westend`
- Requires `Target directory` to be `cumulus`
You can use the following [`gh cli`](https://cli.github.com/) inside the repo:
```bash
gh workflow run command-bench-overheard.yml -f pr=1000 -f benchmark=substrate -f runtime=rococo -f target_dir=substrate
```
### Sync
Run sync and commit back results to PR.
Posible combinations based on the `benchmark` dropdown.
- `chain`
- Requires one of the following:
- `rococo`
- `westend`
- `sync-type`
- Requires one of the following:
- `warp`
- `full`
- `fast`
- `fast-unsafe`
You can use the following [`gh cli`](https://cli.github.com/) inside the repo:
```bash
gh workflow run command-sync.yml -f pr=1000 -f chain=rococo -f sync-type=full
```
## How to modify an action
If you want to modify an action and test it, you can do by simply pushing your changes and then selecting your branch in the `Use worflow from` option.
This will use a file from a specified branch.
IMAGE="docker.io/paritytech/ci-unified:bullseye-1.77.0-2024-04-10-v202407161507"
IMAGE="docker.io/paritytech/ci-unified:bullseye-1.84.1-2025-01-28-v202502131220"
../docs/contributor/PULL_REQUEST_TEMPLATE.md
\ No newline at end of file
......@@ -29,7 +29,7 @@ rules:
# excluding files from 'Runtime files' and 'CI files' rules
exclude:
- ^cumulus/parachains/common/src/[^/]+\.rs$
- ^substrate/frame/(?!.*(nfts/.*|uniques/.*|babe/.*|grandpa/.*|beefy|merkle-mountain-range/.*|contracts/.*|election|nomination-pools/.*|staking/.*|aura/.*))
- ^substrate/frame/(?!.*(nfts/.*|uniques/.*|babe/.*|grandpa/.*|beefy|merkle-mountain-range/.*|contracts/.*|revive/.*|election|nomination-pools/.*|staking/.*|aura/.*))
- ^\.gitlab-ci\.yml
- ^docker/.*
- ^\.github/.*
......@@ -56,7 +56,7 @@ rules:
- name: FRAME coders substrate
condition:
include:
- ^substrate/frame/(?!.*(nfts/.*|uniques/.*|babe/.*|grandpa/.*|beefy|merkle-mountain-range/.*|contracts/.*|election|nomination-pools/.*|staking/.*|aura/.*))
- ^substrate/frame/(?!.*(nfts/.*|uniques/.*|babe/.*|grandpa/.*|beefy|merkle-mountain-range/.*|contracts/.*|revive/.*|election|nomination-pools/.*|staking/.*|aura/.*))
type: "and"
reviewers:
- minApprovals: 2
......@@ -66,6 +66,17 @@ rules:
teams:
- frame-coders
# Smart Contracts
- name: Smart Contracts
type: basic
condition:
include:
- ^substrate/frame/contracts/.*
- ^substrate/frame/revive/.*
minApprovals: 2
teams:
- smart-contracts
# Protection of THIS file
- name: Review Bot
countAuthor: true
......
......@@ -9,6 +9,7 @@
#
# - `target_group`: Integer starting from 1, the group this script should execute.
# - `groups_total`: Integer starting from 1, total number of groups.
# - `disable_forklift`: Boolean, whether to disable forklift or not.
import subprocess, sys
......@@ -31,6 +32,9 @@ crates.sort()
target_group = int(sys.argv[1]) - 1
groups_total = int(sys.argv[2])
disable_forklift = bool(sys.argv[3] if len(sys.argv) > 3 else False)
print(f"Target group: {target_group}, Total groups: {groups_total}, Disable forklift: {disable_forklift}", file=sys.stderr)
if len(crates) == 0:
print("No crates detected!", file=sys.stderr)
......@@ -55,7 +59,11 @@ for i in range(0, crates_per_group + overflow_crates):
print(f"Checking {crates[crate][0]}", file=sys.stderr)
res = subprocess.run(["forklift", "cargo", "check", "--locked"], cwd = crates[crate][1])
cmd = ["cargo", "check", "--locked"]
cmd.insert(0, 'forklift') if not disable_forklift else None
res = subprocess.run(cmd, cwd = crates[crate][1])
if res.returncode != 0:
sys.exit(1)
#!/bin/bash
echo "Running script relative to `pwd`"
# Find all README.docify.md files
DOCIFY_FILES=$(find . -name "README.docify.md")
# Initialize a variable to track directories needing README regeneration
NEED_REGENERATION=""
for file in $DOCIFY_FILES; do
echo "Processing $file"
# Get the directory containing the docify file
DIR=$(dirname "$file")
# Go to the directory and run cargo build
cd "$DIR"
cargo check --features generate-readme || { echo "Readme generation for $DIR failed. Ensure the crate compiles successfully and has a `generate-readme` feature which guards markdown compilation in the crate as follows: https://docs.rs/docify/latest/docify/macro.compile_markdown.html#conventions." && exit 1; }
# Check if README.md has any uncommitted changes
git diff --exit-code README.md
if [ $? -ne 0 ]; then
echo "Error: Found uncommitted changes in $DIR/README.md"
NEED_REGENERATION="$NEED_REGENERATION $DIR"
fi
# Return to the original directory
cd - > /dev/null
done
# Check if any directories need README regeneration
if [ -n "$NEED_REGENERATION" ]; then
echo "The following directories need README regeneration:"
echo "$NEED_REGENERATION"
exit 1
fi
\ No newline at end of file
import argparse
"""
Custom help action for argparse, it prints the help message for the main parser and all subparsers.
"""
class _HelpAction(argparse._HelpAction):
def __call__(self, parser, namespace, values, option_string=None):
parser.print_help()
# retrieve subparsers from parser
subparsers_actions = [
action for action in parser._actions
if isinstance(action, argparse._SubParsersAction)]
# there will probably only be one subparser_action,
# but better save than sorry
for subparsers_action in subparsers_actions:
# get all subparsers and print help
for choice, subparser in subparsers_action.choices.items():
print("\n### Command '{}'".format(choice))
print(subparser.format_help())
parser.exit()
#!/usr/bin/env python3
import os
import sys
import json
import argparse
import _help
import importlib.util
import re
_HelpAction = _help._HelpAction
f = open('.github/workflows/runtimes-matrix.json', 'r')
runtimesMatrix = json.load(f)
runtimeNames = list(map(lambda x: x['name'], runtimesMatrix))
common_args = {
'--quiet': {"action": "store_true", "help": "Won't print start/end/failed messages in PR"},
'--clean': {"action": "store_true", "help": "Clean up the previous bot's & author's comments in PR"},
'--image': {"help": "Override docker image '--image docker.io/paritytech/ci-unified:latest'"},
}
def print_and_log(message, output_file='/tmp/cmd/command_output.log'):
print(message)
with open(output_file, 'a') as f:
f.write(message + '\n')
def setup_logging():
if not os.path.exists('/tmp/cmd'):
os.makedirs('/tmp/cmd')
open('/tmp/cmd/command_output.log', 'w')
parser = argparse.ArgumentParser(prog="/cmd ", description='A command runner for polkadot-sdk repo', add_help=False)
parser.add_argument('--help', action=_HelpAction, help='help for help if you need some help') # help for help
for arg, config in common_args.items():
parser.add_argument(arg, **config)
subparsers = parser.add_subparsers(help='a command to run', dest='command')
setup_logging()
"""
BENCH
"""
bench_example = '''**Examples**:
Runs all benchmarks
%(prog)s
Runs benchmarks for pallet_balances and pallet_multisig for all runtimes which have these pallets. **--quiet** makes it to output nothing to PR but reactions
%(prog)s --pallet pallet_balances pallet_xcm_benchmarks::generic --quiet
Runs bench for all pallets for westend runtime and fails fast on first failed benchmark
%(prog)s --runtime westend --fail-fast
Does not output anything and cleans up the previous bot's & author command triggering comments in PR
%(prog)s --runtime westend rococo --pallet pallet_balances pallet_multisig --quiet --clean
'''
parser_bench = subparsers.add_parser('bench', aliases=['bench-omni'], help='Runs benchmarks (frame omni bencher)', epilog=bench_example, formatter_class=argparse.RawDescriptionHelpFormatter)
for arg, config in common_args.items():
parser_bench.add_argument(arg, **config)
parser_bench.add_argument('--runtime', help='Runtime(s) space separated', choices=runtimeNames, nargs='*', default=runtimeNames)
parser_bench.add_argument('--pallet', help='Pallet(s) space separated', nargs='*', default=[])
parser_bench.add_argument('--fail-fast', help='Fail fast on first failed benchmark', action='store_true')
"""
FMT
"""
parser_fmt = subparsers.add_parser('fmt', help='Formats code (cargo +nightly-VERSION fmt) and configs (taplo format)')
for arg, config in common_args.items():
parser_fmt.add_argument(arg, **config)
"""
Update UI
"""
parser_ui = subparsers.add_parser('update-ui', help='Updates UI tests')
for arg, config in common_args.items():
parser_ui.add_argument(arg, **config)
"""
PRDOC
"""
# Import generate-prdoc.py dynamically
spec = importlib.util.spec_from_file_location("generate_prdoc", ".github/scripts/generate-prdoc.py")
generate_prdoc = importlib.util.module_from_spec(spec)
spec.loader.exec_module(generate_prdoc)
parser_prdoc = subparsers.add_parser('prdoc', help='Generates PR documentation')
generate_prdoc.setup_parser(parser_prdoc, pr_required=False)
def main():
global args, unknown, runtimesMatrix
args, unknown = parser.parse_known_args()
print(f'args: {args}')
if args.command == 'bench' or args.command == 'bench-omni':
runtime_pallets_map = {}
failed_benchmarks = {}
successful_benchmarks = {}
profile = "production"
print(f'Provided runtimes: {args.runtime}')
# convert to mapped dict
runtimesMatrix = list(filter(lambda x: x['name'] in args.runtime, runtimesMatrix))
runtimesMatrix = {x['name']: x for x in runtimesMatrix}
print(f'Filtered out runtimes: {runtimesMatrix}')
compile_bencher = os.system(f"cargo install --path substrate/utils/frame/omni-bencher --locked --profile {profile}")
if compile_bencher != 0:
print_and_log('❌ Failed to compile frame-omni-bencher')
sys.exit(1)
# loop over remaining runtimes to collect available pallets
for runtime in runtimesMatrix.values():
build_command = f"forklift cargo build -p {runtime['package']} --profile {profile} --features={runtime['bench_features']}"
print(f'-- building "{runtime["name"]}" with `{build_command}`')
build_status = os.system(build_command)
if build_status != 0:
print_and_log(f'❌ Failed to build {runtime["name"]}')
if args.fail_fast:
sys.exit(1)
else:
continue
print(f'-- listing pallets for benchmark for {runtime["name"]}')
wasm_file = f"target/{profile}/wbuild/{runtime['package']}/{runtime['package'].replace('-', '_')}.wasm"
list_command = f"frame-omni-bencher v1 benchmark pallet " \
f"--no-csv-header " \
f"--no-storage-info " \
f"--no-min-squares " \
f"--no-median-slopes " \
f"--all " \
f"--list " \
f"--runtime={wasm_file} " \
f"{runtime['bench_flags']}"
print(f'-- running: {list_command}')
output = os.popen(list_command).read()
raw_pallets = output.strip().split('\n')
all_pallets = set()
for pallet in raw_pallets:
if pallet:
all_pallets.add(pallet.split(',')[0].strip())
pallets = list(all_pallets)
print(f'Pallets in {runtime["name"]}: {pallets}')
runtime_pallets_map[runtime['name']] = pallets
print(f'\n')
# filter out only the specified pallets from collected runtimes/pallets
if args.pallet:
print(f'Pallets: {args.pallet}')
new_pallets_map = {}
# keep only specified pallets if they exist in the runtime
for runtime in runtime_pallets_map:
if set(args.pallet).issubset(set(runtime_pallets_map[runtime])):
new_pallets_map[runtime] = args.pallet
runtime_pallets_map = new_pallets_map
print(f'Filtered out runtimes & pallets: {runtime_pallets_map}\n')
if not runtime_pallets_map:
if args.pallet and not args.runtime:
print(f"No pallets {args.pallet} found in any runtime")
elif args.runtime and not args.pallet:
print(f"{args.runtime} runtime does not have any pallets")
elif args.runtime and args.pallet:
print(f"No pallets {args.pallet} found in {args.runtime}")
else:
print('No runtimes found')
sys.exit(1)
for runtime in runtime_pallets_map:
for pallet in runtime_pallets_map[runtime]:
config = runtimesMatrix[runtime]
header_path = os.path.abspath(config['header'])
template = None
print(f'-- config: {config}')
if runtime == 'dev':
# to support sub-modules (https://github.com/paritytech/command-bot/issues/275)
search_manifest_path = f"cargo metadata --locked --format-version 1 --no-deps | jq -r '.packages[] | select(.name == \"{pallet.replace('_', '-')}\") | .manifest_path'"
print(f'-- running: {search_manifest_path}')
manifest_path = os.popen(search_manifest_path).read()
if not manifest_path:
print(f'-- pallet {pallet} not found in dev runtime')
if args.fail_fast:
print_and_log(f'Error: {pallet} not found in dev runtime')
sys.exit(1)
package_dir = os.path.dirname(manifest_path)
print(f'-- package_dir: {package_dir}')
print(f'-- manifest_path: {manifest_path}')
output_path = os.path.join(package_dir, "src", "weights.rs")
# TODO: we can remove once all pallets in dev runtime are migrated to polkadot-sdk-frame
try:
uses_polkadot_sdk_frame = "true" in os.popen(f"cargo metadata --locked --format-version 1 --no-deps | jq -r '.packages[] | select(.name == \"{pallet.replace('_', '-')}\") | .dependencies | any(.name == \"polkadot-sdk-frame\")'").read()
print(f'uses_polkadot_sdk_frame: {uses_polkadot_sdk_frame}')
# Empty output from the previous os.popen command
except StopIteration:
print(f'Error: {pallet} not found in dev runtime')
uses_polkadot_sdk_frame = False
template = config['template']
if uses_polkadot_sdk_frame and re.match(r"frame-(:?umbrella-)?weight-template\.hbs", os.path.normpath(template).split(os.path.sep)[-1]):
template = "substrate/.maintain/frame-umbrella-weight-template.hbs"
print(f'template: {template}')
else:
default_path = f"./{config['path']}/src/weights"
xcm_path = f"./{config['path']}/src/weights/xcm"
output_path = default_path
if pallet.startswith("pallet_xcm_benchmarks"):
template = config['template']
output_path = xcm_path
print(f'-- benchmarking {pallet} in {runtime} into {output_path}')
cmd = f"frame-omni-bencher v1 benchmark pallet " \
f"--extrinsic=* " \
f"--runtime=target/{profile}/wbuild/{config['package']}/{config['package'].replace('-', '_')}.wasm " \
f"--pallet={pallet} " \
f"--header={header_path} " \
f"--output={output_path} " \
f"--wasm-execution=compiled " \
f"--steps=50 " \
f"--repeat=20 " \
f"--heap-pages=4096 " \
f"{f'--template={template} ' if template else ''}" \
f"--no-storage-info --no-min-squares --no-median-slopes " \
f"{config['bench_flags']}"
print(f'-- Running: {cmd} \n')
status = os.system(cmd)
if status != 0 and args.fail_fast:
print_and_log(f'❌ Failed to benchmark {pallet} in {runtime}')
sys.exit(1)
# Otherwise collect failed benchmarks and print them at the end
# push failed pallets to failed_benchmarks
if status != 0:
failed_benchmarks[f'{runtime}'] = failed_benchmarks.get(f'{runtime}', []) + [pallet]
else:
successful_benchmarks[f'{runtime}'] = successful_benchmarks.get(f'{runtime}', []) + [pallet]
if failed_benchmarks:
print_and_log('❌ Failed benchmarks of runtimes/pallets:')
for runtime, pallets in failed_benchmarks.items():
print_and_log(f'-- {runtime}: {pallets}')
if successful_benchmarks:
print_and_log('✅ Successful benchmarks of runtimes/pallets:')
for runtime, pallets in successful_benchmarks.items():
print_and_log(f'-- {runtime}: {pallets}')
elif args.command == 'fmt':
command = f"cargo +nightly fmt"
print(f'Formatting with `{command}`')
nightly_status = os.system(f'{command}')
taplo_status = os.system('taplo format --config .config/taplo.toml')
if (nightly_status != 0 or taplo_status != 0):
print_and_log('❌ Failed to format code')
sys.exit(1)
elif args.command == 'update-ui':
command = 'sh ./scripts/update-ui-tests.sh'
print(f'Updating ui with `{command}`')
status = os.system(f'{command}')
if status != 0:
print_and_log('❌ Failed to update ui')
sys.exit(1)
elif args.command == 'prdoc':
# Call the main function from ./github/scripts/generate-prdoc.py module
exit_code = generate_prdoc.main(args)
if exit_code != 0:
print_and_log('❌ Failed to generate prdoc')
sys.exit(exit_code)
print('🚀 Done')
if __name__ == '__main__':
main()