diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 0540e0d41007..7b41e4ea2199 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -1,25 +1,36 @@ # Contributing to The Graph Docs -Welcome to the Graph Protocol! Thanks so much for helping us improve our documentation. Any contribution to this project, when it’s approved and merged, will eventually be visible on [https://thegraph.com/docs](https://thegraph.com/docs). +Welcome to The Graph! Thanks so much for helping us improve our documentation. Any contribution to this project, when it’s approved and merged, will eventually be visible on [https://thegraph.com/docs](https://thegraph.com/docs). -Please read and follow our [Code of Conduct](https://github.com/graphprotocol/graph-node/blob/master/CODE_OF_CONDUCT.md) to keep our community approachable and respectable. +Direct contributions are much appreciated for simple things (corrections, small additions to existing content). If the change is more complex, we encourage you to start a discussion in GitHub Issues or Discord first. -## Contributor’s Guide +## Making changes -Most of our docs are written in Markdown. If you are not familiar with Markdown, learn more [here](https://docs.github.com/en/github/writing-on-github/getting-started-with-writing-and-formatting-on-github/basic-writing-and-formatting-syntax). The files that you’ll likely be updating are inside of the “pages” folder. From there select a language in order to view the Markdown files. +Most of our docs are written in [Markdown](https://www.markdownguide.org/getting-started/), or more specifically, [MDX](https://mdxjs.com/docs/what-is-mdx/). The files that you’ll likely be updating are in [the `/website/src/pages/en` directory](https://github.com/graphprotocol/docs/tree/main/website/src/pages/en). -Direct contributions are much appreciated for simple things (corrections, small additions to existing content). If the change is more complex, we encourage you to start a discussion in GitHub Issues or Discord first. +> [!NOTE] +> +> Changes should only be made to the English language version of pages, as translations are handled by [Crowdin](https://crowdin.com/). If you spot an issue with a translation, please open an issue to let us know! -Change proposals should only be made to the English language version of pages (under `/pages/en/`), as translations are handled by [Crowdin](https://crowdin.com/). If you spot an issue with a translation, please do open an issue to let us know! +Once you located the file that you want to update, click on “Edit” which will create a new forked repo. You can make your edits there, and submit a PR. Alternatively, you can manually fork the repo, create a branch in your fork and make all the edits you want before submitting a PR. You can optionally [run the application locally](https://github.com/graphprotocol/docs/blob/main/README.md) to review your changes in context. -## Making changes +## Adding new pages + +When adding a new page, you should also add it to the sidebar navigation. This is done by adding an entry to the JavaScript object exported by the `_meta.js` file found in the directory of the file you created, where the key is the filename (minus the `.mdx` extension) and the value is an empty string. The `_meta.js` files control the order of the sidebar items. To give your new page a different title in the navigation (in case the full title is too long), you should add a `sidebarTitle` property to the [frontmatter](https://mdxjs.com/guides/frontmatter/) of the page, below `title`. + +## Moving or renaming pages or directories + +If you want to make larger changes that involve moving or renaming pages or directories, you should use the `pnpm run move-pages` script in the `website` package (`cd website && pnpm run move-pages`; example usage is provided when running the script with no arguments). This will move/rename files/directories in all languages simultaneously, which is necessary to prevent build errors. -Once you located the file that you want to update, click on “Edit” which will create a new forked repo. You can make your edits there, and submit a PR. Alternatively, you can manually fork the repo, create a branch in your fork and make all the edits you want before submitting a PR. +> [!NOTE] +> +> It is technically possible to manually move/rename files in English only and then fix the build with the `pnpm run fix-pages-structure` script, but translations for the moved/renamed pages will be lost in the process. -Tag `graphprotocol/docs-reviewers` in your PR to get the reviewers’ attention. Once we review it, we’ll likely provide feedback and might ask you for improvements. Once the review process is finalized and at least 2 people approve, the PR will be merged. We aim to provide a meaningful response to all PRs and issues from external contributors within 5 business days. +Since URLs are generated from the file structure, you should also do the following _for every URL change_ in a PR that moves or renames pages: -You can optionally [run the application locally](https://github.com/graphprotocol/docs/blob/main/README.md) to review your changes. +- Update all links across docs pages, from the old URL to the new URL (e.g. `[see the Delegating page](/old/delegating/)` => `[see the Delegating page](/new/delegating/)`). +- Add a redirect from the old URL to the new URL in the `nginx.conf` file. ## Creating an issue -If you would like to report a bug, or propose a larger feature, please create an issue. Before doing so, please search existing issues for relevant keywords, in case your issue has already been raised by someone else. +If you would like to report a bug, or propose a larger feature, please create an issue. Before doing so, please search existing issues for relevant keywords, in case your issue was already raised by someone else. diff --git a/LICENSE-MIT b/LICENSE-MIT index 6ef9ca981cb7..b3b36fc37adb 100644 --- a/LICENSE-MIT +++ b/LICENSE-MIT @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2018 Graph Protocol, Inc. and contributors. +Copyright (c) 2025 The Graph Foundation and contributors. Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/README.md b/README.md index 293e73af34ee..5e54d6c60840 100644 --- a/README.md +++ b/README.md @@ -34,4 +34,4 @@ Then, run the project: pnpm dev ``` -That’s it! Go to http://localhost:3000 to see it in action. Any change you make to a file in `pages` should be refreshed automatically in your browser. +That’s it! Go to http://localhost:3000/docs to see it in action. Any change you make to a file in `website/src/pages` should be refreshed automatically in your browser. diff --git a/nginx.conf b/nginx.conf index 9e78983562e1..ef61184c6feb 100644 --- a/nginx.conf +++ b/nginx.conf @@ -59,26 +59,33 @@ http { rewrite ^/docs/([a-zA-Z][a-zA-Z])/billing/$ $scheme://$http_host/docs/$1/subgraphs/billing/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/chain-integration-overview/$ $scheme://$http_host/docs/$1/indexing/chain-integration-overview/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/arweave/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/arweave/ permanent; - rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/avoid-eth-calls/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/avoid-eth-calls/ permanent; - rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/derivedfrom/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/derivedfrom/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/avoid-eth-calls/$ $scheme://$http_host/docs/$1/subgraphs/best-practices/avoid-eth-calls/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/subgraphs/cookbook/avoid-eth-calls/$ $scheme://$http_host/docs/$1/subgraphs/best-practices/avoid-eth-calls/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/derivedfrom/$ $scheme://$http_host/docs/$1/subgraphs/best-practices/derivedfrom/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/subgraphs/cookbook/derivedfrom/$ $scheme://$http_host/docs/$1/subgraphs/best-practices/derivedfrom/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/enums/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/enums/ permanent; - rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/grafting-hotfix/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/grafting-hotfix/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/grafting-hotfix/$ $scheme://$http_host/docs/$1/subgraphs/best-practices/grafting-hotfix/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/subgraphs/cookbook/grafting-hotfix/$ $scheme://$http_host/docs/$1/subgraphs/best-practices/grafting-hotfix/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/grafting/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/grafting/ permanent; - rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/immutable-entities-bytes-as-ids/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/immutable-entities-bytes-as-ids/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/immutable-entities-bytes-as-ids/$ $scheme://$http_host/docs/$1/subgraphs/best-practices/immutable-entities-bytes-as-ids/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/subgraphs/cookbook/immutable-entities-bytes-as-ids/$ $scheme://$http_host/docs/$1/subgraphs/best-practices/immutable-entities-bytes-as-ids/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/near/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/near/ permanent; - rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/pruning/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/pruning/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/pruning/$ $scheme://$http_host/docs/$1/subgraphs/best-practices/pruning/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/subgraphs/cookbook/pruning/$ $scheme://$http_host/docs/$1/subgraphs/best-practices/pruning/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/quick-start/$ $scheme://$http_host/docs/$1/subgraphs/quick-start/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/subgraph-debug-forking/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/subgraph-debug-forking/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/subgraph-uncrashable/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/subgraph-uncrashable/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/substreams-powered-subgraphs/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/substreams-powered-subgraphs/ permanent; - rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/timeseries/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/timeseries/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/timeseries/$ $scheme://$http_host/docs/$1/subgraphs/best-practices/timeseries/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/subgraphs/cookbook/timeseries/$ $scheme://$http_host/docs/$1/subgraphs/best-practices/timeseries/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/cookbook/transfer-to-the-graph/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/transfer-to-the-graph/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/curating/$ $scheme://$http_host/docs/$1/resources/roles/curating/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/delegating/$ $scheme://$http_host/docs/$1/resources/roles/delegating/delegating/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/deploying/deploy-using-subgraph-studio/$ $scheme://$http_host/docs/$1/subgraphs/developing/deploying/using-subgraph-studio/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/deploying/deploying-a-subgraph-to-studio/$ $scheme://$http_host/docs/$1/subgraphs/developing/deploying/using-subgraph-studio/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/deploying/multiple-networks/$ $scheme://$http_host/docs/$1/subgraphs/developing/deploying/multiple-networks/ permanent; - rewrite ^/docs/([a-zA-Z][a-zA-Z])/deploying/subgraph-studio-faqs/$ $scheme://$http_host/docs/$1/subgraphs/developing/deploying/subgraph-studio-faq/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/deploying/subgraph-studio-faqs/$ $scheme://$http_host/docs/$1/resources/subgraph-studio-faq/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/subgraphs/developing/deploying/subgraph-studio-faq/$ $scheme://$http_host/docs/$1/resources/subgraph-studio-faq/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/deploying/subgraph-studio/$ $scheme://$http_host/docs/$1/subgraphs/developing/deploying/using-subgraph-studio/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/developing/assemblyscript-api/$ $scheme://$http_host/docs/$1/subgraphs/developing/creating/graph-ts/api/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/developing/creating-a-subgraph/$ $scheme://$http_host/docs/$1/subgraphs/developing/creating/starting-your-subgraph/ permanent; @@ -127,18 +134,21 @@ http { rewrite ^/docs/([a-zA-Z][a-zA-Z])/querying/querying-the-graph/$ $scheme://$http_host/docs/$1/subgraphs/querying/introduction/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/querying/querying-with-python/$ $scheme://$http_host/docs/$1/subgraphs/querying/python/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/quick-start/$ $scheme://$http_host/docs/$1/subgraphs/quick-start/ permanent; - rewrite ^/docs/([a-zA-Z][a-zA-Z])/release-notes/assemblyscript-migration-guide/$ $scheme://$http_host/docs/$1/resources/release-notes/assemblyscript-migration-guide/ permanent; - rewrite ^/docs/([a-zA-Z][a-zA-Z])/release-notes/graphql-validations-migration-guide/$ $scheme://$http_host/docs/$1/resources/release-notes/graphql-validations-migration-guide/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/release-notes/assemblyscript-migration-guide/$ $scheme://$http_host/docs/$1/resources/migration-guides/assemblyscript-migration-guide/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/resources/release-notes/assemblyscript-migration-guide/$ $scheme://$http_host/docs/$1/resources/migration-guides/assemblyscript-migration-guide/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/release-notes/graphql-validations-migration-guide/$ $scheme://$http_host/docs/$1/resources/migration-guides/graphql-validations-migration-guide/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/resources/release-notes/graphql-validations-migration-guide/$ $scheme://$http_host/docs/$1/resources/migration-guides/graphql-validations-migration-guide/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/sps/triggers-example/$ $scheme://$http_host/docs/$1/sps/tutorial/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/studio/billing/$ $scheme://$http_host/docs/$1/subgraphs/billing/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/studio/deploy-subgraph-studio/$ $scheme://$http_host/docs/$1/subgraphs/developing/deploying/using-subgraph-studio/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/studio/managing-api-keys/$ $scheme://$http_host/docs/$1/subgraphs/querying/managing-api-keys/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/studio/multisig/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/multisig/ permanent; - rewrite ^/docs/([a-zA-Z][a-zA-Z])/studio/studio-faq/$ $scheme://$http_host/docs/$1/subgraphs/developing/deploying/subgraph-studio-faq/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/studio/studio-faq/$ $scheme://$http_host/docs/$1/resources/subgraph-studio-faq/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/studio/subgraph-studio/$ $scheme://$http_host/docs/$1/subgraphs/developing/deploying/using-subgraph-studio/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/studio/transferring-subgraph-ownership/$ $scheme://$http_host/docs/$1/subgraphs/developing/managing/transferring-a-subgraph/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/subgraphs/$ $scheme://$http_host/docs/$1/subgraphs/developing/subgraphs/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/substreams/$ $scheme://$http_host/docs/$1/substreams/introduction/ permanent; + rewrite ^/docs/([a-zA-Z][a-zA-Z])/substreams/developing/sinks/sinks/$ $scheme://$http_host/docs/$1/substreams/developing/sinks/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/sunrise/$ $scheme://$http_host/docs/$1/archived/sunrise/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/supported-network-requirements/$ $scheme://$http_host/docs/$1/indexing/supported-network-requirements/ permanent; rewrite ^/docs/([a-zA-Z][a-zA-Z])/supported-networks/arweave/$ $scheme://$http_host/docs/$1/subgraphs/cookbook/arweave/ permanent; diff --git a/website/route-lockfile.txt b/website/route-lockfile.txt index 8ad8d25f9ae9..d0b0d9279cb5 100644 --- a/website/route-lockfile.txt +++ b/website/route-lockfile.txt @@ -17,32 +17,32 @@ /ar/indexing/tooling/graphcast/ /ar/resources/benefits/ /ar/resources/glossary/ -/ar/resources/release-notes/assemblyscript-migration-guide/ -/ar/resources/release-notes/graphql-validations-migration-guide/ +/ar/resources/migration-guides/assemblyscript-migration-guide/ +/ar/resources/migration-guides/graphql-validations-migration-guide/ /ar/resources/roles/curating/ /ar/resources/roles/delegating/delegating/ /ar/resources/roles/delegating/undelegating/ +/ar/resources/subgraph-studio-faq/ /ar/resources/tokenomics/ /ar/sps/introduction/ /ar/sps/sps-faq/ /ar/sps/triggers/ /ar/sps/tutorial/ +/ar/subgraphs/best-practices/avoid-eth-calls/ +/ar/subgraphs/best-practices/derivedfrom/ +/ar/subgraphs/best-practices/grafting-hotfix/ +/ar/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/ar/subgraphs/best-practices/pruning/ +/ar/subgraphs/best-practices/timeseries/ /ar/subgraphs/billing/ /ar/subgraphs/cookbook/arweave/ -/ar/subgraphs/cookbook/avoid-eth-calls/ -/ar/subgraphs/cookbook/cosmos/ -/ar/subgraphs/cookbook/derivedfrom/ /ar/subgraphs/cookbook/enums/ -/ar/subgraphs/cookbook/grafting-hotfix/ /ar/subgraphs/cookbook/grafting/ -/ar/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /ar/subgraphs/cookbook/near/ /ar/subgraphs/cookbook/polymarket/ -/ar/subgraphs/cookbook/pruning/ /ar/subgraphs/cookbook/secure-api-keys-nextjs/ /ar/subgraphs/cookbook/subgraph-debug-forking/ /ar/subgraphs/cookbook/subgraph-uncrashable/ -/ar/subgraphs/cookbook/timeseries/ /ar/subgraphs/cookbook/transfer-to-the-graph/ /ar/subgraphs/developing/creating/advanced/ /ar/subgraphs/developing/creating/assemblyscript-mappings/ @@ -56,7 +56,6 @@ /ar/subgraphs/developing/creating/subgraph-manifest/ /ar/subgraphs/developing/creating/unit-testing-framework/ /ar/subgraphs/developing/deploying/multiple-networks/ -/ar/subgraphs/developing/deploying/subgraph-studio-faq/ /ar/subgraphs/developing/deploying/using-subgraph-studio/ /ar/subgraphs/developing/developer-faq/ /ar/subgraphs/developing/introduction/ @@ -78,7 +77,7 @@ /ar/subgraphs/querying/subgraph-id-vs-deployment-id/ /ar/subgraphs/quick-start/ /ar/substreams/developing/dev-container/ -/ar/substreams/developing/sinks/sinks/ +/ar/substreams/developing/sinks/ /ar/substreams/developing/solana/account-changes/ /ar/substreams/developing/solana/transactions/ /ar/substreams/introduction/ @@ -103,32 +102,32 @@ /cs/indexing/tooling/graphcast/ /cs/resources/benefits/ /cs/resources/glossary/ -/cs/resources/release-notes/assemblyscript-migration-guide/ -/cs/resources/release-notes/graphql-validations-migration-guide/ +/cs/resources/migration-guides/assemblyscript-migration-guide/ +/cs/resources/migration-guides/graphql-validations-migration-guide/ /cs/resources/roles/curating/ /cs/resources/roles/delegating/delegating/ /cs/resources/roles/delegating/undelegating/ +/cs/resources/subgraph-studio-faq/ /cs/resources/tokenomics/ /cs/sps/introduction/ /cs/sps/sps-faq/ /cs/sps/triggers/ /cs/sps/tutorial/ +/cs/subgraphs/best-practices/avoid-eth-calls/ +/cs/subgraphs/best-practices/derivedfrom/ +/cs/subgraphs/best-practices/grafting-hotfix/ +/cs/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/cs/subgraphs/best-practices/pruning/ +/cs/subgraphs/best-practices/timeseries/ /cs/subgraphs/billing/ /cs/subgraphs/cookbook/arweave/ -/cs/subgraphs/cookbook/avoid-eth-calls/ -/cs/subgraphs/cookbook/cosmos/ -/cs/subgraphs/cookbook/derivedfrom/ /cs/subgraphs/cookbook/enums/ -/cs/subgraphs/cookbook/grafting-hotfix/ /cs/subgraphs/cookbook/grafting/ -/cs/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /cs/subgraphs/cookbook/near/ /cs/subgraphs/cookbook/polymarket/ -/cs/subgraphs/cookbook/pruning/ /cs/subgraphs/cookbook/secure-api-keys-nextjs/ /cs/subgraphs/cookbook/subgraph-debug-forking/ /cs/subgraphs/cookbook/subgraph-uncrashable/ -/cs/subgraphs/cookbook/timeseries/ /cs/subgraphs/cookbook/transfer-to-the-graph/ /cs/subgraphs/developing/creating/advanced/ /cs/subgraphs/developing/creating/assemblyscript-mappings/ @@ -142,7 +141,6 @@ /cs/subgraphs/developing/creating/subgraph-manifest/ /cs/subgraphs/developing/creating/unit-testing-framework/ /cs/subgraphs/developing/deploying/multiple-networks/ -/cs/subgraphs/developing/deploying/subgraph-studio-faq/ /cs/subgraphs/developing/deploying/using-subgraph-studio/ /cs/subgraphs/developing/developer-faq/ /cs/subgraphs/developing/introduction/ @@ -164,7 +162,7 @@ /cs/subgraphs/querying/subgraph-id-vs-deployment-id/ /cs/subgraphs/quick-start/ /cs/substreams/developing/dev-container/ -/cs/substreams/developing/sinks/sinks/ +/cs/substreams/developing/sinks/ /cs/substreams/developing/solana/account-changes/ /cs/substreams/developing/solana/transactions/ /cs/substreams/introduction/ @@ -187,32 +185,32 @@ /de/indexing/tooling/graphcast/ /de/resources/benefits/ /de/resources/glossary/ -/de/resources/release-notes/assemblyscript-migration-guide/ -/de/resources/release-notes/graphql-validations-migration-guide/ +/de/resources/migration-guides/assemblyscript-migration-guide/ +/de/resources/migration-guides/graphql-validations-migration-guide/ /de/resources/roles/curating/ /de/resources/roles/delegating/delegating/ /de/resources/roles/delegating/undelegating/ +/de/resources/subgraph-studio-faq/ /de/resources/tokenomics/ /de/sps/introduction/ /de/sps/sps-faq/ /de/sps/triggers/ /de/sps/tutorial/ +/de/subgraphs/best-practices/avoid-eth-calls/ +/de/subgraphs/best-practices/derivedfrom/ +/de/subgraphs/best-practices/grafting-hotfix/ +/de/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/de/subgraphs/best-practices/pruning/ +/de/subgraphs/best-practices/timeseries/ /de/subgraphs/billing/ /de/subgraphs/cookbook/arweave/ -/de/subgraphs/cookbook/avoid-eth-calls/ -/de/subgraphs/cookbook/cosmos/ -/de/subgraphs/cookbook/derivedfrom/ /de/subgraphs/cookbook/enums/ -/de/subgraphs/cookbook/grafting-hotfix/ /de/subgraphs/cookbook/grafting/ -/de/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /de/subgraphs/cookbook/near/ /de/subgraphs/cookbook/polymarket/ -/de/subgraphs/cookbook/pruning/ /de/subgraphs/cookbook/secure-api-keys-nextjs/ /de/subgraphs/cookbook/subgraph-debug-forking/ /de/subgraphs/cookbook/subgraph-uncrashable/ -/de/subgraphs/cookbook/timeseries/ /de/subgraphs/cookbook/transfer-to-the-graph/ /de/subgraphs/developing/creating/advanced/ /de/subgraphs/developing/creating/assemblyscript-mappings/ @@ -226,7 +224,6 @@ /de/subgraphs/developing/creating/subgraph-manifest/ /de/subgraphs/developing/creating/unit-testing-framework/ /de/subgraphs/developing/deploying/multiple-networks/ -/de/subgraphs/developing/deploying/subgraph-studio-faq/ /de/subgraphs/developing/deploying/using-subgraph-studio/ /de/subgraphs/developing/developer-faq/ /de/subgraphs/developing/introduction/ @@ -248,7 +245,7 @@ /de/subgraphs/querying/subgraph-id-vs-deployment-id/ /de/subgraphs/quick-start/ /de/substreams/developing/dev-container/ -/de/substreams/developing/sinks/sinks/ +/de/substreams/developing/sinks/ /de/substreams/developing/solana/account-changes/ /de/substreams/developing/solana/transactions/ /de/substreams/introduction/ @@ -273,32 +270,32 @@ /en/indexing/tooling/graphcast/ /en/resources/benefits/ /en/resources/glossary/ -/en/resources/release-notes/assemblyscript-migration-guide/ -/en/resources/release-notes/graphql-validations-migration-guide/ +/en/resources/migration-guides/assemblyscript-migration-guide/ +/en/resources/migration-guides/graphql-validations-migration-guide/ /en/resources/roles/curating/ /en/resources/roles/delegating/delegating/ /en/resources/roles/delegating/undelegating/ +/en/resources/subgraph-studio-faq/ /en/resources/tokenomics/ /en/sps/introduction/ /en/sps/sps-faq/ /en/sps/triggers/ /en/sps/tutorial/ +/en/subgraphs/best-practices/avoid-eth-calls/ +/en/subgraphs/best-practices/derivedfrom/ +/en/subgraphs/best-practices/grafting-hotfix/ +/en/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/en/subgraphs/best-practices/pruning/ +/en/subgraphs/best-practices/timeseries/ /en/subgraphs/billing/ /en/subgraphs/cookbook/arweave/ -/en/subgraphs/cookbook/avoid-eth-calls/ -/en/subgraphs/cookbook/cosmos/ -/en/subgraphs/cookbook/derivedfrom/ /en/subgraphs/cookbook/enums/ -/en/subgraphs/cookbook/grafting-hotfix/ /en/subgraphs/cookbook/grafting/ -/en/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /en/subgraphs/cookbook/near/ /en/subgraphs/cookbook/polymarket/ -/en/subgraphs/cookbook/pruning/ /en/subgraphs/cookbook/secure-api-keys-nextjs/ /en/subgraphs/cookbook/subgraph-debug-forking/ /en/subgraphs/cookbook/subgraph-uncrashable/ -/en/subgraphs/cookbook/timeseries/ /en/subgraphs/cookbook/transfer-to-the-graph/ /en/subgraphs/developing/creating/advanced/ /en/subgraphs/developing/creating/assemblyscript-mappings/ @@ -312,7 +309,6 @@ /en/subgraphs/developing/creating/subgraph-manifest/ /en/subgraphs/developing/creating/unit-testing-framework/ /en/subgraphs/developing/deploying/multiple-networks/ -/en/subgraphs/developing/deploying/subgraph-studio-faq/ /en/subgraphs/developing/deploying/using-subgraph-studio/ /en/subgraphs/developing/developer-faq/ /en/subgraphs/developing/introduction/ @@ -334,7 +330,7 @@ /en/subgraphs/querying/subgraph-id-vs-deployment-id/ /en/subgraphs/quick-start/ /en/substreams/developing/dev-container/ -/en/substreams/developing/sinks/sinks/ +/en/substreams/developing/sinks/ /en/substreams/developing/solana/account-changes/ /en/substreams/developing/solana/transactions/ /en/substreams/introduction/ @@ -359,32 +355,32 @@ /es/indexing/tooling/graphcast/ /es/resources/benefits/ /es/resources/glossary/ -/es/resources/release-notes/assemblyscript-migration-guide/ -/es/resources/release-notes/graphql-validations-migration-guide/ +/es/resources/migration-guides/assemblyscript-migration-guide/ +/es/resources/migration-guides/graphql-validations-migration-guide/ /es/resources/roles/curating/ /es/resources/roles/delegating/delegating/ /es/resources/roles/delegating/undelegating/ +/es/resources/subgraph-studio-faq/ /es/resources/tokenomics/ /es/sps/introduction/ /es/sps/sps-faq/ /es/sps/triggers/ /es/sps/tutorial/ +/es/subgraphs/best-practices/avoid-eth-calls/ +/es/subgraphs/best-practices/derivedfrom/ +/es/subgraphs/best-practices/grafting-hotfix/ +/es/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/es/subgraphs/best-practices/pruning/ +/es/subgraphs/best-practices/timeseries/ /es/subgraphs/billing/ /es/subgraphs/cookbook/arweave/ -/es/subgraphs/cookbook/avoid-eth-calls/ -/es/subgraphs/cookbook/cosmos/ -/es/subgraphs/cookbook/derivedfrom/ /es/subgraphs/cookbook/enums/ -/es/subgraphs/cookbook/grafting-hotfix/ /es/subgraphs/cookbook/grafting/ -/es/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /es/subgraphs/cookbook/near/ /es/subgraphs/cookbook/polymarket/ -/es/subgraphs/cookbook/pruning/ /es/subgraphs/cookbook/secure-api-keys-nextjs/ /es/subgraphs/cookbook/subgraph-debug-forking/ /es/subgraphs/cookbook/subgraph-uncrashable/ -/es/subgraphs/cookbook/timeseries/ /es/subgraphs/cookbook/transfer-to-the-graph/ /es/subgraphs/developing/creating/advanced/ /es/subgraphs/developing/creating/assemblyscript-mappings/ @@ -398,7 +394,6 @@ /es/subgraphs/developing/creating/subgraph-manifest/ /es/subgraphs/developing/creating/unit-testing-framework/ /es/subgraphs/developing/deploying/multiple-networks/ -/es/subgraphs/developing/deploying/subgraph-studio-faq/ /es/subgraphs/developing/deploying/using-subgraph-studio/ /es/subgraphs/developing/developer-faq/ /es/subgraphs/developing/introduction/ @@ -420,7 +415,7 @@ /es/subgraphs/querying/subgraph-id-vs-deployment-id/ /es/subgraphs/quick-start/ /es/substreams/developing/dev-container/ -/es/substreams/developing/sinks/sinks/ +/es/substreams/developing/sinks/ /es/substreams/developing/solana/account-changes/ /es/substreams/developing/solana/transactions/ /es/substreams/introduction/ @@ -445,32 +440,32 @@ /fr/indexing/tooling/graphcast/ /fr/resources/benefits/ /fr/resources/glossary/ -/fr/resources/release-notes/assemblyscript-migration-guide/ -/fr/resources/release-notes/graphql-validations-migration-guide/ +/fr/resources/migration-guides/assemblyscript-migration-guide/ +/fr/resources/migration-guides/graphql-validations-migration-guide/ /fr/resources/roles/curating/ /fr/resources/roles/delegating/delegating/ /fr/resources/roles/delegating/undelegating/ +/fr/resources/subgraph-studio-faq/ /fr/resources/tokenomics/ /fr/sps/introduction/ /fr/sps/sps-faq/ /fr/sps/triggers/ /fr/sps/tutorial/ +/fr/subgraphs/best-practices/avoid-eth-calls/ +/fr/subgraphs/best-practices/derivedfrom/ +/fr/subgraphs/best-practices/grafting-hotfix/ +/fr/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/fr/subgraphs/best-practices/pruning/ +/fr/subgraphs/best-practices/timeseries/ /fr/subgraphs/billing/ /fr/subgraphs/cookbook/arweave/ -/fr/subgraphs/cookbook/avoid-eth-calls/ -/fr/subgraphs/cookbook/cosmos/ -/fr/subgraphs/cookbook/derivedfrom/ /fr/subgraphs/cookbook/enums/ -/fr/subgraphs/cookbook/grafting-hotfix/ /fr/subgraphs/cookbook/grafting/ -/fr/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /fr/subgraphs/cookbook/near/ /fr/subgraphs/cookbook/polymarket/ -/fr/subgraphs/cookbook/pruning/ /fr/subgraphs/cookbook/secure-api-keys-nextjs/ /fr/subgraphs/cookbook/subgraph-debug-forking/ /fr/subgraphs/cookbook/subgraph-uncrashable/ -/fr/subgraphs/cookbook/timeseries/ /fr/subgraphs/cookbook/transfer-to-the-graph/ /fr/subgraphs/developing/creating/advanced/ /fr/subgraphs/developing/creating/assemblyscript-mappings/ @@ -484,7 +479,6 @@ /fr/subgraphs/developing/creating/subgraph-manifest/ /fr/subgraphs/developing/creating/unit-testing-framework/ /fr/subgraphs/developing/deploying/multiple-networks/ -/fr/subgraphs/developing/deploying/subgraph-studio-faq/ /fr/subgraphs/developing/deploying/using-subgraph-studio/ /fr/subgraphs/developing/developer-faq/ /fr/subgraphs/developing/introduction/ @@ -506,7 +500,7 @@ /fr/subgraphs/querying/subgraph-id-vs-deployment-id/ /fr/subgraphs/quick-start/ /fr/substreams/developing/dev-container/ -/fr/substreams/developing/sinks/sinks/ +/fr/substreams/developing/sinks/ /fr/substreams/developing/solana/account-changes/ /fr/substreams/developing/solana/transactions/ /fr/substreams/introduction/ @@ -531,32 +525,32 @@ /hi/indexing/tooling/graphcast/ /hi/resources/benefits/ /hi/resources/glossary/ -/hi/resources/release-notes/assemblyscript-migration-guide/ -/hi/resources/release-notes/graphql-validations-migration-guide/ +/hi/resources/migration-guides/assemblyscript-migration-guide/ +/hi/resources/migration-guides/graphql-validations-migration-guide/ /hi/resources/roles/curating/ /hi/resources/roles/delegating/delegating/ /hi/resources/roles/delegating/undelegating/ +/hi/resources/subgraph-studio-faq/ /hi/resources/tokenomics/ /hi/sps/introduction/ /hi/sps/sps-faq/ /hi/sps/triggers/ /hi/sps/tutorial/ +/hi/subgraphs/best-practices/avoid-eth-calls/ +/hi/subgraphs/best-practices/derivedfrom/ +/hi/subgraphs/best-practices/grafting-hotfix/ +/hi/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/hi/subgraphs/best-practices/pruning/ +/hi/subgraphs/best-practices/timeseries/ /hi/subgraphs/billing/ /hi/subgraphs/cookbook/arweave/ -/hi/subgraphs/cookbook/avoid-eth-calls/ -/hi/subgraphs/cookbook/cosmos/ -/hi/subgraphs/cookbook/derivedfrom/ /hi/subgraphs/cookbook/enums/ -/hi/subgraphs/cookbook/grafting-hotfix/ /hi/subgraphs/cookbook/grafting/ -/hi/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /hi/subgraphs/cookbook/near/ /hi/subgraphs/cookbook/polymarket/ -/hi/subgraphs/cookbook/pruning/ /hi/subgraphs/cookbook/secure-api-keys-nextjs/ /hi/subgraphs/cookbook/subgraph-debug-forking/ /hi/subgraphs/cookbook/subgraph-uncrashable/ -/hi/subgraphs/cookbook/timeseries/ /hi/subgraphs/cookbook/transfer-to-the-graph/ /hi/subgraphs/developing/creating/advanced/ /hi/subgraphs/developing/creating/assemblyscript-mappings/ @@ -570,7 +564,6 @@ /hi/subgraphs/developing/creating/subgraph-manifest/ /hi/subgraphs/developing/creating/unit-testing-framework/ /hi/subgraphs/developing/deploying/multiple-networks/ -/hi/subgraphs/developing/deploying/subgraph-studio-faq/ /hi/subgraphs/developing/deploying/using-subgraph-studio/ /hi/subgraphs/developing/developer-faq/ /hi/subgraphs/developing/introduction/ @@ -592,7 +585,7 @@ /hi/subgraphs/querying/subgraph-id-vs-deployment-id/ /hi/subgraphs/quick-start/ /hi/substreams/developing/dev-container/ -/hi/substreams/developing/sinks/sinks/ +/hi/substreams/developing/sinks/ /hi/substreams/developing/solana/account-changes/ /hi/substreams/developing/solana/transactions/ /hi/substreams/introduction/ @@ -617,32 +610,32 @@ /it/indexing/tooling/graphcast/ /it/resources/benefits/ /it/resources/glossary/ -/it/resources/release-notes/assemblyscript-migration-guide/ -/it/resources/release-notes/graphql-validations-migration-guide/ +/it/resources/migration-guides/assemblyscript-migration-guide/ +/it/resources/migration-guides/graphql-validations-migration-guide/ /it/resources/roles/curating/ /it/resources/roles/delegating/delegating/ /it/resources/roles/delegating/undelegating/ +/it/resources/subgraph-studio-faq/ /it/resources/tokenomics/ /it/sps/introduction/ /it/sps/sps-faq/ /it/sps/triggers/ /it/sps/tutorial/ +/it/subgraphs/best-practices/avoid-eth-calls/ +/it/subgraphs/best-practices/derivedfrom/ +/it/subgraphs/best-practices/grafting-hotfix/ +/it/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/it/subgraphs/best-practices/pruning/ +/it/subgraphs/best-practices/timeseries/ /it/subgraphs/billing/ /it/subgraphs/cookbook/arweave/ -/it/subgraphs/cookbook/avoid-eth-calls/ -/it/subgraphs/cookbook/cosmos/ -/it/subgraphs/cookbook/derivedfrom/ /it/subgraphs/cookbook/enums/ -/it/subgraphs/cookbook/grafting-hotfix/ /it/subgraphs/cookbook/grafting/ -/it/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /it/subgraphs/cookbook/near/ /it/subgraphs/cookbook/polymarket/ -/it/subgraphs/cookbook/pruning/ /it/subgraphs/cookbook/secure-api-keys-nextjs/ /it/subgraphs/cookbook/subgraph-debug-forking/ /it/subgraphs/cookbook/subgraph-uncrashable/ -/it/subgraphs/cookbook/timeseries/ /it/subgraphs/cookbook/transfer-to-the-graph/ /it/subgraphs/developing/creating/advanced/ /it/subgraphs/developing/creating/assemblyscript-mappings/ @@ -656,7 +649,6 @@ /it/subgraphs/developing/creating/subgraph-manifest/ /it/subgraphs/developing/creating/unit-testing-framework/ /it/subgraphs/developing/deploying/multiple-networks/ -/it/subgraphs/developing/deploying/subgraph-studio-faq/ /it/subgraphs/developing/deploying/using-subgraph-studio/ /it/subgraphs/developing/developer-faq/ /it/subgraphs/developing/introduction/ @@ -678,7 +670,7 @@ /it/subgraphs/querying/subgraph-id-vs-deployment-id/ /it/subgraphs/quick-start/ /it/substreams/developing/dev-container/ -/it/substreams/developing/sinks/sinks/ +/it/substreams/developing/sinks/ /it/substreams/developing/solana/account-changes/ /it/substreams/developing/solana/transactions/ /it/substreams/introduction/ @@ -703,32 +695,32 @@ /ja/indexing/tooling/graphcast/ /ja/resources/benefits/ /ja/resources/glossary/ -/ja/resources/release-notes/assemblyscript-migration-guide/ -/ja/resources/release-notes/graphql-validations-migration-guide/ +/ja/resources/migration-guides/assemblyscript-migration-guide/ +/ja/resources/migration-guides/graphql-validations-migration-guide/ /ja/resources/roles/curating/ /ja/resources/roles/delegating/delegating/ /ja/resources/roles/delegating/undelegating/ +/ja/resources/subgraph-studio-faq/ /ja/resources/tokenomics/ /ja/sps/introduction/ /ja/sps/sps-faq/ /ja/sps/triggers/ /ja/sps/tutorial/ +/ja/subgraphs/best-practices/avoid-eth-calls/ +/ja/subgraphs/best-practices/derivedfrom/ +/ja/subgraphs/best-practices/grafting-hotfix/ +/ja/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/ja/subgraphs/best-practices/pruning/ +/ja/subgraphs/best-practices/timeseries/ /ja/subgraphs/billing/ /ja/subgraphs/cookbook/arweave/ -/ja/subgraphs/cookbook/avoid-eth-calls/ -/ja/subgraphs/cookbook/cosmos/ -/ja/subgraphs/cookbook/derivedfrom/ /ja/subgraphs/cookbook/enums/ -/ja/subgraphs/cookbook/grafting-hotfix/ /ja/subgraphs/cookbook/grafting/ -/ja/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /ja/subgraphs/cookbook/near/ /ja/subgraphs/cookbook/polymarket/ -/ja/subgraphs/cookbook/pruning/ /ja/subgraphs/cookbook/secure-api-keys-nextjs/ /ja/subgraphs/cookbook/subgraph-debug-forking/ /ja/subgraphs/cookbook/subgraph-uncrashable/ -/ja/subgraphs/cookbook/timeseries/ /ja/subgraphs/cookbook/transfer-to-the-graph/ /ja/subgraphs/developing/creating/advanced/ /ja/subgraphs/developing/creating/assemblyscript-mappings/ @@ -742,7 +734,6 @@ /ja/subgraphs/developing/creating/subgraph-manifest/ /ja/subgraphs/developing/creating/unit-testing-framework/ /ja/subgraphs/developing/deploying/multiple-networks/ -/ja/subgraphs/developing/deploying/subgraph-studio-faq/ /ja/subgraphs/developing/deploying/using-subgraph-studio/ /ja/subgraphs/developing/developer-faq/ /ja/subgraphs/developing/introduction/ @@ -764,7 +755,7 @@ /ja/subgraphs/querying/subgraph-id-vs-deployment-id/ /ja/subgraphs/quick-start/ /ja/substreams/developing/dev-container/ -/ja/substreams/developing/sinks/sinks/ +/ja/substreams/developing/sinks/ /ja/substreams/developing/solana/account-changes/ /ja/substreams/developing/solana/transactions/ /ja/substreams/introduction/ @@ -787,32 +778,32 @@ /ko/indexing/tooling/graphcast/ /ko/resources/benefits/ /ko/resources/glossary/ -/ko/resources/release-notes/assemblyscript-migration-guide/ -/ko/resources/release-notes/graphql-validations-migration-guide/ +/ko/resources/migration-guides/assemblyscript-migration-guide/ +/ko/resources/migration-guides/graphql-validations-migration-guide/ /ko/resources/roles/curating/ /ko/resources/roles/delegating/delegating/ /ko/resources/roles/delegating/undelegating/ +/ko/resources/subgraph-studio-faq/ /ko/resources/tokenomics/ /ko/sps/introduction/ /ko/sps/sps-faq/ /ko/sps/triggers/ /ko/sps/tutorial/ +/ko/subgraphs/best-practices/avoid-eth-calls/ +/ko/subgraphs/best-practices/derivedfrom/ +/ko/subgraphs/best-practices/grafting-hotfix/ +/ko/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/ko/subgraphs/best-practices/pruning/ +/ko/subgraphs/best-practices/timeseries/ /ko/subgraphs/billing/ /ko/subgraphs/cookbook/arweave/ -/ko/subgraphs/cookbook/avoid-eth-calls/ -/ko/subgraphs/cookbook/cosmos/ -/ko/subgraphs/cookbook/derivedfrom/ /ko/subgraphs/cookbook/enums/ -/ko/subgraphs/cookbook/grafting-hotfix/ /ko/subgraphs/cookbook/grafting/ -/ko/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /ko/subgraphs/cookbook/near/ /ko/subgraphs/cookbook/polymarket/ -/ko/subgraphs/cookbook/pruning/ /ko/subgraphs/cookbook/secure-api-keys-nextjs/ /ko/subgraphs/cookbook/subgraph-debug-forking/ /ko/subgraphs/cookbook/subgraph-uncrashable/ -/ko/subgraphs/cookbook/timeseries/ /ko/subgraphs/cookbook/transfer-to-the-graph/ /ko/subgraphs/developing/creating/advanced/ /ko/subgraphs/developing/creating/assemblyscript-mappings/ @@ -826,7 +817,6 @@ /ko/subgraphs/developing/creating/subgraph-manifest/ /ko/subgraphs/developing/creating/unit-testing-framework/ /ko/subgraphs/developing/deploying/multiple-networks/ -/ko/subgraphs/developing/deploying/subgraph-studio-faq/ /ko/subgraphs/developing/deploying/using-subgraph-studio/ /ko/subgraphs/developing/developer-faq/ /ko/subgraphs/developing/introduction/ @@ -848,7 +838,7 @@ /ko/subgraphs/querying/subgraph-id-vs-deployment-id/ /ko/subgraphs/quick-start/ /ko/substreams/developing/dev-container/ -/ko/substreams/developing/sinks/sinks/ +/ko/substreams/developing/sinks/ /ko/substreams/developing/solana/account-changes/ /ko/substreams/developing/solana/transactions/ /ko/substreams/introduction/ @@ -873,32 +863,32 @@ /mr/indexing/tooling/graphcast/ /mr/resources/benefits/ /mr/resources/glossary/ -/mr/resources/release-notes/assemblyscript-migration-guide/ -/mr/resources/release-notes/graphql-validations-migration-guide/ +/mr/resources/migration-guides/assemblyscript-migration-guide/ +/mr/resources/migration-guides/graphql-validations-migration-guide/ /mr/resources/roles/curating/ /mr/resources/roles/delegating/delegating/ /mr/resources/roles/delegating/undelegating/ +/mr/resources/subgraph-studio-faq/ /mr/resources/tokenomics/ /mr/sps/introduction/ /mr/sps/sps-faq/ /mr/sps/triggers/ /mr/sps/tutorial/ +/mr/subgraphs/best-practices/avoid-eth-calls/ +/mr/subgraphs/best-practices/derivedfrom/ +/mr/subgraphs/best-practices/grafting-hotfix/ +/mr/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/mr/subgraphs/best-practices/pruning/ +/mr/subgraphs/best-practices/timeseries/ /mr/subgraphs/billing/ /mr/subgraphs/cookbook/arweave/ -/mr/subgraphs/cookbook/avoid-eth-calls/ -/mr/subgraphs/cookbook/cosmos/ -/mr/subgraphs/cookbook/derivedfrom/ /mr/subgraphs/cookbook/enums/ -/mr/subgraphs/cookbook/grafting-hotfix/ /mr/subgraphs/cookbook/grafting/ -/mr/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /mr/subgraphs/cookbook/near/ /mr/subgraphs/cookbook/polymarket/ -/mr/subgraphs/cookbook/pruning/ /mr/subgraphs/cookbook/secure-api-keys-nextjs/ /mr/subgraphs/cookbook/subgraph-debug-forking/ /mr/subgraphs/cookbook/subgraph-uncrashable/ -/mr/subgraphs/cookbook/timeseries/ /mr/subgraphs/cookbook/transfer-to-the-graph/ /mr/subgraphs/developing/creating/advanced/ /mr/subgraphs/developing/creating/assemblyscript-mappings/ @@ -912,7 +902,6 @@ /mr/subgraphs/developing/creating/subgraph-manifest/ /mr/subgraphs/developing/creating/unit-testing-framework/ /mr/subgraphs/developing/deploying/multiple-networks/ -/mr/subgraphs/developing/deploying/subgraph-studio-faq/ /mr/subgraphs/developing/deploying/using-subgraph-studio/ /mr/subgraphs/developing/developer-faq/ /mr/subgraphs/developing/introduction/ @@ -934,7 +923,7 @@ /mr/subgraphs/querying/subgraph-id-vs-deployment-id/ /mr/subgraphs/quick-start/ /mr/substreams/developing/dev-container/ -/mr/substreams/developing/sinks/sinks/ +/mr/substreams/developing/sinks/ /mr/substreams/developing/solana/account-changes/ /mr/substreams/developing/solana/transactions/ /mr/substreams/introduction/ @@ -957,32 +946,32 @@ /nl/indexing/tooling/graphcast/ /nl/resources/benefits/ /nl/resources/glossary/ -/nl/resources/release-notes/assemblyscript-migration-guide/ -/nl/resources/release-notes/graphql-validations-migration-guide/ +/nl/resources/migration-guides/assemblyscript-migration-guide/ +/nl/resources/migration-guides/graphql-validations-migration-guide/ /nl/resources/roles/curating/ /nl/resources/roles/delegating/delegating/ /nl/resources/roles/delegating/undelegating/ +/nl/resources/subgraph-studio-faq/ /nl/resources/tokenomics/ /nl/sps/introduction/ /nl/sps/sps-faq/ /nl/sps/triggers/ /nl/sps/tutorial/ +/nl/subgraphs/best-practices/avoid-eth-calls/ +/nl/subgraphs/best-practices/derivedfrom/ +/nl/subgraphs/best-practices/grafting-hotfix/ +/nl/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/nl/subgraphs/best-practices/pruning/ +/nl/subgraphs/best-practices/timeseries/ /nl/subgraphs/billing/ /nl/subgraphs/cookbook/arweave/ -/nl/subgraphs/cookbook/avoid-eth-calls/ -/nl/subgraphs/cookbook/cosmos/ -/nl/subgraphs/cookbook/derivedfrom/ /nl/subgraphs/cookbook/enums/ -/nl/subgraphs/cookbook/grafting-hotfix/ /nl/subgraphs/cookbook/grafting/ -/nl/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /nl/subgraphs/cookbook/near/ /nl/subgraphs/cookbook/polymarket/ -/nl/subgraphs/cookbook/pruning/ /nl/subgraphs/cookbook/secure-api-keys-nextjs/ /nl/subgraphs/cookbook/subgraph-debug-forking/ /nl/subgraphs/cookbook/subgraph-uncrashable/ -/nl/subgraphs/cookbook/timeseries/ /nl/subgraphs/cookbook/transfer-to-the-graph/ /nl/subgraphs/developing/creating/advanced/ /nl/subgraphs/developing/creating/assemblyscript-mappings/ @@ -996,7 +985,6 @@ /nl/subgraphs/developing/creating/subgraph-manifest/ /nl/subgraphs/developing/creating/unit-testing-framework/ /nl/subgraphs/developing/deploying/multiple-networks/ -/nl/subgraphs/developing/deploying/subgraph-studio-faq/ /nl/subgraphs/developing/deploying/using-subgraph-studio/ /nl/subgraphs/developing/developer-faq/ /nl/subgraphs/developing/introduction/ @@ -1018,7 +1006,7 @@ /nl/subgraphs/querying/subgraph-id-vs-deployment-id/ /nl/subgraphs/quick-start/ /nl/substreams/developing/dev-container/ -/nl/substreams/developing/sinks/sinks/ +/nl/substreams/developing/sinks/ /nl/substreams/developing/solana/account-changes/ /nl/substreams/developing/solana/transactions/ /nl/substreams/introduction/ @@ -1041,32 +1029,32 @@ /pl/indexing/tooling/graphcast/ /pl/resources/benefits/ /pl/resources/glossary/ -/pl/resources/release-notes/assemblyscript-migration-guide/ -/pl/resources/release-notes/graphql-validations-migration-guide/ +/pl/resources/migration-guides/assemblyscript-migration-guide/ +/pl/resources/migration-guides/graphql-validations-migration-guide/ /pl/resources/roles/curating/ /pl/resources/roles/delegating/delegating/ /pl/resources/roles/delegating/undelegating/ +/pl/resources/subgraph-studio-faq/ /pl/resources/tokenomics/ /pl/sps/introduction/ /pl/sps/sps-faq/ /pl/sps/triggers/ /pl/sps/tutorial/ +/pl/subgraphs/best-practices/avoid-eth-calls/ +/pl/subgraphs/best-practices/derivedfrom/ +/pl/subgraphs/best-practices/grafting-hotfix/ +/pl/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/pl/subgraphs/best-practices/pruning/ +/pl/subgraphs/best-practices/timeseries/ /pl/subgraphs/billing/ /pl/subgraphs/cookbook/arweave/ -/pl/subgraphs/cookbook/avoid-eth-calls/ -/pl/subgraphs/cookbook/cosmos/ -/pl/subgraphs/cookbook/derivedfrom/ /pl/subgraphs/cookbook/enums/ -/pl/subgraphs/cookbook/grafting-hotfix/ /pl/subgraphs/cookbook/grafting/ -/pl/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /pl/subgraphs/cookbook/near/ /pl/subgraphs/cookbook/polymarket/ -/pl/subgraphs/cookbook/pruning/ /pl/subgraphs/cookbook/secure-api-keys-nextjs/ /pl/subgraphs/cookbook/subgraph-debug-forking/ /pl/subgraphs/cookbook/subgraph-uncrashable/ -/pl/subgraphs/cookbook/timeseries/ /pl/subgraphs/cookbook/transfer-to-the-graph/ /pl/subgraphs/developing/creating/advanced/ /pl/subgraphs/developing/creating/assemblyscript-mappings/ @@ -1080,7 +1068,6 @@ /pl/subgraphs/developing/creating/subgraph-manifest/ /pl/subgraphs/developing/creating/unit-testing-framework/ /pl/subgraphs/developing/deploying/multiple-networks/ -/pl/subgraphs/developing/deploying/subgraph-studio-faq/ /pl/subgraphs/developing/deploying/using-subgraph-studio/ /pl/subgraphs/developing/developer-faq/ /pl/subgraphs/developing/introduction/ @@ -1102,7 +1089,7 @@ /pl/subgraphs/querying/subgraph-id-vs-deployment-id/ /pl/subgraphs/quick-start/ /pl/substreams/developing/dev-container/ -/pl/substreams/developing/sinks/sinks/ +/pl/substreams/developing/sinks/ /pl/substreams/developing/solana/account-changes/ /pl/substreams/developing/solana/transactions/ /pl/substreams/introduction/ @@ -1127,32 +1114,32 @@ /pt/indexing/tooling/graphcast/ /pt/resources/benefits/ /pt/resources/glossary/ -/pt/resources/release-notes/assemblyscript-migration-guide/ -/pt/resources/release-notes/graphql-validations-migration-guide/ +/pt/resources/migration-guides/assemblyscript-migration-guide/ +/pt/resources/migration-guides/graphql-validations-migration-guide/ /pt/resources/roles/curating/ /pt/resources/roles/delegating/delegating/ /pt/resources/roles/delegating/undelegating/ +/pt/resources/subgraph-studio-faq/ /pt/resources/tokenomics/ /pt/sps/introduction/ /pt/sps/sps-faq/ /pt/sps/triggers/ /pt/sps/tutorial/ +/pt/subgraphs/best-practices/avoid-eth-calls/ +/pt/subgraphs/best-practices/derivedfrom/ +/pt/subgraphs/best-practices/grafting-hotfix/ +/pt/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/pt/subgraphs/best-practices/pruning/ +/pt/subgraphs/best-practices/timeseries/ /pt/subgraphs/billing/ /pt/subgraphs/cookbook/arweave/ -/pt/subgraphs/cookbook/avoid-eth-calls/ -/pt/subgraphs/cookbook/cosmos/ -/pt/subgraphs/cookbook/derivedfrom/ /pt/subgraphs/cookbook/enums/ -/pt/subgraphs/cookbook/grafting-hotfix/ /pt/subgraphs/cookbook/grafting/ -/pt/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /pt/subgraphs/cookbook/near/ /pt/subgraphs/cookbook/polymarket/ -/pt/subgraphs/cookbook/pruning/ /pt/subgraphs/cookbook/secure-api-keys-nextjs/ /pt/subgraphs/cookbook/subgraph-debug-forking/ /pt/subgraphs/cookbook/subgraph-uncrashable/ -/pt/subgraphs/cookbook/timeseries/ /pt/subgraphs/cookbook/transfer-to-the-graph/ /pt/subgraphs/developing/creating/advanced/ /pt/subgraphs/developing/creating/assemblyscript-mappings/ @@ -1166,7 +1153,6 @@ /pt/subgraphs/developing/creating/subgraph-manifest/ /pt/subgraphs/developing/creating/unit-testing-framework/ /pt/subgraphs/developing/deploying/multiple-networks/ -/pt/subgraphs/developing/deploying/subgraph-studio-faq/ /pt/subgraphs/developing/deploying/using-subgraph-studio/ /pt/subgraphs/developing/developer-faq/ /pt/subgraphs/developing/introduction/ @@ -1188,7 +1174,7 @@ /pt/subgraphs/querying/subgraph-id-vs-deployment-id/ /pt/subgraphs/quick-start/ /pt/substreams/developing/dev-container/ -/pt/substreams/developing/sinks/sinks/ +/pt/substreams/developing/sinks/ /pt/substreams/developing/solana/account-changes/ /pt/substreams/developing/solana/transactions/ /pt/substreams/introduction/ @@ -1211,32 +1197,32 @@ /ro/indexing/tooling/graphcast/ /ro/resources/benefits/ /ro/resources/glossary/ -/ro/resources/release-notes/assemblyscript-migration-guide/ -/ro/resources/release-notes/graphql-validations-migration-guide/ +/ro/resources/migration-guides/assemblyscript-migration-guide/ +/ro/resources/migration-guides/graphql-validations-migration-guide/ /ro/resources/roles/curating/ /ro/resources/roles/delegating/delegating/ /ro/resources/roles/delegating/undelegating/ +/ro/resources/subgraph-studio-faq/ /ro/resources/tokenomics/ /ro/sps/introduction/ /ro/sps/sps-faq/ /ro/sps/triggers/ /ro/sps/tutorial/ +/ro/subgraphs/best-practices/avoid-eth-calls/ +/ro/subgraphs/best-practices/derivedfrom/ +/ro/subgraphs/best-practices/grafting-hotfix/ +/ro/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/ro/subgraphs/best-practices/pruning/ +/ro/subgraphs/best-practices/timeseries/ /ro/subgraphs/billing/ /ro/subgraphs/cookbook/arweave/ -/ro/subgraphs/cookbook/avoid-eth-calls/ -/ro/subgraphs/cookbook/cosmos/ -/ro/subgraphs/cookbook/derivedfrom/ /ro/subgraphs/cookbook/enums/ -/ro/subgraphs/cookbook/grafting-hotfix/ /ro/subgraphs/cookbook/grafting/ -/ro/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /ro/subgraphs/cookbook/near/ /ro/subgraphs/cookbook/polymarket/ -/ro/subgraphs/cookbook/pruning/ /ro/subgraphs/cookbook/secure-api-keys-nextjs/ /ro/subgraphs/cookbook/subgraph-debug-forking/ /ro/subgraphs/cookbook/subgraph-uncrashable/ -/ro/subgraphs/cookbook/timeseries/ /ro/subgraphs/cookbook/transfer-to-the-graph/ /ro/subgraphs/developing/creating/advanced/ /ro/subgraphs/developing/creating/assemblyscript-mappings/ @@ -1250,7 +1236,6 @@ /ro/subgraphs/developing/creating/subgraph-manifest/ /ro/subgraphs/developing/creating/unit-testing-framework/ /ro/subgraphs/developing/deploying/multiple-networks/ -/ro/subgraphs/developing/deploying/subgraph-studio-faq/ /ro/subgraphs/developing/deploying/using-subgraph-studio/ /ro/subgraphs/developing/developer-faq/ /ro/subgraphs/developing/introduction/ @@ -1272,7 +1257,7 @@ /ro/subgraphs/querying/subgraph-id-vs-deployment-id/ /ro/subgraphs/quick-start/ /ro/substreams/developing/dev-container/ -/ro/substreams/developing/sinks/sinks/ +/ro/substreams/developing/sinks/ /ro/substreams/developing/solana/account-changes/ /ro/substreams/developing/solana/transactions/ /ro/substreams/introduction/ @@ -1297,32 +1282,32 @@ /ru/indexing/tooling/graphcast/ /ru/resources/benefits/ /ru/resources/glossary/ -/ru/resources/release-notes/assemblyscript-migration-guide/ -/ru/resources/release-notes/graphql-validations-migration-guide/ +/ru/resources/migration-guides/assemblyscript-migration-guide/ +/ru/resources/migration-guides/graphql-validations-migration-guide/ /ru/resources/roles/curating/ /ru/resources/roles/delegating/delegating/ /ru/resources/roles/delegating/undelegating/ +/ru/resources/subgraph-studio-faq/ /ru/resources/tokenomics/ /ru/sps/introduction/ /ru/sps/sps-faq/ /ru/sps/triggers/ /ru/sps/tutorial/ +/ru/subgraphs/best-practices/avoid-eth-calls/ +/ru/subgraphs/best-practices/derivedfrom/ +/ru/subgraphs/best-practices/grafting-hotfix/ +/ru/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/ru/subgraphs/best-practices/pruning/ +/ru/subgraphs/best-practices/timeseries/ /ru/subgraphs/billing/ /ru/subgraphs/cookbook/arweave/ -/ru/subgraphs/cookbook/avoid-eth-calls/ -/ru/subgraphs/cookbook/cosmos/ -/ru/subgraphs/cookbook/derivedfrom/ /ru/subgraphs/cookbook/enums/ -/ru/subgraphs/cookbook/grafting-hotfix/ /ru/subgraphs/cookbook/grafting/ -/ru/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /ru/subgraphs/cookbook/near/ /ru/subgraphs/cookbook/polymarket/ -/ru/subgraphs/cookbook/pruning/ /ru/subgraphs/cookbook/secure-api-keys-nextjs/ /ru/subgraphs/cookbook/subgraph-debug-forking/ /ru/subgraphs/cookbook/subgraph-uncrashable/ -/ru/subgraphs/cookbook/timeseries/ /ru/subgraphs/cookbook/transfer-to-the-graph/ /ru/subgraphs/developing/creating/advanced/ /ru/subgraphs/developing/creating/assemblyscript-mappings/ @@ -1336,7 +1321,6 @@ /ru/subgraphs/developing/creating/subgraph-manifest/ /ru/subgraphs/developing/creating/unit-testing-framework/ /ru/subgraphs/developing/deploying/multiple-networks/ -/ru/subgraphs/developing/deploying/subgraph-studio-faq/ /ru/subgraphs/developing/deploying/using-subgraph-studio/ /ru/subgraphs/developing/developer-faq/ /ru/subgraphs/developing/introduction/ @@ -1358,7 +1342,7 @@ /ru/subgraphs/querying/subgraph-id-vs-deployment-id/ /ru/subgraphs/quick-start/ /ru/substreams/developing/dev-container/ -/ru/substreams/developing/sinks/sinks/ +/ru/substreams/developing/sinks/ /ru/substreams/developing/solana/account-changes/ /ru/substreams/developing/solana/transactions/ /ru/substreams/introduction/ @@ -1383,32 +1367,32 @@ /sv/indexing/tooling/graphcast/ /sv/resources/benefits/ /sv/resources/glossary/ -/sv/resources/release-notes/assemblyscript-migration-guide/ -/sv/resources/release-notes/graphql-validations-migration-guide/ +/sv/resources/migration-guides/assemblyscript-migration-guide/ +/sv/resources/migration-guides/graphql-validations-migration-guide/ /sv/resources/roles/curating/ /sv/resources/roles/delegating/delegating/ /sv/resources/roles/delegating/undelegating/ +/sv/resources/subgraph-studio-faq/ /sv/resources/tokenomics/ /sv/sps/introduction/ /sv/sps/sps-faq/ /sv/sps/triggers/ /sv/sps/tutorial/ +/sv/subgraphs/best-practices/avoid-eth-calls/ +/sv/subgraphs/best-practices/derivedfrom/ +/sv/subgraphs/best-practices/grafting-hotfix/ +/sv/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/sv/subgraphs/best-practices/pruning/ +/sv/subgraphs/best-practices/timeseries/ /sv/subgraphs/billing/ /sv/subgraphs/cookbook/arweave/ -/sv/subgraphs/cookbook/avoid-eth-calls/ -/sv/subgraphs/cookbook/cosmos/ -/sv/subgraphs/cookbook/derivedfrom/ /sv/subgraphs/cookbook/enums/ -/sv/subgraphs/cookbook/grafting-hotfix/ /sv/subgraphs/cookbook/grafting/ -/sv/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /sv/subgraphs/cookbook/near/ /sv/subgraphs/cookbook/polymarket/ -/sv/subgraphs/cookbook/pruning/ /sv/subgraphs/cookbook/secure-api-keys-nextjs/ /sv/subgraphs/cookbook/subgraph-debug-forking/ /sv/subgraphs/cookbook/subgraph-uncrashable/ -/sv/subgraphs/cookbook/timeseries/ /sv/subgraphs/cookbook/transfer-to-the-graph/ /sv/subgraphs/developing/creating/advanced/ /sv/subgraphs/developing/creating/assemblyscript-mappings/ @@ -1422,7 +1406,6 @@ /sv/subgraphs/developing/creating/subgraph-manifest/ /sv/subgraphs/developing/creating/unit-testing-framework/ /sv/subgraphs/developing/deploying/multiple-networks/ -/sv/subgraphs/developing/deploying/subgraph-studio-faq/ /sv/subgraphs/developing/deploying/using-subgraph-studio/ /sv/subgraphs/developing/developer-faq/ /sv/subgraphs/developing/introduction/ @@ -1444,7 +1427,7 @@ /sv/subgraphs/querying/subgraph-id-vs-deployment-id/ /sv/subgraphs/quick-start/ /sv/substreams/developing/dev-container/ -/sv/substreams/developing/sinks/sinks/ +/sv/substreams/developing/sinks/ /sv/substreams/developing/solana/account-changes/ /sv/substreams/developing/solana/transactions/ /sv/substreams/introduction/ @@ -1469,32 +1452,32 @@ /tr/indexing/tooling/graphcast/ /tr/resources/benefits/ /tr/resources/glossary/ -/tr/resources/release-notes/assemblyscript-migration-guide/ -/tr/resources/release-notes/graphql-validations-migration-guide/ +/tr/resources/migration-guides/assemblyscript-migration-guide/ +/tr/resources/migration-guides/graphql-validations-migration-guide/ /tr/resources/roles/curating/ /tr/resources/roles/delegating/delegating/ /tr/resources/roles/delegating/undelegating/ +/tr/resources/subgraph-studio-faq/ /tr/resources/tokenomics/ /tr/sps/introduction/ /tr/sps/sps-faq/ /tr/sps/triggers/ /tr/sps/tutorial/ +/tr/subgraphs/best-practices/avoid-eth-calls/ +/tr/subgraphs/best-practices/derivedfrom/ +/tr/subgraphs/best-practices/grafting-hotfix/ +/tr/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/tr/subgraphs/best-practices/pruning/ +/tr/subgraphs/best-practices/timeseries/ /tr/subgraphs/billing/ /tr/subgraphs/cookbook/arweave/ -/tr/subgraphs/cookbook/avoid-eth-calls/ -/tr/subgraphs/cookbook/cosmos/ -/tr/subgraphs/cookbook/derivedfrom/ /tr/subgraphs/cookbook/enums/ -/tr/subgraphs/cookbook/grafting-hotfix/ /tr/subgraphs/cookbook/grafting/ -/tr/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /tr/subgraphs/cookbook/near/ /tr/subgraphs/cookbook/polymarket/ -/tr/subgraphs/cookbook/pruning/ /tr/subgraphs/cookbook/secure-api-keys-nextjs/ /tr/subgraphs/cookbook/subgraph-debug-forking/ /tr/subgraphs/cookbook/subgraph-uncrashable/ -/tr/subgraphs/cookbook/timeseries/ /tr/subgraphs/cookbook/transfer-to-the-graph/ /tr/subgraphs/developing/creating/advanced/ /tr/subgraphs/developing/creating/assemblyscript-mappings/ @@ -1508,7 +1491,6 @@ /tr/subgraphs/developing/creating/subgraph-manifest/ /tr/subgraphs/developing/creating/unit-testing-framework/ /tr/subgraphs/developing/deploying/multiple-networks/ -/tr/subgraphs/developing/deploying/subgraph-studio-faq/ /tr/subgraphs/developing/deploying/using-subgraph-studio/ /tr/subgraphs/developing/developer-faq/ /tr/subgraphs/developing/introduction/ @@ -1530,7 +1512,7 @@ /tr/subgraphs/querying/subgraph-id-vs-deployment-id/ /tr/subgraphs/quick-start/ /tr/substreams/developing/dev-container/ -/tr/substreams/developing/sinks/sinks/ +/tr/substreams/developing/sinks/ /tr/substreams/developing/solana/account-changes/ /tr/substreams/developing/solana/transactions/ /tr/substreams/introduction/ @@ -1553,32 +1535,32 @@ /uk/indexing/tooling/graphcast/ /uk/resources/benefits/ /uk/resources/glossary/ -/uk/resources/release-notes/assemblyscript-migration-guide/ -/uk/resources/release-notes/graphql-validations-migration-guide/ +/uk/resources/migration-guides/assemblyscript-migration-guide/ +/uk/resources/migration-guides/graphql-validations-migration-guide/ /uk/resources/roles/curating/ /uk/resources/roles/delegating/delegating/ /uk/resources/roles/delegating/undelegating/ +/uk/resources/subgraph-studio-faq/ /uk/resources/tokenomics/ /uk/sps/introduction/ /uk/sps/sps-faq/ /uk/sps/triggers/ /uk/sps/tutorial/ +/uk/subgraphs/best-practices/avoid-eth-calls/ +/uk/subgraphs/best-practices/derivedfrom/ +/uk/subgraphs/best-practices/grafting-hotfix/ +/uk/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/uk/subgraphs/best-practices/pruning/ +/uk/subgraphs/best-practices/timeseries/ /uk/subgraphs/billing/ /uk/subgraphs/cookbook/arweave/ -/uk/subgraphs/cookbook/avoid-eth-calls/ -/uk/subgraphs/cookbook/cosmos/ -/uk/subgraphs/cookbook/derivedfrom/ /uk/subgraphs/cookbook/enums/ -/uk/subgraphs/cookbook/grafting-hotfix/ /uk/subgraphs/cookbook/grafting/ -/uk/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /uk/subgraphs/cookbook/near/ /uk/subgraphs/cookbook/polymarket/ -/uk/subgraphs/cookbook/pruning/ /uk/subgraphs/cookbook/secure-api-keys-nextjs/ /uk/subgraphs/cookbook/subgraph-debug-forking/ /uk/subgraphs/cookbook/subgraph-uncrashable/ -/uk/subgraphs/cookbook/timeseries/ /uk/subgraphs/cookbook/transfer-to-the-graph/ /uk/subgraphs/developing/creating/advanced/ /uk/subgraphs/developing/creating/assemblyscript-mappings/ @@ -1592,7 +1574,6 @@ /uk/subgraphs/developing/creating/subgraph-manifest/ /uk/subgraphs/developing/creating/unit-testing-framework/ /uk/subgraphs/developing/deploying/multiple-networks/ -/uk/subgraphs/developing/deploying/subgraph-studio-faq/ /uk/subgraphs/developing/deploying/using-subgraph-studio/ /uk/subgraphs/developing/developer-faq/ /uk/subgraphs/developing/introduction/ @@ -1614,7 +1595,7 @@ /uk/subgraphs/querying/subgraph-id-vs-deployment-id/ /uk/subgraphs/quick-start/ /uk/substreams/developing/dev-container/ -/uk/substreams/developing/sinks/sinks/ +/uk/substreams/developing/sinks/ /uk/substreams/developing/solana/account-changes/ /uk/substreams/developing/solana/transactions/ /uk/substreams/introduction/ @@ -1639,32 +1620,32 @@ /ur/indexing/tooling/graphcast/ /ur/resources/benefits/ /ur/resources/glossary/ -/ur/resources/release-notes/assemblyscript-migration-guide/ -/ur/resources/release-notes/graphql-validations-migration-guide/ +/ur/resources/migration-guides/assemblyscript-migration-guide/ +/ur/resources/migration-guides/graphql-validations-migration-guide/ /ur/resources/roles/curating/ /ur/resources/roles/delegating/delegating/ /ur/resources/roles/delegating/undelegating/ +/ur/resources/subgraph-studio-faq/ /ur/resources/tokenomics/ /ur/sps/introduction/ /ur/sps/sps-faq/ /ur/sps/triggers/ /ur/sps/tutorial/ +/ur/subgraphs/best-practices/avoid-eth-calls/ +/ur/subgraphs/best-practices/derivedfrom/ +/ur/subgraphs/best-practices/grafting-hotfix/ +/ur/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/ur/subgraphs/best-practices/pruning/ +/ur/subgraphs/best-practices/timeseries/ /ur/subgraphs/billing/ /ur/subgraphs/cookbook/arweave/ -/ur/subgraphs/cookbook/avoid-eth-calls/ -/ur/subgraphs/cookbook/cosmos/ -/ur/subgraphs/cookbook/derivedfrom/ /ur/subgraphs/cookbook/enums/ -/ur/subgraphs/cookbook/grafting-hotfix/ /ur/subgraphs/cookbook/grafting/ -/ur/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /ur/subgraphs/cookbook/near/ /ur/subgraphs/cookbook/polymarket/ -/ur/subgraphs/cookbook/pruning/ /ur/subgraphs/cookbook/secure-api-keys-nextjs/ /ur/subgraphs/cookbook/subgraph-debug-forking/ /ur/subgraphs/cookbook/subgraph-uncrashable/ -/ur/subgraphs/cookbook/timeseries/ /ur/subgraphs/cookbook/transfer-to-the-graph/ /ur/subgraphs/developing/creating/advanced/ /ur/subgraphs/developing/creating/assemblyscript-mappings/ @@ -1678,7 +1659,6 @@ /ur/subgraphs/developing/creating/subgraph-manifest/ /ur/subgraphs/developing/creating/unit-testing-framework/ /ur/subgraphs/developing/deploying/multiple-networks/ -/ur/subgraphs/developing/deploying/subgraph-studio-faq/ /ur/subgraphs/developing/deploying/using-subgraph-studio/ /ur/subgraphs/developing/developer-faq/ /ur/subgraphs/developing/introduction/ @@ -1700,7 +1680,7 @@ /ur/subgraphs/querying/subgraph-id-vs-deployment-id/ /ur/subgraphs/quick-start/ /ur/substreams/developing/dev-container/ -/ur/substreams/developing/sinks/sinks/ +/ur/substreams/developing/sinks/ /ur/substreams/developing/solana/account-changes/ /ur/substreams/developing/solana/transactions/ /ur/substreams/introduction/ @@ -1723,32 +1703,32 @@ /vi/indexing/tooling/graphcast/ /vi/resources/benefits/ /vi/resources/glossary/ -/vi/resources/release-notes/assemblyscript-migration-guide/ -/vi/resources/release-notes/graphql-validations-migration-guide/ +/vi/resources/migration-guides/assemblyscript-migration-guide/ +/vi/resources/migration-guides/graphql-validations-migration-guide/ /vi/resources/roles/curating/ /vi/resources/roles/delegating/delegating/ /vi/resources/roles/delegating/undelegating/ +/vi/resources/subgraph-studio-faq/ /vi/resources/tokenomics/ /vi/sps/introduction/ /vi/sps/sps-faq/ /vi/sps/triggers/ /vi/sps/tutorial/ +/vi/subgraphs/best-practices/avoid-eth-calls/ +/vi/subgraphs/best-practices/derivedfrom/ +/vi/subgraphs/best-practices/grafting-hotfix/ +/vi/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/vi/subgraphs/best-practices/pruning/ +/vi/subgraphs/best-practices/timeseries/ /vi/subgraphs/billing/ /vi/subgraphs/cookbook/arweave/ -/vi/subgraphs/cookbook/avoid-eth-calls/ -/vi/subgraphs/cookbook/cosmos/ -/vi/subgraphs/cookbook/derivedfrom/ /vi/subgraphs/cookbook/enums/ -/vi/subgraphs/cookbook/grafting-hotfix/ /vi/subgraphs/cookbook/grafting/ -/vi/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /vi/subgraphs/cookbook/near/ /vi/subgraphs/cookbook/polymarket/ -/vi/subgraphs/cookbook/pruning/ /vi/subgraphs/cookbook/secure-api-keys-nextjs/ /vi/subgraphs/cookbook/subgraph-debug-forking/ /vi/subgraphs/cookbook/subgraph-uncrashable/ -/vi/subgraphs/cookbook/timeseries/ /vi/subgraphs/cookbook/transfer-to-the-graph/ /vi/subgraphs/developing/creating/advanced/ /vi/subgraphs/developing/creating/assemblyscript-mappings/ @@ -1762,7 +1742,6 @@ /vi/subgraphs/developing/creating/subgraph-manifest/ /vi/subgraphs/developing/creating/unit-testing-framework/ /vi/subgraphs/developing/deploying/multiple-networks/ -/vi/subgraphs/developing/deploying/subgraph-studio-faq/ /vi/subgraphs/developing/deploying/using-subgraph-studio/ /vi/subgraphs/developing/developer-faq/ /vi/subgraphs/developing/introduction/ @@ -1784,7 +1763,7 @@ /vi/subgraphs/querying/subgraph-id-vs-deployment-id/ /vi/subgraphs/quick-start/ /vi/substreams/developing/dev-container/ -/vi/substreams/developing/sinks/sinks/ +/vi/substreams/developing/sinks/ /vi/substreams/developing/solana/account-changes/ /vi/substreams/developing/solana/transactions/ /vi/substreams/introduction/ @@ -1809,32 +1788,32 @@ /zh/indexing/tooling/graphcast/ /zh/resources/benefits/ /zh/resources/glossary/ -/zh/resources/release-notes/assemblyscript-migration-guide/ -/zh/resources/release-notes/graphql-validations-migration-guide/ +/zh/resources/migration-guides/assemblyscript-migration-guide/ +/zh/resources/migration-guides/graphql-validations-migration-guide/ /zh/resources/roles/curating/ /zh/resources/roles/delegating/delegating/ /zh/resources/roles/delegating/undelegating/ +/zh/resources/subgraph-studio-faq/ /zh/resources/tokenomics/ /zh/sps/introduction/ /zh/sps/sps-faq/ /zh/sps/triggers/ /zh/sps/tutorial/ +/zh/subgraphs/best-practices/avoid-eth-calls/ +/zh/subgraphs/best-practices/derivedfrom/ +/zh/subgraphs/best-practices/grafting-hotfix/ +/zh/subgraphs/best-practices/immutable-entities-bytes-as-ids/ +/zh/subgraphs/best-practices/pruning/ +/zh/subgraphs/best-practices/timeseries/ /zh/subgraphs/billing/ /zh/subgraphs/cookbook/arweave/ -/zh/subgraphs/cookbook/avoid-eth-calls/ -/zh/subgraphs/cookbook/cosmos/ -/zh/subgraphs/cookbook/derivedfrom/ /zh/subgraphs/cookbook/enums/ -/zh/subgraphs/cookbook/grafting-hotfix/ /zh/subgraphs/cookbook/grafting/ -/zh/subgraphs/cookbook/immutable-entities-bytes-as-ids/ /zh/subgraphs/cookbook/near/ /zh/subgraphs/cookbook/polymarket/ -/zh/subgraphs/cookbook/pruning/ /zh/subgraphs/cookbook/secure-api-keys-nextjs/ /zh/subgraphs/cookbook/subgraph-debug-forking/ /zh/subgraphs/cookbook/subgraph-uncrashable/ -/zh/subgraphs/cookbook/timeseries/ /zh/subgraphs/cookbook/transfer-to-the-graph/ /zh/subgraphs/developing/creating/advanced/ /zh/subgraphs/developing/creating/assemblyscript-mappings/ @@ -1848,7 +1827,6 @@ /zh/subgraphs/developing/creating/subgraph-manifest/ /zh/subgraphs/developing/creating/unit-testing-framework/ /zh/subgraphs/developing/deploying/multiple-networks/ -/zh/subgraphs/developing/deploying/subgraph-studio-faq/ /zh/subgraphs/developing/deploying/using-subgraph-studio/ /zh/subgraphs/developing/developer-faq/ /zh/subgraphs/developing/introduction/ @@ -1870,7 +1848,7 @@ /zh/subgraphs/querying/subgraph-id-vs-deployment-id/ /zh/subgraphs/quick-start/ /zh/substreams/developing/dev-container/ -/zh/substreams/developing/sinks/sinks/ +/zh/substreams/developing/sinks/ /zh/substreams/developing/solana/account-changes/ /zh/substreams/developing/solana/transactions/ /zh/substreams/introduction/ diff --git a/website/src/Layout.tsx b/website/src/Layout.tsx index 029d8c9c9583..618db31baffd 100644 --- a/website/src/Layout.tsx +++ b/website/src/Layout.tsx @@ -318,7 +318,7 @@ export default function Layout({ pageOpts, children }: NextraThemeLayoutProps [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Even though all data can be accessed with a block handler, other handlers enable subgraph developers to process data in a much more granular way. - -## Building a Cosmos subgraph - -### Subgraph Dependencies - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Subgraph Main Components - -There are three key parts when it comes to defining a subgraph: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### تعريف Subgraph Manifest - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### تعريف المخطط - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript Mappings - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Each handler type comes with its own data structure that is passed as an argument to a mapping function. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Message decoding - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Creating and building a Cosmos subgraph - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Deploying a Cosmos subgraph - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Querying a Cosmos subgraph - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Supported Cosmos Blockchains - -### Cosmos Hub - -#### What is Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### الشبكات - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### What is Osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### الشبكات - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## أمثلة على الـ Subgraphs - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/ar/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/ar/subgraphs/developing/creating/graph-ts/api.mdx index 88b1af6c6c88..8245a637cc8a 100644 --- a/website/src/pages/ar/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/ar/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/ar/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/ar/subgraphs/developing/creating/install-the-cli.mdx index 76c1d923b417..b55d24367e50 100644 --- a/website/src/pages/ar/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/ar/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: قم بتثبيت Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## نظره عامة diff --git a/website/src/pages/ar/subgraphs/developing/deploying/_meta.js b/website/src/pages/ar/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/ar/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/ar/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/ar/subgraphs/querying/best-practices.mdx b/website/src/pages/ar/subgraphs/querying/best-practices.mdx index ba7439d7752d..23dcd2cb8920 100644 --- a/website/src/pages/ar/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/ar/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### إرسال استعلام إلى GraphQL API diff --git a/website/src/pages/ar/subgraphs/querying/managing-api-keys.mdx b/website/src/pages/ar/subgraphs/querying/managing-api-keys.mdx index f23017bf015e..33e9d7b78fc2 100644 --- a/website/src/pages/ar/subgraphs/querying/managing-api-keys.mdx +++ b/website/src/pages/ar/subgraphs/querying/managing-api-keys.mdx @@ -1,5 +1,5 @@ --- -title: Managing your API keys +title: Managing API keys --- ## نظره عامة diff --git a/website/src/pages/ar/substreams/developing/sinks/sinks.mdx b/website/src/pages/ar/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/ar/substreams/developing/sinks/sinks.mdx rename to website/src/pages/ar/substreams/developing/sinks.mdx diff --git a/website/src/pages/ar/substreams/developing/sinks/_meta.js b/website/src/pages/ar/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/ar/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/ar/substreams/quick-start.mdx b/website/src/pages/ar/substreams/quick-start.mdx index da261def34e2..7428d67bf4ff 100644 --- a/website/src/pages/ar/substreams/quick-start.mdx +++ b/website/src/pages/ar/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/cs/resources/_meta-titles.json b/website/src/pages/cs/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/cs/resources/_meta-titles.json +++ b/website/src/pages/cs/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/cs/resources/_meta.js b/website/src/pages/cs/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/cs/resources/_meta.js +++ b/website/src/pages/cs/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/cs/resources/release-notes/_meta.js b/website/src/pages/cs/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/cs/resources/release-notes/_meta.js rename to website/src/pages/cs/resources/migration-guides/_meta.js diff --git a/website/src/pages/cs/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/cs/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/cs/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/cs/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/cs/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/cs/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 100% rename from website/src/pages/cs/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/cs/resources/migration-guides/graphql-validations-migration-guide.mdx diff --git a/website/src/pages/cs/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/cs/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/cs/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/cs/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/cs/sps/sps-faq.mdx b/website/src/pages/cs/sps/sps-faq.mdx index 7fc44c405709..657b027cf5e9 100644 --- a/website/src/pages/cs/sps/sps-faq.mdx +++ b/website/src/pages/cs/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/cs/subgraphs/_meta-titles.json b/website/src/pages/cs/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/cs/subgraphs/_meta-titles.json +++ b/website/src/pages/cs/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/cs/subgraphs/_meta.js b/website/src/pages/cs/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/cs/subgraphs/_meta.js +++ b/website/src/pages/cs/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/cs/subgraphs/best-practices/_meta.js b/website/src/pages/cs/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/cs/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/cs/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/cs/subgraphs/best-practices/avoid-eth-calls.mdx similarity index 93% rename from website/src/pages/cs/subgraphs/cookbook/avoid-eth-calls.mdx rename to website/src/pages/cs/subgraphs/best-practices/avoid-eth-calls.mdx index a37d4b271dc1..3ce9c29a17a0 100644 --- a/website/src/pages/cs/subgraphs/cookbook/avoid-eth-calls.mdx +++ b/website/src/pages/cs/subgraphs/best-practices/avoid-eth-calls.mdx @@ -104,14 +104,14 @@ You can significantly improve indexing performance by minimizing or eliminating ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/cs/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/cs/subgraphs/best-practices/derivedfrom.mdx similarity index 88% rename from website/src/pages/cs/subgraphs/cookbook/derivedfrom.mdx rename to website/src/pages/cs/subgraphs/best-practices/derivedfrom.mdx index 61e2c2c040f4..f6ec5a660bf2 100644 --- a/website/src/pages/cs/subgraphs/cookbook/derivedfrom.mdx +++ b/website/src/pages/cs/subgraphs/best-practices/derivedfrom.mdx @@ -76,14 +76,14 @@ For a more detailed explanation of strategies to avoid large arrays, check out K ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/cs/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/cs/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/cs/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/cs/subgraphs/best-practices/grafting-hotfix.mdx index 08ba054d4fcc..7a2dbdda86f6 100644 --- a/website/src/pages/cs/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/cs/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/cs/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/cs/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx similarity index 93% rename from website/src/pages/cs/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx rename to website/src/pages/cs/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx index 1053454b9642..5b058ee9d7cf 100644 --- a/website/src/pages/cs/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ b/website/src/pages/cs/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -178,14 +178,14 @@ Více informací o používání nezměnitelných entit a bytů jako ID najdete ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/cs/subgraphs/cookbook/pruning.mdx b/website/src/pages/cs/subgraphs/best-practices/pruning.mdx similarity index 86% rename from website/src/pages/cs/subgraphs/cookbook/pruning.mdx rename to website/src/pages/cs/subgraphs/best-practices/pruning.mdx index 551c6d69b391..e6b23f71c409 100644 --- a/website/src/pages/cs/subgraphs/cookbook/pruning.mdx +++ b/website/src/pages/cs/subgraphs/best-practices/pruning.mdx @@ -43,14 +43,14 @@ Ořezávání pomocí `indexerHints` je osvědčeným postupem pro vývoj podgra ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/cs/subgraphs/cookbook/timeseries.mdx b/website/src/pages/cs/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/cs/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/cs/subgraphs/best-practices/timeseries.mdx index 4355c82716ef..f35ab0913563 100644 --- a/website/src/pages/cs/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/cs/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/cs/subgraphs/cookbook/_meta.js b/website/src/pages/cs/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/cs/subgraphs/cookbook/_meta.js +++ b/website/src/pages/cs/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/cs/subgraphs/cookbook/cosmos.mdx b/website/src/pages/cs/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 0274cc6b5370..000000000000 --- a/website/src/pages/cs/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Vytváření podgrafů v Cosmos ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## Co jsou podgrafy Cosmos? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -V podgrafech Cosmos jsou podporovány čtyři typy ovladačů: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Přestože ke všem datům lze přistupovat pomocí blokové obsluhy, jiné obsluhy umožňují vývojářům podgrafů zpracovávat data mnohem podrobnějším způsobem. - -## Sestavení podgrafu Cosmos - -### Závislosti podgrafů - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Hlavní součásti subgrafu - -Při definování podgrafu existují tři klíčové části: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### Definice podgrafu Manifest - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### Definice schématu - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript Mapování - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Každý typ obslužné rutiny má svou vlastní datovou strukturu, která se předává jako argument mapovací funkci. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Dekódování zpráv - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Vytvoření a sestavení podgrafu Cosmos - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Nasazení podgrafu Cosmos - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Navštivte Studio podgrafů a vytvořte nový podgraf. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Dotazování podgrafu Cosmos - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Podporované blockchainy Cosmos - -### Cosmos Hub - -#### Co je Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### Sítě - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Podpora Osmosis v uzel grafua v Podgraph Studio je ve fázi beta: s případnými dotazy ohledně vytváření podgrafů Osmosis se obraťte na grafový tým! - -#### Co je osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### Sítě - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## Příklady podgrafů - -Zde je několik příkladů podgrafů: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/cs/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/cs/subgraphs/developing/creating/graph-ts/api.mdx index 33a53bdd2e68..3c3dbdc7671f 100644 --- a/website/src/pages/cs/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/cs/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ Knihovna `@graphprotocol/graph-ts` poskytuje následující API: | 0.0.8 | Přidá ověření existence polí ve schéma při ukládání entity. | | 0.0.7 | Přidání tříd `TransactionReceipt` a `Log` do typů Ethereum
Přidání pole `receipt` do objektu Ethereum událost | | 0.0.6 | Přidáno pole `nonce` do objektu Ethereum Transaction
Přidáno `baseFeePerGas` do objektu Ethereum bloku | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Přidání pole `functionSignature` do objektu Ethereum SmartContractCall | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Přidání pole `input` do objektu Ethereum Transackce | diff --git a/website/src/pages/cs/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/cs/subgraphs/developing/creating/install-the-cli.mdx index 913017bb3632..dbeac0c137a5 100644 --- a/website/src/pages/cs/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/cs/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Instalace Graf CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Přehled diff --git a/website/src/pages/cs/subgraphs/developing/deploying/_meta.js b/website/src/pages/cs/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/cs/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/cs/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/cs/subgraphs/querying/best-practices.mdx b/website/src/pages/cs/subgraphs/querying/best-practices.mdx index 114ca91306f9..a28d505b9b46 100644 --- a/website/src/pages/cs/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/cs/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Odeslání dotazu na GraphQL API diff --git a/website/src/pages/cs/substreams/developing/sinks/sinks.mdx b/website/src/pages/cs/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/cs/substreams/developing/sinks/sinks.mdx rename to website/src/pages/cs/substreams/developing/sinks.mdx diff --git a/website/src/pages/cs/substreams/developing/sinks/_meta.js b/website/src/pages/cs/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/cs/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/cs/substreams/quick-start.mdx b/website/src/pages/cs/substreams/quick-start.mdx index f10848316ff6..50a16d470cfe 100644 --- a/website/src/pages/cs/substreams/quick-start.mdx +++ b/website/src/pages/cs/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/de/resources/_meta-titles.json b/website/src/pages/de/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/de/resources/_meta-titles.json +++ b/website/src/pages/de/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/de/resources/_meta.js b/website/src/pages/de/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/de/resources/_meta.js +++ b/website/src/pages/de/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/de/resources/release-notes/_meta.js b/website/src/pages/de/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/de/resources/release-notes/_meta.js rename to website/src/pages/de/resources/migration-guides/_meta.js diff --git a/website/src/pages/de/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/de/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/de/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/de/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/de/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/de/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 99% rename from website/src/pages/de/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/de/resources/migration-guides/graphql-validations-migration-guide.mdx index 31788f43b53c..68c70b711a60 100644 --- a/website/src/pages/de/resources/release-notes/graphql-validations-migration-guide.mdx +++ b/website/src/pages/de/resources/migration-guides/graphql-validations-migration-guide.mdx @@ -1,5 +1,5 @@ --- -title: GraphQL Validations migration guide +title: GraphQL Validations Migration Guide --- Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). diff --git a/website/src/pages/de/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/de/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/de/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/de/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/de/sps/sps-faq.mdx b/website/src/pages/de/sps/sps-faq.mdx index d325908a4bb3..72005f6cfc09 100644 --- a/website/src/pages/de/sps/sps-faq.mdx +++ b/website/src/pages/de/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/de/subgraphs/_meta-titles.json b/website/src/pages/de/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/de/subgraphs/_meta-titles.json +++ b/website/src/pages/de/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/de/subgraphs/_meta.js b/website/src/pages/de/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/de/subgraphs/_meta.js +++ b/website/src/pages/de/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/de/subgraphs/best-practices/_meta.js b/website/src/pages/de/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/de/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/ar/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/de/subgraphs/best-practices/avoid-eth-calls.mdx similarity index 93% rename from website/src/pages/ar/subgraphs/cookbook/avoid-eth-calls.mdx rename to website/src/pages/de/subgraphs/best-practices/avoid-eth-calls.mdx index ae29cdf03a34..e40a7b3712e4 100644 --- a/website/src/pages/ar/subgraphs/cookbook/avoid-eth-calls.mdx +++ b/website/src/pages/de/subgraphs/best-practices/avoid-eth-calls.mdx @@ -104,14 +104,14 @@ You can significantly improve indexing performance by minimizing or eliminating ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/es/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/de/subgraphs/best-practices/derivedfrom.mdx similarity index 88% rename from website/src/pages/es/subgraphs/cookbook/derivedfrom.mdx rename to website/src/pages/de/subgraphs/best-practices/derivedfrom.mdx index a0942645c999..db3a49928c89 100644 --- a/website/src/pages/es/subgraphs/cookbook/derivedfrom.mdx +++ b/website/src/pages/de/subgraphs/best-practices/derivedfrom.mdx @@ -76,14 +76,14 @@ For a more detailed explanation of strategies to avoid large arrays, check out K ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/de/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/de/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/de/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/de/subgraphs/best-practices/grafting-hotfix.mdx index 71e9b7c52833..f0297328b52d 100644 --- a/website/src/pages/de/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/de/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/es/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/de/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx similarity index 92% rename from website/src/pages/es/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx rename to website/src/pages/de/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx index 511565bb3dd4..6ff60ec9ab34 100644 --- a/website/src/pages/es/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ b/website/src/pages/de/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -178,14 +178,14 @@ Read more about using Immutable Entities and Bytes as IDs in this blog post by D ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/es/subgraphs/cookbook/pruning.mdx b/website/src/pages/de/subgraphs/best-practices/pruning.mdx similarity index 86% rename from website/src/pages/es/subgraphs/cookbook/pruning.mdx rename to website/src/pages/de/subgraphs/best-practices/pruning.mdx index e212d5d02bc9..1b51dde8894f 100644 --- a/website/src/pages/es/subgraphs/cookbook/pruning.mdx +++ b/website/src/pages/de/subgraphs/best-practices/pruning.mdx @@ -43,14 +43,14 @@ Pruning using `indexerHints` is a best practice for subgraph development, offeri ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/de/subgraphs/cookbook/timeseries.mdx b/website/src/pages/de/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/de/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/de/subgraphs/best-practices/timeseries.mdx index 8e8300865da3..060540f991bf 100644 --- a/website/src/pages/de/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/de/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/de/subgraphs/cookbook/_meta.js b/website/src/pages/de/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/de/subgraphs/cookbook/_meta.js +++ b/website/src/pages/de/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/de/subgraphs/cookbook/cosmos.mdx b/website/src/pages/de/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index d2c95ef10f58..000000000000 --- a/website/src/pages/de/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Erstellen von Subgrafen auf Cosmos ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## Was sind Cosmos-Subgrafen? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -In Cosmos-Subgrafen werden vier Arten von Handlern unterstützt: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Obwohl man mit einem Block-Handler auf alle Daten zugegriffen werden kann, ermöglichen andere Handler den Subgrafen-Entwicklern, Daten viel detaillierter zu verarbeiten. - -## Erstellen eines Subgrafen auf Cosmos - -### Subgraf-Abhängigkeiten - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Hauptkomponenten des Subgrafen - -Bei der Definition eines Subgrafen gibt es drei Schlüsselelemente: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### Subgraf-Manifest-Definition - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # Link zur Schemadatei -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # Dies wird sich für jede kosmosbasierte Blockchain ändern. In diesem Fall verwendet das Beispiel das Cosmos Hub-Mainnet. - source: - startBlock: 0 # Erforderlich für Cosmos, setzen Sie dies auf 0, um die Indizierung ab dem Chain-Genesis zu starten - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # der Funktionsname in der Zuordnungsdatei - eventHandlers: - - event: rewards # die Art des Ereignisses, das behandelt wird - handler: handleReward # der Funktionsname in der Zuordnungsdatei - transactionHandlers: - - handler: handleTransaction # der Funktionsname in der Zuordnungsdatei - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # die Art einer Meldung - handler: handleMsgDelegate # der Funktionsname in der Zuordnungsdatei - file: ./src/mapping.ts # Link zur Datei mit den Assemblyscript-Zuordnungen -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### Schema-Definition - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript-Mappings - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Jeder Handler-Typ verfügt über eine eigene Datenstruktur, die als Argument an eine Zuordnungsfunktion übergeben wird. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Nachrichtendecodierung - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Creating and building a Cosmos subgraph - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Bereitstellen eines Subgrafen auf Cosmos - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Querying a Cosmos subgraph - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Unterstützte Cosmos-Blockchains - -### Cosmos Hub - -#### Was ist Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### Netzwerke - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### What is Osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### Netzwerke - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## Beispiele von Subgrafen - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/de/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/de/subgraphs/developing/creating/graph-ts/api.mdx index 0afac2648574..6106b8cdf0dc 100644 --- a/website/src/pages/de/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/de/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/de/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/de/subgraphs/developing/creating/install-the-cli.mdx index 9049bce0ce9d..f9d419ffe1ce 100644 --- a/website/src/pages/de/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/de/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Install the Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Überblick diff --git a/website/src/pages/de/subgraphs/developing/deploying/_meta.js b/website/src/pages/de/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/de/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/de/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/de/subgraphs/querying/best-practices.mdx b/website/src/pages/de/subgraphs/querying/best-practices.mdx index 3736fa32faeb..ff5f381e2993 100644 --- a/website/src/pages/de/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/de/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Sending a query to a GraphQL API diff --git a/website/src/pages/de/subgraphs/querying/managing-api-keys.mdx b/website/src/pages/de/subgraphs/querying/managing-api-keys.mdx index 2a4d92726084..45ead286cf8a 100644 --- a/website/src/pages/de/subgraphs/querying/managing-api-keys.mdx +++ b/website/src/pages/de/subgraphs/querying/managing-api-keys.mdx @@ -1,5 +1,5 @@ --- -title: Managing your API keys +title: Managing API keys --- ## Überblick diff --git a/website/src/pages/de/substreams/developing/sinks/sinks.mdx b/website/src/pages/de/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/de/substreams/developing/sinks/sinks.mdx rename to website/src/pages/de/substreams/developing/sinks.mdx diff --git a/website/src/pages/de/substreams/developing/sinks/_meta.js b/website/src/pages/de/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/de/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/de/substreams/quick-start.mdx b/website/src/pages/de/substreams/quick-start.mdx index 088c39022eb0..cd29be60d2f9 100644 --- a/website/src/pages/de/substreams/quick-start.mdx +++ b/website/src/pages/de/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/en/resources/_meta-titles.json b/website/src/pages/en/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/en/resources/_meta-titles.json +++ b/website/src/pages/en/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/en/resources/_meta.js b/website/src/pages/en/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/en/resources/_meta.js +++ b/website/src/pages/en/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/en/resources/release-notes/_meta.js b/website/src/pages/en/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/en/resources/release-notes/_meta.js rename to website/src/pages/en/resources/migration-guides/_meta.js diff --git a/website/src/pages/en/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/en/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/en/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/en/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/nl/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/en/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 99% rename from website/src/pages/nl/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/en/resources/migration-guides/graphql-validations-migration-guide.mdx index 4d909e8970a8..29fed533ef8c 100644 --- a/website/src/pages/nl/resources/release-notes/graphql-validations-migration-guide.mdx +++ b/website/src/pages/en/resources/migration-guides/graphql-validations-migration-guide.mdx @@ -1,5 +1,5 @@ --- -title: GraphQL Validations migration guide +title: GraphQL Validations Migration Guide --- Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). diff --git a/website/src/pages/en/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/en/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/en/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/en/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/en/sps/sps-faq.mdx b/website/src/pages/en/sps/sps-faq.mdx index 537f29b09ea6..abc1f3906686 100644 --- a/website/src/pages/en/sps/sps-faq.mdx +++ b/website/src/pages/en/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/en/subgraphs/_meta-titles.json b/website/src/pages/en/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/en/subgraphs/_meta-titles.json +++ b/website/src/pages/en/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/en/subgraphs/_meta.js b/website/src/pages/en/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/en/subgraphs/_meta.js +++ b/website/src/pages/en/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/en/subgraphs/best-practices/_meta.js b/website/src/pages/en/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/en/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/en/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/en/subgraphs/best-practices/avoid-eth-calls.mdx similarity index 93% rename from website/src/pages/en/subgraphs/cookbook/avoid-eth-calls.mdx rename to website/src/pages/en/subgraphs/best-practices/avoid-eth-calls.mdx index 4b24fafac947..1d4178f234d2 100644 --- a/website/src/pages/en/subgraphs/cookbook/avoid-eth-calls.mdx +++ b/website/src/pages/en/subgraphs/best-practices/avoid-eth-calls.mdx @@ -1,6 +1,6 @@ --- title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls -sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' +sidebarTitle: 'Avoiding eth_calls' --- ## TLDR @@ -104,14 +104,14 @@ You can significantly improve indexing performance by minimizing or eliminating ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/en/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/en/subgraphs/best-practices/derivedfrom.mdx similarity index 88% rename from website/src/pages/en/subgraphs/cookbook/derivedfrom.mdx rename to website/src/pages/en/subgraphs/best-practices/derivedfrom.mdx index 344c906ffe55..7b0bb1f712fe 100644 --- a/website/src/pages/en/subgraphs/cookbook/derivedfrom.mdx +++ b/website/src/pages/en/subgraphs/best-practices/derivedfrom.mdx @@ -1,6 +1,6 @@ --- title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom -sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' +sidebarTitle: 'Arrays with @derivedFrom' --- ## TLDR @@ -75,14 +75,14 @@ For a more detailed explanation of strategies to avoid large arrays, check out K ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/en/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/en/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/en/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/en/subgraphs/best-practices/grafting-hotfix.mdx index ae41a5ce20ba..3991197e7379 100644 --- a/website/src/pages/en/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/en/subgraphs/best-practices/grafting-hotfix.mdx @@ -1,6 +1,6 @@ --- title: Subgraph Best Practice 6 - Use Grafting for Quick Hotfix Deployment -sidebarTitle: 'Subgraph Best Practice 6: Grafting and Hotfixing' +sidebarTitle: 'Grafting and Hotfixing' --- ## TLDR @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/en/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/en/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx similarity index 92% rename from website/src/pages/en/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx rename to website/src/pages/en/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx index 067f26ffacf7..042d904b6ef0 100644 --- a/website/src/pages/en/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ b/website/src/pages/en/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -1,6 +1,6 @@ --- title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs -sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' +sidebarTitle: 'Immutable Entities and Bytes as IDs' --- ## TLDR @@ -178,14 +178,14 @@ Read more about using Immutable Entities and Bytes as IDs in this blog post by D ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/en/subgraphs/cookbook/pruning.mdx b/website/src/pages/en/subgraphs/best-practices/pruning.mdx similarity index 86% rename from website/src/pages/en/subgraphs/cookbook/pruning.mdx rename to website/src/pages/en/subgraphs/best-practices/pruning.mdx index b620e504ab86..85fc9cc61baa 100644 --- a/website/src/pages/en/subgraphs/cookbook/pruning.mdx +++ b/website/src/pages/en/subgraphs/best-practices/pruning.mdx @@ -1,6 +1,6 @@ --- title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning -sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' +sidebarTitle: 'Pruning with indexerHints' --- ## TLDR @@ -43,14 +43,14 @@ Pruning using `indexerHints` is a best practice for subgraph development, offeri ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/en/subgraphs/cookbook/timeseries.mdx b/website/src/pages/en/subgraphs/best-practices/timeseries.mdx similarity index 94% rename from website/src/pages/en/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/en/subgraphs/best-practices/timeseries.mdx index ea6040d1931d..756e0ff78b8e 100644 --- a/website/src/pages/en/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/en/subgraphs/best-practices/timeseries.mdx @@ -1,6 +1,6 @@ --- title: Subgraph Best Practice 5 - Simplify and Optimize with Timeseries and Aggregations -sidebarTitle: 'Subgraph Best Practice 5: Timeseries and Aggregations' +sidebarTitle: 'Timeseries and Aggregations' --- ## TLDR @@ -186,14 +186,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/en/subgraphs/cookbook/_meta.js b/website/src/pages/en/subgraphs/cookbook/_meta.js index fcce9a6b07bf..e642f12ef11d 100644 --- a/website/src/pages/en/subgraphs/cookbook/_meta.js +++ b/website/src/pages/en/subgraphs/cookbook/_meta.js @@ -5,12 +5,6 @@ export default { grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/en/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/en/subgraphs/developing/creating/graph-ts/api.mdx index 2e22f85a18c0..d9099127799c 100644 --- a/website/src/pages/en/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/en/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/en/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/en/subgraphs/developing/creating/install-the-cli.mdx index a58e6be82324..674cc5bc22d2 100644 --- a/website/src/pages/en/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/en/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Install the Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Overview diff --git a/website/src/pages/en/subgraphs/developing/deploying/_meta.js b/website/src/pages/en/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/en/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/en/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/en/subgraphs/developing/deploying/multiple-networks.mdx b/website/src/pages/en/subgraphs/developing/deploying/multiple-networks.mdx index 4f7dcd3864e8..1c324352d372 100644 --- a/website/src/pages/en/subgraphs/developing/deploying/multiple-networks.mdx +++ b/website/src/pages/en/subgraphs/developing/deploying/multiple-networks.mdx @@ -1,5 +1,6 @@ --- title: Deploying a Subgraph to Multiple Networks +sidebarTitle: Deploying to Multiple Networks --- This page explains how to deploy a subgraph to multiple networks. To deploy a subgraph you need to first install the [Graph CLI](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli). If you have not created a subgraph already, see [Creating a subgraph](/developing/creating-a-subgraph/). diff --git a/website/src/pages/en/subgraphs/developing/publishing/publishing-a-subgraph.mdx b/website/src/pages/en/subgraphs/developing/publishing/publishing-a-subgraph.mdx index 443a91217bc2..32ed9b96d5f3 100644 --- a/website/src/pages/en/subgraphs/developing/publishing/publishing-a-subgraph.mdx +++ b/website/src/pages/en/subgraphs/developing/publishing/publishing-a-subgraph.mdx @@ -1,5 +1,6 @@ --- title: Publishing a Subgraph to the Decentralized Network +sidebarTitle: Publishing to the Decentralized Network --- Once you have [deployed your subgraph to Subgraph Studio](/deploying/deploying-a-subgraph-to-studio/) and it's ready to go into production, you can publish it to the decentralized network. diff --git a/website/src/pages/en/subgraphs/querying/best-practices.mdx b/website/src/pages/en/subgraphs/querying/best-practices.mdx index 3736fa32faeb..ff5f381e2993 100644 --- a/website/src/pages/en/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/en/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Sending a query to a GraphQL API diff --git a/website/src/pages/en/subgraphs/querying/from-an-application.mdx b/website/src/pages/en/subgraphs/querying/from-an-application.mdx index 681f6e6ba8d5..0995fc8cbb7c 100644 --- a/website/src/pages/en/subgraphs/querying/from-an-application.mdx +++ b/website/src/pages/en/subgraphs/querying/from-an-application.mdx @@ -1,5 +1,6 @@ --- title: Querying from an Application +sidebarTitle: Querying from an App --- Learn how to query The Graph from your application. diff --git a/website/src/pages/en/subgraphs/querying/managing-api-keys.mdx b/website/src/pages/en/subgraphs/querying/managing-api-keys.mdx index f7aff33ea926..6964b1a7ad9b 100644 --- a/website/src/pages/en/subgraphs/querying/managing-api-keys.mdx +++ b/website/src/pages/en/subgraphs/querying/managing-api-keys.mdx @@ -1,5 +1,5 @@ --- -title: Managing your API keys +title: Managing API keys --- ## Overview diff --git a/website/src/pages/uk/substreams/developing/sinks/sinks.mdx b/website/src/pages/en/substreams/developing/sinks.mdx similarity index 99% rename from website/src/pages/uk/substreams/developing/sinks/sinks.mdx rename to website/src/pages/en/substreams/developing/sinks.mdx index 5f6f9de21326..c270193e0c15 100644 --- a/website/src/pages/uk/substreams/developing/sinks/sinks.mdx +++ b/website/src/pages/en/substreams/developing/sinks.mdx @@ -1,5 +1,5 @@ --- -title: Official Sinks +title: Sink your Substreams --- Choose a sink that meets your project's needs. diff --git a/website/src/pages/en/substreams/developing/sinks/_meta.js b/website/src/pages/en/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/en/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/en/substreams/quick-start.mdx b/website/src/pages/en/substreams/quick-start.mdx index 34e59b54491b..b5eec572b00a 100644 --- a/website/src/pages/en/substreams/quick-start.mdx +++ b/website/src/pages/en/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/es/resources/_meta-titles.json b/website/src/pages/es/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/es/resources/_meta-titles.json +++ b/website/src/pages/es/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/es/resources/_meta.js b/website/src/pages/es/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/es/resources/_meta.js +++ b/website/src/pages/es/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/es/resources/release-notes/_meta.js b/website/src/pages/es/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/es/resources/release-notes/_meta.js rename to website/src/pages/es/resources/migration-guides/_meta.js diff --git a/website/src/pages/es/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/es/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/es/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/es/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/es/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/es/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 100% rename from website/src/pages/es/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/es/resources/migration-guides/graphql-validations-migration-guide.mdx diff --git a/website/src/pages/es/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/es/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/es/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/es/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/es/sps/sps-faq.mdx b/website/src/pages/es/sps/sps-faq.mdx index 63058cdcfb9b..592bdff3db63 100644 --- a/website/src/pages/es/sps/sps-faq.mdx +++ b/website/src/pages/es/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/es/subgraphs/_meta-titles.json b/website/src/pages/es/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/es/subgraphs/_meta-titles.json +++ b/website/src/pages/es/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/es/subgraphs/_meta.js b/website/src/pages/es/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/es/subgraphs/_meta.js +++ b/website/src/pages/es/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/es/subgraphs/best-practices/_meta.js b/website/src/pages/es/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/es/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/it/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/es/subgraphs/best-practices/avoid-eth-calls.mdx similarity index 93% rename from website/src/pages/it/subgraphs/cookbook/avoid-eth-calls.mdx rename to website/src/pages/es/subgraphs/best-practices/avoid-eth-calls.mdx index ae29cdf03a34..e40a7b3712e4 100644 --- a/website/src/pages/it/subgraphs/cookbook/avoid-eth-calls.mdx +++ b/website/src/pages/es/subgraphs/best-practices/avoid-eth-calls.mdx @@ -104,14 +104,14 @@ You can significantly improve indexing performance by minimizing or eliminating ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/it/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/es/subgraphs/best-practices/derivedfrom.mdx similarity index 88% rename from website/src/pages/it/subgraphs/cookbook/derivedfrom.mdx rename to website/src/pages/es/subgraphs/best-practices/derivedfrom.mdx index a0942645c999..db3a49928c89 100644 --- a/website/src/pages/it/subgraphs/cookbook/derivedfrom.mdx +++ b/website/src/pages/es/subgraphs/best-practices/derivedfrom.mdx @@ -76,14 +76,14 @@ For a more detailed explanation of strategies to avoid large arrays, check out K ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/es/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/es/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/es/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/es/subgraphs/best-practices/grafting-hotfix.mdx index d4d4288fe7f5..0f85dfc8acf6 100644 --- a/website/src/pages/es/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/es/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/de/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/es/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx similarity index 92% rename from website/src/pages/de/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx rename to website/src/pages/es/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx index 511565bb3dd4..6ff60ec9ab34 100644 --- a/website/src/pages/de/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ b/website/src/pages/es/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -178,14 +178,14 @@ Read more about using Immutable Entities and Bytes as IDs in this blog post by D ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ar/subgraphs/cookbook/pruning.mdx b/website/src/pages/es/subgraphs/best-practices/pruning.mdx similarity index 86% rename from website/src/pages/ar/subgraphs/cookbook/pruning.mdx rename to website/src/pages/es/subgraphs/best-practices/pruning.mdx index e212d5d02bc9..1b51dde8894f 100644 --- a/website/src/pages/ar/subgraphs/cookbook/pruning.mdx +++ b/website/src/pages/es/subgraphs/best-practices/pruning.mdx @@ -43,14 +43,14 @@ Pruning using `indexerHints` is a best practice for subgraph development, offeri ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/es/subgraphs/cookbook/timeseries.mdx b/website/src/pages/es/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/es/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/es/subgraphs/best-practices/timeseries.mdx index 9e80e08ab148..991ac69c38b7 100644 --- a/website/src/pages/es/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/es/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/es/subgraphs/cookbook/_meta.js b/website/src/pages/es/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/es/subgraphs/cookbook/_meta.js +++ b/website/src/pages/es/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/es/subgraphs/cookbook/cosmos.mdx b/website/src/pages/es/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 3e8c35df064f..000000000000 --- a/website/src/pages/es/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Construyendo subgrafos en Cosmos ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## ¿Qué son los subgrafos de Cosmos? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -Hay cuatro tipos de handlers admitidos en los subgrafos de Cosmos: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Aunque se puede acceder a todos los datos con un handler de bloques, otros handlers permiten a los developers de subgrafos procesar datos de una manera mucho más granular. - -## Construyendo un subgrafo de Cosmos - -### Dependencias de subgrafos - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Componentes principales del subgrafo - -Hay tres partes clave cuando se trata de definir un subgrafo: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### Definición de manifiesto del subgrafo - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### Definición de esquema - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### Asignaciones de AssemblyScript - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Cada tipo de handler viene con su propia estructura de datos que se pasa como argumento a una función de mapping. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Decodificación de mensajes - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Crear y construir un subgrafo de Cosmos - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Deployando un subgrafo de Cosmos - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Consultar un subgrafo de Cosmos - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Blockchains Cosmos compatibles - -### Cosmos Hub - -#### ¿Qué es Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### Networks - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### ¿Qué es Osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### Networks - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## Subgrafos de ejemplo - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/es/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/es/subgraphs/developing/creating/graph-ts/api.mdx index 1d0b8de550a6..67ec89027c6b 100644 --- a/website/src/pages/es/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/es/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/es/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/es/subgraphs/developing/creating/install-the-cli.mdx index ef16d813c431..5a0e73fd0bbd 100644 --- a/website/src/pages/es/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/es/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Instalar The Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Descripción diff --git a/website/src/pages/es/subgraphs/developing/deploying/_meta.js b/website/src/pages/es/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/es/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/es/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/es/subgraphs/querying/best-practices.mdx b/website/src/pages/es/subgraphs/querying/best-practices.mdx index 2091619aa25f..c3340b65f4b2 100644 --- a/website/src/pages/es/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/es/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Envío de una consulta a una API GraphQL diff --git a/website/src/pages/es/substreams/developing/sinks/sinks.mdx b/website/src/pages/es/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/es/substreams/developing/sinks/sinks.mdx rename to website/src/pages/es/substreams/developing/sinks.mdx diff --git a/website/src/pages/es/substreams/developing/sinks/_meta.js b/website/src/pages/es/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/es/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/es/substreams/quick-start.mdx b/website/src/pages/es/substreams/quick-start.mdx index 42eae4521ae1..897daa5fe502 100644 --- a/website/src/pages/es/substreams/quick-start.mdx +++ b/website/src/pages/es/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/fr/resources/_meta-titles.json b/website/src/pages/fr/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/fr/resources/_meta-titles.json +++ b/website/src/pages/fr/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/fr/resources/_meta.js b/website/src/pages/fr/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/fr/resources/_meta.js +++ b/website/src/pages/fr/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/fr/resources/release-notes/_meta.js b/website/src/pages/fr/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/fr/resources/release-notes/_meta.js rename to website/src/pages/fr/resources/migration-guides/_meta.js diff --git a/website/src/pages/fr/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/fr/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/fr/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/fr/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/fr/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/fr/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 100% rename from website/src/pages/fr/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/fr/resources/migration-guides/graphql-validations-migration-guide.mdx diff --git a/website/src/pages/fr/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/fr/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/fr/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/fr/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/fr/sps/sps-faq.mdx b/website/src/pages/fr/sps/sps-faq.mdx index 153ade57d1e5..0924ecb989ca 100644 --- a/website/src/pages/fr/sps/sps-faq.mdx +++ b/website/src/pages/fr/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/fr/subgraphs/_meta-titles.json b/website/src/pages/fr/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/fr/subgraphs/_meta-titles.json +++ b/website/src/pages/fr/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/fr/subgraphs/_meta.js b/website/src/pages/fr/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/fr/subgraphs/_meta.js +++ b/website/src/pages/fr/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/fr/subgraphs/best-practices/_meta.js b/website/src/pages/fr/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/fr/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/fr/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/fr/subgraphs/best-practices/avoid-eth-calls.mdx similarity index 93% rename from website/src/pages/fr/subgraphs/cookbook/avoid-eth-calls.mdx rename to website/src/pages/fr/subgraphs/best-practices/avoid-eth-calls.mdx index 8a8941e0897f..2015af316873 100644 --- a/website/src/pages/fr/subgraphs/cookbook/avoid-eth-calls.mdx +++ b/website/src/pages/fr/subgraphs/best-practices/avoid-eth-calls.mdx @@ -104,14 +104,14 @@ You can significantly improve indexing performance by minimizing or eliminating ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/fr/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/fr/subgraphs/best-practices/derivedfrom.mdx similarity index 89% rename from website/src/pages/fr/subgraphs/cookbook/derivedfrom.mdx rename to website/src/pages/fr/subgraphs/best-practices/derivedfrom.mdx index 05297bebcb70..0f735fd35304 100644 --- a/website/src/pages/fr/subgraphs/cookbook/derivedfrom.mdx +++ b/website/src/pages/fr/subgraphs/best-practices/derivedfrom.mdx @@ -76,14 +76,14 @@ For a more detailed explanation of strategies to avoid large arrays, check out K ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/fr/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/fr/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/fr/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/fr/subgraphs/best-practices/grafting-hotfix.mdx index 53ac16db3cfe..3b56e2b7eb6c 100644 --- a/website/src/pages/fr/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/fr/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/fr/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/fr/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx similarity index 93% rename from website/src/pages/fr/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx rename to website/src/pages/fr/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx index 0f1bdacbc1e3..ae0e39b2564b 100644 --- a/website/src/pages/fr/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ b/website/src/pages/fr/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -178,14 +178,14 @@ En savoir plus sur l'utilisation des Entités immuables et des Bytes en tant qu' ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/fr/subgraphs/cookbook/pruning.mdx b/website/src/pages/fr/subgraphs/best-practices/pruning.mdx similarity index 87% rename from website/src/pages/fr/subgraphs/cookbook/pruning.mdx rename to website/src/pages/fr/subgraphs/best-practices/pruning.mdx index 5677b220aafe..82db761dcdac 100644 --- a/website/src/pages/fr/subgraphs/cookbook/pruning.mdx +++ b/website/src/pages/fr/subgraphs/best-practices/pruning.mdx @@ -43,14 +43,14 @@ L'élagage en utilisant `indexerHints` est une meilleure bonne pour le développ ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/fr/subgraphs/cookbook/timeseries.mdx b/website/src/pages/fr/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/fr/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/fr/subgraphs/best-practices/timeseries.mdx index 9461513e7c6f..39363a06651f 100644 --- a/website/src/pages/fr/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/fr/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/fr/subgraphs/cookbook/_meta.js b/website/src/pages/fr/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/fr/subgraphs/cookbook/_meta.js +++ b/website/src/pages/fr/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/fr/subgraphs/cookbook/cosmos.mdx b/website/src/pages/fr/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 286a8a2005be..000000000000 --- a/website/src/pages/fr/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Création de subgraphes sur Cosmos ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## Que sont les subgraphs de Cosmos ? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -Il existe quatre types de gestionnaires pris en charge dans les subgraphs de Cosmos : - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Même si toutes les données sont accessibles avec un gestionnaire de blocs, des gestionnaires tiers permettent aux développeurs de subgraphs de traiter les données de manière beaucoup plus précise. - -## Création d'un subgraph ciblant Cosmos - -### Dépendances des subgraphs - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Composants principaux du subgraph - -La définition d'un subgraph comporte trois éléments clés : - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### Définition du manifeste du subgraph - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -version spec: 0.0.5 -description: Exemple de subgraph Cosmos -schéma: - fichier: ./schema.graphql # lien vers le fichier de schéma -les sources de données: - - genre: cosmos - nom: CosmosHub - réseau: cosmoshub-4 # Cela changera pour chaque blockchain basée sur le cosmos. Dans ce cas, l’exemple utilise le mainnet Cosmos Hub. - source: - startBlock: 0 # Requis pour Cosmos, définissez-le sur 0 pour démarrer l'indexation à partir de la genèse de la chaîne - cartographie: - Version api: 0.0.7 - langage: wasm/assemblyscript - gestionnaires de blocs: - - handler: handleNewBlock # le nom de la fonction dans le fichier de mappage - Gestionnaires d'événements: - - event: récompenses # le type d'événement qui sera géré - handler: handleReward # le nom de la fonction dans le fichier de mappage - Gestionnaires de transactions: - - handler: handleTransaction # le nom de la fonction dans le fichier de mappage - Gestionnaires de messages: - - message: /cosmos.staking.v1beta1.MsgDelegate # le type d'un message - handler: handleMsgDelegate # le nom de la fonction dans le fichier de mappage - fichier: ./src/mapping.ts # lien vers le fichier avec les mappages Assemblyscript -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### Définition de schéma - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### Cartographies AssemblyScript - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Chaque structure de type de gestionnaire transmise en tant qu'argument à une fonction de mappage. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Décodage des messages - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Création et construction d'un subgraph Cosmos - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ codegen graph -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ construction de graph -``` - -## Déploiement d'un subgraph Cosmos - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visitez Subgraph Studio pour créer un nouveau subgraph. - -```bash -graph deploy nom-du-subgraph -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create nom-du-subgraph --node http://localhost:8020 -``` - -```bash -graph deploy nom-du-subgraph --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Interroger un subgraph de Cosmos - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Blockchains Cosmos prises en charge - -### Cosmos Hub - -#### Qu'est-ce qu'un Cosmos Hub ? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### Les Réseaux - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> La prise en charge d'Osmosis dans Graph Node et sur Subgraph Studio est en bêta : veuillez contacter l'équipe de The Graph pour toute question sur la création de subgraphs Osmosis ! - -#### Qu’est-ce que l’osmose ? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### Les Réseaux - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## Exemples de subgraphs - -Voici quelques exemples de subgraphs pour référence : - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/fr/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/fr/subgraphs/developing/creating/graph-ts/api.mdx index 0e194fc08e1c..a74814844016 100644 --- a/website/src/pages/fr/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/fr/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: API AssemblyScript --- -> Note : Si vous avez créé un subgraph avant la version `graph-cli`/`graph-ts` `0.22.0`, alors vous utilisez une ancienne version d'AssemblyScript. Il est recommandé de consulter le [`Guide de Migration`](/resources/release-notes/assemblyscript-migration-guide/). +> Note : Si vous avez créé un subgraph avant la version `graph-cli`/`graph-ts` `0.22.0`, alors vous utilisez une ancienne version d'AssemblyScript. Il est recommandé de consulter le [`Guide de Migration`](/resources/migration-guides/assemblyscript-migration-guide/). Découvrez quelles APIs intégrées peuvent être utilisées lors de l'écriture des mappages de subgraph. Il existe deux types d'APIs disponibles par défaut : @@ -35,7 +35,7 @@ La `apiVersion` dans le manifeste du subgraph spécifie la version de l'API de m | 0.0.8 | Ajout de la validation pour l'existence des champs dans le schéma lors de l'enregistrement d'une entité. | | 0.0.7 | Ajout des classes `TransactionReceipt` et `Log`aux types Ethereum
Ajout du champ `receipt` à l'objet Ethereum Event | | 0.0.6 | Ajout du champ `nonce` à l'objet Ethereum Transaction
Ajout de `baseFeePerGas` à l'objet Ethereum Block | -| 0.0.5 | AssemblyScript a été mis à niveau à niveau vers la version 0.19.10 (cela inclut des changements brusques, veuillez consulter le [`Guide de migration`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renommé en `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript a été mis à niveau à niveau vers la version 0.19.10 (cela inclut des changements brusques, veuillez consulter le [`Guide de migration`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renommé en `ethereum.transaction.gasLimit` | | 0.0.4 | Ajout du champ `functionSignature` à l'objet Ethereum SmartContractCall | | 0.0.3 | Ajout du champ `from` à l'objet Ethereum Call
`ethereum.call.address` renommé en `ethereum.call.to` | | 0.0.2 | Ajout du champ `input` à l'objet Ethereum Transaction | diff --git a/website/src/pages/fr/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/fr/subgraphs/developing/creating/install-the-cli.mdx index 339674050b52..0376a713f058 100644 --- a/website/src/pages/fr/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/fr/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Installation du Graph CLI --- -> Pour utiliser votre subgraph sur le réseau décentralisé de The Graph, vous devrez [créer une clé API](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) dans [Subgraph Studio](https://thegraph.com/studio/apikeys/). Il est recommandé d'ajouter un signal à votre subgraph avec au moins 3 000 GRT pour attirer 2 à 3 Indexeurs. Pour en savoir plus sur la signalisation, consultez [curation](/resources/roles/curating/). +> Pour utiliser votre subgraph sur le réseau décentralisé de The Graph, vous devrez [créer une clé API](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) dans [Subgraph Studio](https://thegraph.com/studio/apikeys/). Il est recommandé d'ajouter un signal à votre subgraph avec au moins 3 000 GRT pour attirer 2 à 3 Indexeurs. Pour en savoir plus sur la signalisation, consultez [curation](/resources/roles/curating/). ## Aperçu diff --git a/website/src/pages/fr/subgraphs/developing/deploying/_meta.js b/website/src/pages/fr/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/fr/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/fr/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/fr/subgraphs/querying/best-practices.mdx b/website/src/pages/fr/subgraphs/querying/best-practices.mdx index 4c9ac69b2af4..7840723ca03d 100644 --- a/website/src/pages/fr/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/fr/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Envoi d'une requête à une API GraphQL diff --git a/website/src/pages/fr/substreams/developing/sinks/sinks.mdx b/website/src/pages/fr/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/fr/substreams/developing/sinks/sinks.mdx rename to website/src/pages/fr/substreams/developing/sinks.mdx diff --git a/website/src/pages/fr/substreams/developing/sinks/_meta.js b/website/src/pages/fr/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/fr/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/fr/substreams/quick-start.mdx b/website/src/pages/fr/substreams/quick-start.mdx index 7957593ded67..ad7774b5102e 100644 --- a/website/src/pages/fr/substreams/quick-start.mdx +++ b/website/src/pages/fr/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/hi/resources/_meta-titles.json b/website/src/pages/hi/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/hi/resources/_meta-titles.json +++ b/website/src/pages/hi/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/hi/resources/_meta.js b/website/src/pages/hi/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/hi/resources/_meta.js +++ b/website/src/pages/hi/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/hi/resources/release-notes/_meta.js b/website/src/pages/hi/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/hi/resources/release-notes/_meta.js rename to website/src/pages/hi/resources/migration-guides/_meta.js diff --git a/website/src/pages/hi/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/hi/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/hi/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/hi/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/hi/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/hi/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 100% rename from website/src/pages/hi/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/hi/resources/migration-guides/graphql-validations-migration-guide.mdx diff --git a/website/src/pages/hi/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/hi/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/hi/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/hi/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/hi/sps/sps-faq.mdx b/website/src/pages/hi/sps/sps-faq.mdx index 05a62d9f9ac2..53a8f393a5bc 100644 --- a/website/src/pages/hi/sps/sps-faq.mdx +++ b/website/src/pages/hi/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/hi/subgraphs/_meta-titles.json b/website/src/pages/hi/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/hi/subgraphs/_meta-titles.json +++ b/website/src/pages/hi/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/hi/subgraphs/_meta.js b/website/src/pages/hi/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/hi/subgraphs/_meta.js +++ b/website/src/pages/hi/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/hi/subgraphs/best-practices/_meta.js b/website/src/pages/hi/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/hi/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/hi/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/hi/subgraphs/best-practices/avoid-eth-calls.mdx similarity index 96% rename from website/src/pages/hi/subgraphs/cookbook/avoid-eth-calls.mdx rename to website/src/pages/hi/subgraphs/best-practices/avoid-eth-calls.mdx index 8c9f3a4f0d91..cd5921ae8354 100644 --- a/website/src/pages/hi/subgraphs/cookbook/avoid-eth-calls.mdx +++ b/website/src/pages/hi/subgraphs/best-practices/avoid-eth-calls.mdx @@ -104,14 +104,14 @@ You can significantly improve indexing performance by minimizing or eliminating ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/hi/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/hi/subgraphs/best-practices/derivedfrom.mdx similarity index 93% rename from website/src/pages/hi/subgraphs/cookbook/derivedfrom.mdx rename to website/src/pages/hi/subgraphs/best-practices/derivedfrom.mdx index a5c5b392a400..6711d2943209 100644 --- a/website/src/pages/hi/subgraphs/cookbook/derivedfrom.mdx +++ b/website/src/pages/hi/subgraphs/best-practices/derivedfrom.mdx @@ -76,14 +76,14 @@ For a more detailed explanation of strategies to avoid large arrays, check out K ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/hi/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/hi/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/hi/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/hi/subgraphs/best-practices/grafting-hotfix.mdx index e4fc99c0f862..cc3c759ebdea 100644 --- a/website/src/pages/hi/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/hi/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/hi/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/hi/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx similarity index 96% rename from website/src/pages/hi/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx rename to website/src/pages/hi/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx index d4f199414677..5cccca23acb2 100644 --- a/website/src/pages/hi/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ b/website/src/pages/hi/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -178,14 +178,14 @@ Immutable Entities और Bytes को IDs के रूप में उपय ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/hi/subgraphs/cookbook/pruning.mdx b/website/src/pages/hi/subgraphs/best-practices/pruning.mdx similarity index 90% rename from website/src/pages/hi/subgraphs/cookbook/pruning.mdx rename to website/src/pages/hi/subgraphs/best-practices/pruning.mdx index 0ddc96a1ee85..e566e35d240e 100644 --- a/website/src/pages/hi/subgraphs/cookbook/pruning.mdx +++ b/website/src/pages/hi/subgraphs/best-practices/pruning.mdx @@ -43,14 +43,14 @@ Pruning का उपयोग indexerHints से करना एक सर् ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/hi/subgraphs/cookbook/timeseries.mdx b/website/src/pages/hi/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/hi/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/hi/subgraphs/best-practices/timeseries.mdx index 9d778010bf52..a0c4f65157ad 100644 --- a/website/src/pages/hi/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/hi/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/hi/subgraphs/cookbook/_meta.js b/website/src/pages/hi/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/hi/subgraphs/cookbook/_meta.js +++ b/website/src/pages/hi/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/hi/subgraphs/cookbook/cosmos.mdx b/website/src/pages/hi/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index ed1e762363fc..000000000000 --- a/website/src/pages/hi/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: कॉसमॉस पर सब-ग्राफ्स बनाना ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## कॉसमॉस सब-ग्राफ्स क्या होते हैं? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -कॉसमॉस सब-ग्राफ्स में कुल चार प्रकार के हैंडलर्स सहयोगी हैं: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -जबकि सारा डाटा एक ब्लॉक हैंडलर की मदद से प्राप्त किया जा सकता है, बाकी हैंडलर्स सब-ग्राफ डेवलपरों को डाटा अधिक बारीक तरह से प्रोसेस करने में सहायता करते हैं| - -## एक कॉसमॉस सब-ग्राफ बनाना - -### सब-ग्राफ्स की निर्भरता - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### सब-ग्राफ के मुख्या कॉम्पोनेन्ट - -सब-ग्राफ्स को परिभासित करने के तीन मुख्या अंग हैं: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### सब ग्राफ मैनिफेस्ट की परिभाषा - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### स्कीमा की परिभाषा - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### असेंबली स्क्रिप्ट मैप्पिंग्स - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -हर हैंडलर प्रकार अपने खुद के डाटा स्ट्रक्चर के साथ आता है जिसे आर्गुमेंट की तरह मैपिंग फंक्शन में पास किया जा सकता है| - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### मैसेज डिकोडिंग - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## कॉसमॉस सब-ग्राफ्स बनाना और निर्माण करना - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## एक कॉसमॉस सब-ग्राफ डेप्लॉय करना - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## कॉसमॉस सब-ग्राफ को क्वेरी करना - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## समर्थित कॉसमॉस ब्लॉकचेन्स - -### कॉसमॉस हब - -#### कॉसमॉस हब क्या है? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### नेटवर्क्स - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### ऑस्मोसिस - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### ऑस्मोसिस क्या है? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### नेटवर्क्स - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## सब-ग्राफ के उदाहरण - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/hi/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/hi/subgraphs/developing/creating/graph-ts/api.mdx index 1eb1caaa450a..e967ffa1b80b 100644 --- a/website/src/pages/hi/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/hi/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). यह पृष्ठ दस्तावेज करता है कि Subgraph मैपिंग लिखते समय किन अंतर्निहित एपीआई का उपयोग किया जा सकता है। बॉक्स से बाहर दो प्रकार के एपीआई उपलब्ध हैं: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/hi/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/hi/subgraphs/developing/creating/install-the-cli.mdx index 35ca80ae379e..84d3b139b130 100644 --- a/website/src/pages/hi/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/hi/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: . ग्राफ़ सीएलआई इनस्टॉल करें --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## अवलोकन diff --git a/website/src/pages/hi/subgraphs/developing/deploying/_meta.js b/website/src/pages/hi/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/hi/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/hi/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/hi/subgraphs/querying/best-practices.mdx b/website/src/pages/hi/subgraphs/querying/best-practices.mdx index f70313fa64e4..3dd4ad1007d4 100644 --- a/website/src/pages/hi/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/hi/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > ध्यान दें: इन नियमों का पालन न करने पर The Graph API से त्रुटि होगी। -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### एक ग्राफ़क्यूएल एपीआई के लिए एक प्रश्न भेजना diff --git a/website/src/pages/hi/substreams/developing/sinks/sinks.mdx b/website/src/pages/hi/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/hi/substreams/developing/sinks/sinks.mdx rename to website/src/pages/hi/substreams/developing/sinks.mdx diff --git a/website/src/pages/hi/substreams/developing/sinks/_meta.js b/website/src/pages/hi/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/hi/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/hi/substreams/quick-start.mdx b/website/src/pages/hi/substreams/quick-start.mdx index 91251e8bea88..2a54c6032f1a 100644 --- a/website/src/pages/hi/substreams/quick-start.mdx +++ b/website/src/pages/hi/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/it/resources/_meta-titles.json b/website/src/pages/it/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/it/resources/_meta-titles.json +++ b/website/src/pages/it/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/it/resources/_meta.js b/website/src/pages/it/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/it/resources/_meta.js +++ b/website/src/pages/it/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/it/resources/release-notes/_meta.js b/website/src/pages/it/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/it/resources/release-notes/_meta.js rename to website/src/pages/it/resources/migration-guides/_meta.js diff --git a/website/src/pages/it/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/it/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/it/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/it/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/it/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/it/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 100% rename from website/src/pages/it/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/it/resources/migration-guides/graphql-validations-migration-guide.mdx diff --git a/website/src/pages/it/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/it/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/it/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/it/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/it/sps/sps-faq.mdx b/website/src/pages/it/sps/sps-faq.mdx index 537f29b09ea6..abc1f3906686 100644 --- a/website/src/pages/it/sps/sps-faq.mdx +++ b/website/src/pages/it/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/it/subgraphs/_meta-titles.json b/website/src/pages/it/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/it/subgraphs/_meta-titles.json +++ b/website/src/pages/it/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/it/subgraphs/_meta.js b/website/src/pages/it/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/it/subgraphs/_meta.js +++ b/website/src/pages/it/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/it/subgraphs/best-practices/_meta.js b/website/src/pages/it/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/it/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/es/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/it/subgraphs/best-practices/avoid-eth-calls.mdx similarity index 93% rename from website/src/pages/es/subgraphs/cookbook/avoid-eth-calls.mdx rename to website/src/pages/it/subgraphs/best-practices/avoid-eth-calls.mdx index ae29cdf03a34..e40a7b3712e4 100644 --- a/website/src/pages/es/subgraphs/cookbook/avoid-eth-calls.mdx +++ b/website/src/pages/it/subgraphs/best-practices/avoid-eth-calls.mdx @@ -104,14 +104,14 @@ You can significantly improve indexing performance by minimizing or eliminating ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ar/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/it/subgraphs/best-practices/derivedfrom.mdx similarity index 88% rename from website/src/pages/ar/subgraphs/cookbook/derivedfrom.mdx rename to website/src/pages/it/subgraphs/best-practices/derivedfrom.mdx index a0942645c999..db3a49928c89 100644 --- a/website/src/pages/ar/subgraphs/cookbook/derivedfrom.mdx +++ b/website/src/pages/it/subgraphs/best-practices/derivedfrom.mdx @@ -76,14 +76,14 @@ For a more detailed explanation of strategies to avoid large arrays, check out K ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/it/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/it/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/it/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/it/subgraphs/best-practices/grafting-hotfix.mdx index 91eff07eceb6..62edf8926555 100644 --- a/website/src/pages/it/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/it/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/it/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/it/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx similarity index 92% rename from website/src/pages/it/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx rename to website/src/pages/it/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx index 511565bb3dd4..6ff60ec9ab34 100644 --- a/website/src/pages/it/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ b/website/src/pages/it/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -178,14 +178,14 @@ Read more about using Immutable Entities and Bytes as IDs in this blog post by D ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/it/subgraphs/cookbook/pruning.mdx b/website/src/pages/it/subgraphs/best-practices/pruning.mdx similarity index 86% rename from website/src/pages/it/subgraphs/cookbook/pruning.mdx rename to website/src/pages/it/subgraphs/best-practices/pruning.mdx index e212d5d02bc9..1b51dde8894f 100644 --- a/website/src/pages/it/subgraphs/cookbook/pruning.mdx +++ b/website/src/pages/it/subgraphs/best-practices/pruning.mdx @@ -43,14 +43,14 @@ Pruning using `indexerHints` is a best practice for subgraph development, offeri ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/it/subgraphs/cookbook/timeseries.mdx b/website/src/pages/it/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/it/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/it/subgraphs/best-practices/timeseries.mdx index 5e8eea7f648b..112e062e6187 100644 --- a/website/src/pages/it/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/it/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/it/subgraphs/cookbook/_meta.js b/website/src/pages/it/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/it/subgraphs/cookbook/_meta.js +++ b/website/src/pages/it/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/it/subgraphs/cookbook/cosmos.mdx b/website/src/pages/it/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 5ccf1025ca47..000000000000 --- a/website/src/pages/it/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Building Subgraphs on Cosmos ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## What are Cosmos subgraphs? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -There are four types of handlers supported in Cosmos subgraphs: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Even though all data can be accessed with a block handler, other handlers enable subgraph developers to process data in a much more granular way. - -## Building a Cosmos subgraph - -### Subgraph Dependencies - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Subgraph Main Components - -There are three key parts when it comes to defining a subgraph: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### Subgraph Manifest Definition - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### Schema Definition - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript Mappings - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Each handler type comes with its own data structure that is passed as an argument to a mapping function. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Message decoding - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Creating and building a Cosmos subgraph - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Deploying a Cosmos subgraph - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Querying a Cosmos subgraph - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Supported Cosmos Blockchains - -### Cosmos Hub - -#### What is Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### Networks - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### What is Osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### Networks - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## Example Subgraphs - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/it/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/it/subgraphs/developing/creating/graph-ts/api.mdx index ff1d8b3c0952..1d6fa48848b3 100644 --- a/website/src/pages/it/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/it/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: API AssemblyScript --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ La `apiVersion` nel manifest del subgraph specifica la versione dell'API di mapp | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Aggiunte le classi `TransactionReceipt` e `Log` ai tipi di Ethereum
Aggiunto il campo `receipt` all'oggetto Ethereum Event | | 0.0.6 | Aggiunto il campo `nonce` all'oggetto Ethereum Transaction
Aggiunto `baseFeePerGas` all'oggetto Ethereum Block | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Aggiunto il campo `functionSignature` all'oggetto Ethereum SmartContractCall | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Aggiunto il campo `input` all'oggetto Ethereum Transaction | diff --git a/website/src/pages/it/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/it/subgraphs/developing/creating/install-the-cli.mdx index 495beb2a6db4..4f4afcee006a 100644 --- a/website/src/pages/it/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/it/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Installare the Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Panoramica diff --git a/website/src/pages/it/subgraphs/developing/deploying/_meta.js b/website/src/pages/it/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/it/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/it/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/it/subgraphs/querying/best-practices.mdx b/website/src/pages/it/subgraphs/querying/best-practices.mdx index 5e1f5a183b3c..c797e432ac0b 100644 --- a/website/src/pages/it/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/it/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Invio di una query a un API GraphQL diff --git a/website/src/pages/it/substreams/developing/sinks/sinks.mdx b/website/src/pages/it/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/it/substreams/developing/sinks/sinks.mdx rename to website/src/pages/it/substreams/developing/sinks.mdx diff --git a/website/src/pages/it/substreams/developing/sinks/_meta.js b/website/src/pages/it/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/it/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/it/substreams/quick-start.mdx b/website/src/pages/it/substreams/quick-start.mdx index cee8579fd7d0..a4c82cb797d9 100644 --- a/website/src/pages/it/substreams/quick-start.mdx +++ b/website/src/pages/it/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/ja/resources/_meta-titles.json b/website/src/pages/ja/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/ja/resources/_meta-titles.json +++ b/website/src/pages/ja/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/ja/resources/_meta.js b/website/src/pages/ja/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/ja/resources/_meta.js +++ b/website/src/pages/ja/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/ja/resources/release-notes/_meta.js b/website/src/pages/ja/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/ja/resources/release-notes/_meta.js rename to website/src/pages/ja/resources/migration-guides/_meta.js diff --git a/website/src/pages/ja/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/ja/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/ja/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/ja/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/ja/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/ja/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 100% rename from website/src/pages/ja/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/ja/resources/migration-guides/graphql-validations-migration-guide.mdx diff --git a/website/src/pages/ja/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/ja/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/ja/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/ja/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/ja/sps/sps-faq.mdx b/website/src/pages/ja/sps/sps-faq.mdx index 8ed87902ee4f..de0755e30c95 100644 --- a/website/src/pages/ja/sps/sps-faq.mdx +++ b/website/src/pages/ja/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/ja/subgraphs/_meta-titles.json b/website/src/pages/ja/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/ja/subgraphs/_meta-titles.json +++ b/website/src/pages/ja/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/ja/subgraphs/_meta.js b/website/src/pages/ja/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/ja/subgraphs/_meta.js +++ b/website/src/pages/ja/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/ja/subgraphs/best-practices/_meta.js b/website/src/pages/ja/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/ja/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/ja/subgraphs/best-practices/avoid-eth-calls.mdx b/website/src/pages/ja/subgraphs/best-practices/avoid-eth-calls.mdx new file mode 100644 index 000000000000..e40a7b3712e4 --- /dev/null +++ b/website/src/pages/ja/subgraphs/best-practices/avoid-eth-calls.mdx @@ -0,0 +1,117 @@ +--- +title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls +sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' +--- + +## TLDR + +`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. + +## Why Avoiding `eth_calls` Is a Best Practice + +Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. + +### What Does an eth_call Look Like? + +`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: + +```yaml +event Transfer(address indexed from, address indexed to, uint256 value); +``` + +Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, Transfer } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransfer(event: Transfer): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + // Bind the ERC20 contract instance to the given address: + let instance = ERC20.bind(event.address) + + // Retrieve pool information via eth_call + let poolInfo = instance.getPoolInfo(event.params.to) + + transaction.pool = poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is functional, however is not ideal as it slows down our subgraph’s indexing. + +## How to Eliminate `eth_calls` + +Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: + +``` +event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); +``` + +With this update, the subgraph can directly index the required data without external calls: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransferWithPool(event: TransferWithPool): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + transaction.pool = event.params.poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is much more performant as it has eliminated the need for `eth_calls`. + +## How to Optimize `eth_calls` + +If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. + +## Reducing the Runtime Overhead of `eth_calls` + +For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. + +Currently, `eth_calls` can only be declared for event handlers. In the manifest, write + +```yaml +event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) +handler: handleTransferWithPool +calls: + ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) +``` + +The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. + +The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. + +Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. + +## Conclusion + +You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ja/subgraphs/best-practices/derivedfrom.mdx b/website/src/pages/ja/subgraphs/best-practices/derivedfrom.mdx new file mode 100644 index 000000000000..db3a49928c89 --- /dev/null +++ b/website/src/pages/ja/subgraphs/best-practices/derivedfrom.mdx @@ -0,0 +1,89 @@ +--- +title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom +sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' +--- + +## TLDR + +Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. + +## How to Use the `@derivedFrom` Directive + +You just need to add a `@derivedFrom` directive after your array in your schema. Like this: + +```graphql +comments: [Comment!]! @derivedFrom(field: "post") +``` + +`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. + +### Example Use Case for `@derivedFrom` + +An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. + +Let’s start with our two entities, `Post` and `Comment` + +Without optimization, you could implement it like this with an array: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! +} + +type Comment @entity { + id: Bytes! + content: String! +} +``` + +Arrays like these will effectively store extra Comments data on the Post side of the relationship. + +Here’s what an optimized version looks like using `@derivedFrom`: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! @derivedFrom(field: "post") +} + +type Comment @entity { + id: Bytes! + content: String! + post: Post! +} +``` + +Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. + +This will not only make our subgraph more efficient, but it will also unlock three features: + +1. We can query the `Post` and see all of its comments. + +2. We can do a reverse lookup and query any `Comment` and see which post it comes from. + +3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. + +## Conclusion + +Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. + +For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ja/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/ja/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/ja/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/ja/subgraphs/best-practices/grafting-hotfix.mdx index 6f03c994e1e0..cb44f95f25c1 100644 --- a/website/src/pages/ja/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/ja/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ja/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx b/website/src/pages/ja/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx new file mode 100644 index 000000000000..6ff60ec9ab34 --- /dev/null +++ b/website/src/pages/ja/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -0,0 +1,191 @@ +--- +title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs +sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' +--- + +## TLDR + +Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. + +## Immutable Entities + +To make an entity immutable, we simply add `(immutable: true)` to an entity. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. + +Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. + +### Under the hood + +Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. + +### When not to use Immutable Entities + +If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. + +## Bytes as IDs + +Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. + +### Reasons to Not Use Bytes as IDs + +1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. +2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. +3. Indexing and querying performance improvements are not desired. + +### Concatenating With Bytes as IDs + +It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. + +Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. + +```typescript +export function handleTransfer(event: TransferEvent): void { + let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) + entity.from = event.params.from + entity.to = event.params.to + entity.value = event.params.value + + entity.blockNumber = event.block.number + entity.blockTimestamp = event.block.timestamp + entity.transactionHash = event.transaction.hash + + entity.save() +} +``` + +### Sorting With Bytes as IDs + +Sorting using Bytes as IDs is not optimal as seen in this example query and response. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: id) { + id + from + to + value + } +} +``` + +Query response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x00010000", + "from": "0xabcd...", + "to": "0x1234...", + "value": "256" + }, + { + "id": "0x00020000", + "from": "0xefgh...", + "to": "0x5678...", + "value": "512" + }, + { + "id": "0x01000000", + "from": "0xijkl...", + "to": "0x9abc...", + "value": "1" + } + ] + } +} +``` + +The IDs are returned as hex. + +To improve sorting, we should create another field on the entity that is a BigInt. + +```graphql +type Transfer @entity { + id: Bytes! + from: Bytes! # address + to: Bytes! # address + value: BigInt! # unit256 + tokenId: BigInt! # uint256 +} +``` + +This will allow for sorting to be optimized sequentially. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: tokenId) { + id + tokenId + } +} +``` + +Query Response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x…", + "tokenId": "1" + }, + { + "id": "0x…", + "tokenId": "2" + }, + { + "id": "0x…", + "tokenId": "3" + } + ] + } +} +``` + +## Conclusion + +Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. + +Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ja/subgraphs/best-practices/pruning.mdx b/website/src/pages/ja/subgraphs/best-practices/pruning.mdx new file mode 100644 index 000000000000..1b51dde8894f --- /dev/null +++ b/website/src/pages/ja/subgraphs/best-practices/pruning.mdx @@ -0,0 +1,56 @@ +--- +title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning +sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' +--- + +## TLDR + +[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. + +## How to Prune a Subgraph With `indexerHints` + +Add a section called `indexerHints` in the manifest. + +`indexerHints` has three `prune` options: + +- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. +- `prune: `: Sets a custom limit on the number of historical blocks to retain. +- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. + +We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: + +```yaml +specVersion: 1.0.0 +schema: + file: ./schema.graphql +indexerHints: + prune: auto +dataSources: + - kind: ethereum/contract + name: Contract + network: mainnet +``` + +## Important Considerations + +- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. + +- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). + +## Conclusion + +Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ja/subgraphs/cookbook/timeseries.mdx b/website/src/pages/ja/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/ja/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/ja/subgraphs/best-practices/timeseries.mdx index b5a5a346cc2f..c02236d7829c 100644 --- a/website/src/pages/ja/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/ja/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ja/subgraphs/cookbook/_meta.js b/website/src/pages/ja/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/ja/subgraphs/cookbook/_meta.js +++ b/website/src/pages/ja/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/ja/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/ja/subgraphs/cookbook/avoid-eth-calls.mdx deleted file mode 100644 index ae29cdf03a34..000000000000 --- a/website/src/pages/ja/subgraphs/cookbook/avoid-eth-calls.mdx +++ /dev/null @@ -1,117 +0,0 @@ ---- -title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls -sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' ---- - -## TLDR - -`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. - -## Why Avoiding `eth_calls` Is a Best Practice - -Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. - -### What Does an eth_call Look Like? - -`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: - -```yaml -event Transfer(address indexed from, address indexed to, uint256 value); -``` - -Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, Transfer } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransfer(event: Transfer): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - // Bind the ERC20 contract instance to the given address: - let instance = ERC20.bind(event.address) - - // Retrieve pool information via eth_call - let poolInfo = instance.getPoolInfo(event.params.to) - - transaction.pool = poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is functional, however is not ideal as it slows down our subgraph’s indexing. - -## How to Eliminate `eth_calls` - -Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: - -``` -event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); -``` - -With this update, the subgraph can directly index the required data without external calls: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransferWithPool(event: TransferWithPool): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - transaction.pool = event.params.poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is much more performant as it has eliminated the need for `eth_calls`. - -## How to Optimize `eth_calls` - -If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. - -## Reducing the Runtime Overhead of `eth_calls` - -For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. - -Currently, `eth_calls` can only be declared for event handlers. In the manifest, write - -```yaml -event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) -handler: handleTransferWithPool -calls: - ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) -``` - -The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. - -The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. - -Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. - -## Conclusion - -You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ja/subgraphs/cookbook/cosmos.mdx b/website/src/pages/ja/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 008060749aa6..000000000000 --- a/website/src/pages/ja/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Cosmosでのサブグラフ構築 ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## Cosmosのサブグラフとは何ですか? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -Cosmosのサブグラフでサポートされているハンドラーは4種類あります。 - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -ブロックハンドラーでは全てのデータにアクセスできますが、その他のハンドラーでは、サブグラフの開発者がよりきめ細かくデータを処理することができます。 - -## Cosmosサブグラフの構築 - -### サブグラフの依存関係 - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### サブグラフの主な構成要素 - -サブグラフの定義には、3つの重要な部分があります。 - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### サブグラフマニフェストの定義 - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### スキーマ定義 - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript マッピング - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -各ハンドラタイプは独自のデータ構造を持ち、マッピング関数の引数として渡されます。 - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### メッセージ・デコーディング - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Cosmosサブグラフの作成と構築 - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Cosmosサブグラフの展開 - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Cosmosサブグラフのクエリ - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Cosmosブロックチェーンに対応 - -### コスモスハブ - -#### コスモスハブとは? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### ネットワーク - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### Osmosisとは? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### ネットワーク - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## サブグラフの例 - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/ja/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/ja/subgraphs/cookbook/derivedfrom.mdx deleted file mode 100644 index a0942645c999..000000000000 --- a/website/src/pages/ja/subgraphs/cookbook/derivedfrom.mdx +++ /dev/null @@ -1,89 +0,0 @@ ---- -title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom -sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' ---- - -## TLDR - -Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. - -## How to Use the `@derivedFrom` Directive - -You just need to add a `@derivedFrom` directive after your array in your schema. Like this: - -```graphql -comments: [Comment!]! @derivedFrom(field: "post") -``` - -`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. - -### Example Use Case for `@derivedFrom` - -An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. - -Let’s start with our two entities, `Post` and `Comment` - -Without optimization, you could implement it like this with an array: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! -} - -type Comment @entity { - id: Bytes! - content: String! -} -``` - -Arrays like these will effectively store extra Comments data on the Post side of the relationship. - -Here’s what an optimized version looks like using `@derivedFrom`: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! @derivedFrom(field: "post") -} - -type Comment @entity { - id: Bytes! - content: String! - post: Post! -} -``` - -Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. - -This will not only make our subgraph more efficient, but it will also unlock three features: - -1. We can query the `Post` and see all of its comments. - -2. We can do a reverse lookup and query any `Comment` and see which post it comes from. - -3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. - -## Conclusion - -Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. - -For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ja/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/ja/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx deleted file mode 100644 index 511565bb3dd4..000000000000 --- a/website/src/pages/ja/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ /dev/null @@ -1,191 +0,0 @@ ---- -title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs -sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' ---- - -## TLDR - -Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. - -## Immutable Entities - -To make an entity immutable, we simply add `(immutable: true)` to an entity. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. - -Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. - -### Under the hood - -Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. - -### When not to use Immutable Entities - -If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. - -## Bytes as IDs - -Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. - -### Reasons to Not Use Bytes as IDs - -1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. -2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. -3. Indexing and querying performance improvements are not desired. - -### Concatenating With Bytes as IDs - -It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. - -Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. - -```typescript -export function handleTransfer(event: TransferEvent): void { - let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) - entity.from = event.params.from - entity.to = event.params.to - entity.value = event.params.value - - entity.blockNumber = event.block.number - entity.blockTimestamp = event.block.timestamp - entity.transactionHash = event.transaction.hash - - entity.save() -} -``` - -### Sorting With Bytes as IDs - -Sorting using Bytes as IDs is not optimal as seen in this example query and response. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: id) { - id - from - to - value - } -} -``` - -Query response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x00010000", - "from": "0xabcd...", - "to": "0x1234...", - "value": "256" - }, - { - "id": "0x00020000", - "from": "0xefgh...", - "to": "0x5678...", - "value": "512" - }, - { - "id": "0x01000000", - "from": "0xijkl...", - "to": "0x9abc...", - "value": "1" - } - ] - } -} -``` - -The IDs are returned as hex. - -To improve sorting, we should create another field on the entity that is a BigInt. - -```graphql -type Transfer @entity { - id: Bytes! - from: Bytes! # address - to: Bytes! # address - value: BigInt! # unit256 - tokenId: BigInt! # uint256 -} -``` - -This will allow for sorting to be optimized sequentially. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: tokenId) { - id - tokenId - } -} -``` - -Query Response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x…", - "tokenId": "1" - }, - { - "id": "0x…", - "tokenId": "2" - }, - { - "id": "0x…", - "tokenId": "3" - } - ] - } -} -``` - -## Conclusion - -Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. - -Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ja/subgraphs/cookbook/pruning.mdx b/website/src/pages/ja/subgraphs/cookbook/pruning.mdx deleted file mode 100644 index e212d5d02bc9..000000000000 --- a/website/src/pages/ja/subgraphs/cookbook/pruning.mdx +++ /dev/null @@ -1,56 +0,0 @@ ---- -title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning -sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' ---- - -## TLDR - -[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. - -## How to Prune a Subgraph With `indexerHints` - -Add a section called `indexerHints` in the manifest. - -`indexerHints` has three `prune` options: - -- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. -- `prune: `: Sets a custom limit on the number of historical blocks to retain. -- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. - -We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: - -```yaml -specVersion: 1.0.0 -schema: - file: ./schema.graphql -indexerHints: - prune: auto -dataSources: - - kind: ethereum/contract - name: Contract - network: mainnet -``` - -## Important Considerations - -- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. - -- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). - -## Conclusion - -Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ja/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/ja/subgraphs/developing/creating/graph-ts/api.mdx index e493ddd7a5e4..c9d5c8a3ba47 100644 --- a/website/src/pages/ja/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/ja/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ Since language mappings are written in AssemblyScript, it is useful to review th | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Ethereum タイプに `TransactionReceipt` と `Log` クラスを追加
Ethereum Event オブジェクトに `receipt` フィールドを追加。 | | 0.0.6 | Ethereum Transactionオブジェクトに`nonce`フィールドを追加
Ethereum Blockオブジェクトに`baseFeePerGas`を追加。 | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Ethereum SmartContractCall オブジェクトにfunctionSignatureフィールドを追加 | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Ethereum Transaction オブジェクトに inputフィールドを追加 | diff --git a/website/src/pages/ja/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/ja/subgraphs/developing/creating/install-the-cli.mdx index 593ec6d24b2d..397b011cbdd3 100644 --- a/website/src/pages/ja/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/ja/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Graph CLI のインストール --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## 概要 diff --git a/website/src/pages/ja/subgraphs/developing/deploying/_meta.js b/website/src/pages/ja/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/ja/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/ja/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/ja/subgraphs/querying/best-practices.mdx b/website/src/pages/ja/subgraphs/querying/best-practices.mdx index 2866e3ccb933..d0700c1fe37d 100644 --- a/website/src/pages/ja/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/ja/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### GraphQL APIへのクエリの送信 diff --git a/website/src/pages/ja/substreams/developing/sinks/sinks.mdx b/website/src/pages/ja/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/ja/substreams/developing/sinks/sinks.mdx rename to website/src/pages/ja/substreams/developing/sinks.mdx diff --git a/website/src/pages/ja/substreams/developing/sinks/_meta.js b/website/src/pages/ja/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/ja/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/ja/substreams/quick-start.mdx b/website/src/pages/ja/substreams/quick-start.mdx index e67f649fc2c6..9f23f174a4f1 100644 --- a/website/src/pages/ja/substreams/quick-start.mdx +++ b/website/src/pages/ja/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/ko/resources/_meta-titles.json b/website/src/pages/ko/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/ko/resources/_meta-titles.json +++ b/website/src/pages/ko/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/ko/resources/_meta.js b/website/src/pages/ko/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/ko/resources/_meta.js +++ b/website/src/pages/ko/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/ko/resources/release-notes/_meta.js b/website/src/pages/ko/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/ko/resources/release-notes/_meta.js rename to website/src/pages/ko/resources/migration-guides/_meta.js diff --git a/website/src/pages/ko/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/ko/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/ko/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/ko/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/en/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/ko/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 99% rename from website/src/pages/en/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/ko/resources/migration-guides/graphql-validations-migration-guide.mdx index 4d909e8970a8..29fed533ef8c 100644 --- a/website/src/pages/en/resources/release-notes/graphql-validations-migration-guide.mdx +++ b/website/src/pages/ko/resources/migration-guides/graphql-validations-migration-guide.mdx @@ -1,5 +1,5 @@ --- -title: GraphQL Validations migration guide +title: GraphQL Validations Migration Guide --- Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). diff --git a/website/src/pages/ko/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/ko/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/ko/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/ko/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/ko/sps/sps-faq.mdx b/website/src/pages/ko/sps/sps-faq.mdx index 537f29b09ea6..abc1f3906686 100644 --- a/website/src/pages/ko/sps/sps-faq.mdx +++ b/website/src/pages/ko/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/ko/subgraphs/_meta-titles.json b/website/src/pages/ko/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/ko/subgraphs/_meta-titles.json +++ b/website/src/pages/ko/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/ko/subgraphs/_meta.js b/website/src/pages/ko/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/ko/subgraphs/_meta.js +++ b/website/src/pages/ko/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/ko/subgraphs/best-practices/_meta.js b/website/src/pages/ko/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/ko/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/ko/subgraphs/best-practices/avoid-eth-calls.mdx b/website/src/pages/ko/subgraphs/best-practices/avoid-eth-calls.mdx new file mode 100644 index 000000000000..e40a7b3712e4 --- /dev/null +++ b/website/src/pages/ko/subgraphs/best-practices/avoid-eth-calls.mdx @@ -0,0 +1,117 @@ +--- +title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls +sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' +--- + +## TLDR + +`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. + +## Why Avoiding `eth_calls` Is a Best Practice + +Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. + +### What Does an eth_call Look Like? + +`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: + +```yaml +event Transfer(address indexed from, address indexed to, uint256 value); +``` + +Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, Transfer } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransfer(event: Transfer): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + // Bind the ERC20 contract instance to the given address: + let instance = ERC20.bind(event.address) + + // Retrieve pool information via eth_call + let poolInfo = instance.getPoolInfo(event.params.to) + + transaction.pool = poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is functional, however is not ideal as it slows down our subgraph’s indexing. + +## How to Eliminate `eth_calls` + +Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: + +``` +event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); +``` + +With this update, the subgraph can directly index the required data without external calls: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransferWithPool(event: TransferWithPool): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + transaction.pool = event.params.poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is much more performant as it has eliminated the need for `eth_calls`. + +## How to Optimize `eth_calls` + +If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. + +## Reducing the Runtime Overhead of `eth_calls` + +For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. + +Currently, `eth_calls` can only be declared for event handlers. In the manifest, write + +```yaml +event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) +handler: handleTransferWithPool +calls: + ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) +``` + +The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. + +The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. + +Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. + +## Conclusion + +You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ko/subgraphs/best-practices/derivedfrom.mdx b/website/src/pages/ko/subgraphs/best-practices/derivedfrom.mdx new file mode 100644 index 000000000000..db3a49928c89 --- /dev/null +++ b/website/src/pages/ko/subgraphs/best-practices/derivedfrom.mdx @@ -0,0 +1,89 @@ +--- +title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom +sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' +--- + +## TLDR + +Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. + +## How to Use the `@derivedFrom` Directive + +You just need to add a `@derivedFrom` directive after your array in your schema. Like this: + +```graphql +comments: [Comment!]! @derivedFrom(field: "post") +``` + +`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. + +### Example Use Case for `@derivedFrom` + +An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. + +Let’s start with our two entities, `Post` and `Comment` + +Without optimization, you could implement it like this with an array: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! +} + +type Comment @entity { + id: Bytes! + content: String! +} +``` + +Arrays like these will effectively store extra Comments data on the Post side of the relationship. + +Here’s what an optimized version looks like using `@derivedFrom`: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! @derivedFrom(field: "post") +} + +type Comment @entity { + id: Bytes! + content: String! + post: Post! +} +``` + +Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. + +This will not only make our subgraph more efficient, but it will also unlock three features: + +1. We can query the `Post` and see all of its comments. + +2. We can do a reverse lookup and query any `Comment` and see which post it comes from. + +3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. + +## Conclusion + +Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. + +For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ro/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/ko/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/ro/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/ko/subgraphs/best-practices/grafting-hotfix.mdx index 910e32cfacde..d514e1633c75 100644 --- a/website/src/pages/ro/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/ko/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ko/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx b/website/src/pages/ko/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx new file mode 100644 index 000000000000..6ff60ec9ab34 --- /dev/null +++ b/website/src/pages/ko/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -0,0 +1,191 @@ +--- +title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs +sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' +--- + +## TLDR + +Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. + +## Immutable Entities + +To make an entity immutable, we simply add `(immutable: true)` to an entity. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. + +Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. + +### Under the hood + +Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. + +### When not to use Immutable Entities + +If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. + +## Bytes as IDs + +Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. + +### Reasons to Not Use Bytes as IDs + +1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. +2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. +3. Indexing and querying performance improvements are not desired. + +### Concatenating With Bytes as IDs + +It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. + +Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. + +```typescript +export function handleTransfer(event: TransferEvent): void { + let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) + entity.from = event.params.from + entity.to = event.params.to + entity.value = event.params.value + + entity.blockNumber = event.block.number + entity.blockTimestamp = event.block.timestamp + entity.transactionHash = event.transaction.hash + + entity.save() +} +``` + +### Sorting With Bytes as IDs + +Sorting using Bytes as IDs is not optimal as seen in this example query and response. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: id) { + id + from + to + value + } +} +``` + +Query response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x00010000", + "from": "0xabcd...", + "to": "0x1234...", + "value": "256" + }, + { + "id": "0x00020000", + "from": "0xefgh...", + "to": "0x5678...", + "value": "512" + }, + { + "id": "0x01000000", + "from": "0xijkl...", + "to": "0x9abc...", + "value": "1" + } + ] + } +} +``` + +The IDs are returned as hex. + +To improve sorting, we should create another field on the entity that is a BigInt. + +```graphql +type Transfer @entity { + id: Bytes! + from: Bytes! # address + to: Bytes! # address + value: BigInt! # unit256 + tokenId: BigInt! # uint256 +} +``` + +This will allow for sorting to be optimized sequentially. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: tokenId) { + id + tokenId + } +} +``` + +Query Response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x…", + "tokenId": "1" + }, + { + "id": "0x…", + "tokenId": "2" + }, + { + "id": "0x…", + "tokenId": "3" + } + ] + } +} +``` + +## Conclusion + +Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. + +Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ko/subgraphs/best-practices/pruning.mdx b/website/src/pages/ko/subgraphs/best-practices/pruning.mdx new file mode 100644 index 000000000000..1b51dde8894f --- /dev/null +++ b/website/src/pages/ko/subgraphs/best-practices/pruning.mdx @@ -0,0 +1,56 @@ +--- +title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning +sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' +--- + +## TLDR + +[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. + +## How to Prune a Subgraph With `indexerHints` + +Add a section called `indexerHints` in the manifest. + +`indexerHints` has three `prune` options: + +- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. +- `prune: `: Sets a custom limit on the number of historical blocks to retain. +- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. + +We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: + +```yaml +specVersion: 1.0.0 +schema: + file: ./schema.graphql +indexerHints: + prune: auto +dataSources: + - kind: ethereum/contract + name: Contract + network: mainnet +``` + +## Important Considerations + +- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. + +- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). + +## Conclusion + +Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/nl/subgraphs/cookbook/timeseries.mdx b/website/src/pages/ko/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/nl/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/ko/subgraphs/best-practices/timeseries.mdx index 7c1c41008d29..cacdc44711fe 100644 --- a/website/src/pages/nl/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/ko/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ko/subgraphs/cookbook/_meta.js b/website/src/pages/ko/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/ko/subgraphs/cookbook/_meta.js +++ b/website/src/pages/ko/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/ko/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/ko/subgraphs/cookbook/avoid-eth-calls.mdx deleted file mode 100644 index ae29cdf03a34..000000000000 --- a/website/src/pages/ko/subgraphs/cookbook/avoid-eth-calls.mdx +++ /dev/null @@ -1,117 +0,0 @@ ---- -title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls -sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' ---- - -## TLDR - -`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. - -## Why Avoiding `eth_calls` Is a Best Practice - -Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. - -### What Does an eth_call Look Like? - -`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: - -```yaml -event Transfer(address indexed from, address indexed to, uint256 value); -``` - -Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, Transfer } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransfer(event: Transfer): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - // Bind the ERC20 contract instance to the given address: - let instance = ERC20.bind(event.address) - - // Retrieve pool information via eth_call - let poolInfo = instance.getPoolInfo(event.params.to) - - transaction.pool = poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is functional, however is not ideal as it slows down our subgraph’s indexing. - -## How to Eliminate `eth_calls` - -Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: - -``` -event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); -``` - -With this update, the subgraph can directly index the required data without external calls: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransferWithPool(event: TransferWithPool): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - transaction.pool = event.params.poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is much more performant as it has eliminated the need for `eth_calls`. - -## How to Optimize `eth_calls` - -If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. - -## Reducing the Runtime Overhead of `eth_calls` - -For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. - -Currently, `eth_calls` can only be declared for event handlers. In the manifest, write - -```yaml -event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) -handler: handleTransferWithPool -calls: - ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) -``` - -The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. - -The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. - -Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. - -## Conclusion - -You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ko/subgraphs/cookbook/cosmos.mdx b/website/src/pages/ko/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 5ccf1025ca47..000000000000 --- a/website/src/pages/ko/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Building Subgraphs on Cosmos ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## What are Cosmos subgraphs? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -There are four types of handlers supported in Cosmos subgraphs: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Even though all data can be accessed with a block handler, other handlers enable subgraph developers to process data in a much more granular way. - -## Building a Cosmos subgraph - -### Subgraph Dependencies - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Subgraph Main Components - -There are three key parts when it comes to defining a subgraph: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### Subgraph Manifest Definition - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### Schema Definition - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript Mappings - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Each handler type comes with its own data structure that is passed as an argument to a mapping function. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Message decoding - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Creating and building a Cosmos subgraph - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Deploying a Cosmos subgraph - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Querying a Cosmos subgraph - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Supported Cosmos Blockchains - -### Cosmos Hub - -#### What is Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### Networks - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### What is Osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### Networks - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## Example Subgraphs - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/ko/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/ko/subgraphs/cookbook/derivedfrom.mdx deleted file mode 100644 index a0942645c999..000000000000 --- a/website/src/pages/ko/subgraphs/cookbook/derivedfrom.mdx +++ /dev/null @@ -1,89 +0,0 @@ ---- -title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom -sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' ---- - -## TLDR - -Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. - -## How to Use the `@derivedFrom` Directive - -You just need to add a `@derivedFrom` directive after your array in your schema. Like this: - -```graphql -comments: [Comment!]! @derivedFrom(field: "post") -``` - -`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. - -### Example Use Case for `@derivedFrom` - -An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. - -Let’s start with our two entities, `Post` and `Comment` - -Without optimization, you could implement it like this with an array: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! -} - -type Comment @entity { - id: Bytes! - content: String! -} -``` - -Arrays like these will effectively store extra Comments data on the Post side of the relationship. - -Here’s what an optimized version looks like using `@derivedFrom`: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! @derivedFrom(field: "post") -} - -type Comment @entity { - id: Bytes! - content: String! - post: Post! -} -``` - -Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. - -This will not only make our subgraph more efficient, but it will also unlock three features: - -1. We can query the `Post` and see all of its comments. - -2. We can do a reverse lookup and query any `Comment` and see which post it comes from. - -3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. - -## Conclusion - -Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. - -For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ko/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/ko/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx deleted file mode 100644 index 511565bb3dd4..000000000000 --- a/website/src/pages/ko/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ /dev/null @@ -1,191 +0,0 @@ ---- -title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs -sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' ---- - -## TLDR - -Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. - -## Immutable Entities - -To make an entity immutable, we simply add `(immutable: true)` to an entity. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. - -Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. - -### Under the hood - -Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. - -### When not to use Immutable Entities - -If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. - -## Bytes as IDs - -Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. - -### Reasons to Not Use Bytes as IDs - -1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. -2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. -3. Indexing and querying performance improvements are not desired. - -### Concatenating With Bytes as IDs - -It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. - -Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. - -```typescript -export function handleTransfer(event: TransferEvent): void { - let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) - entity.from = event.params.from - entity.to = event.params.to - entity.value = event.params.value - - entity.blockNumber = event.block.number - entity.blockTimestamp = event.block.timestamp - entity.transactionHash = event.transaction.hash - - entity.save() -} -``` - -### Sorting With Bytes as IDs - -Sorting using Bytes as IDs is not optimal as seen in this example query and response. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: id) { - id - from - to - value - } -} -``` - -Query response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x00010000", - "from": "0xabcd...", - "to": "0x1234...", - "value": "256" - }, - { - "id": "0x00020000", - "from": "0xefgh...", - "to": "0x5678...", - "value": "512" - }, - { - "id": "0x01000000", - "from": "0xijkl...", - "to": "0x9abc...", - "value": "1" - } - ] - } -} -``` - -The IDs are returned as hex. - -To improve sorting, we should create another field on the entity that is a BigInt. - -```graphql -type Transfer @entity { - id: Bytes! - from: Bytes! # address - to: Bytes! # address - value: BigInt! # unit256 - tokenId: BigInt! # uint256 -} -``` - -This will allow for sorting to be optimized sequentially. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: tokenId) { - id - tokenId - } -} -``` - -Query Response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x…", - "tokenId": "1" - }, - { - "id": "0x…", - "tokenId": "2" - }, - { - "id": "0x…", - "tokenId": "3" - } - ] - } -} -``` - -## Conclusion - -Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. - -Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ko/subgraphs/cookbook/pruning.mdx b/website/src/pages/ko/subgraphs/cookbook/pruning.mdx deleted file mode 100644 index e212d5d02bc9..000000000000 --- a/website/src/pages/ko/subgraphs/cookbook/pruning.mdx +++ /dev/null @@ -1,56 +0,0 @@ ---- -title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning -sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' ---- - -## TLDR - -[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. - -## How to Prune a Subgraph With `indexerHints` - -Add a section called `indexerHints` in the manifest. - -`indexerHints` has three `prune` options: - -- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. -- `prune: `: Sets a custom limit on the number of historical blocks to retain. -- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. - -We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: - -```yaml -specVersion: 1.0.0 -schema: - file: ./schema.graphql -indexerHints: - prune: auto -dataSources: - - kind: ethereum/contract - name: Contract - network: mainnet -``` - -## Important Considerations - -- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. - -- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). - -## Conclusion - -Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ko/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/ko/subgraphs/developing/creating/graph-ts/api.mdx index b5cec3b091e4..35bb04826c98 100644 --- a/website/src/pages/ko/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/ko/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/ko/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/ko/subgraphs/developing/creating/install-the-cli.mdx index a58e6be82324..674cc5bc22d2 100644 --- a/website/src/pages/ko/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/ko/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Install the Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Overview diff --git a/website/src/pages/ko/subgraphs/developing/deploying/_meta.js b/website/src/pages/ko/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/ko/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/ko/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/ko/subgraphs/querying/best-practices.mdx b/website/src/pages/ko/subgraphs/querying/best-practices.mdx index 3736fa32faeb..ff5f381e2993 100644 --- a/website/src/pages/ko/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/ko/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Sending a query to a GraphQL API diff --git a/website/src/pages/ko/subgraphs/querying/managing-api-keys.mdx b/website/src/pages/ko/subgraphs/querying/managing-api-keys.mdx index f7aff33ea926..6964b1a7ad9b 100644 --- a/website/src/pages/ko/subgraphs/querying/managing-api-keys.mdx +++ b/website/src/pages/ko/subgraphs/querying/managing-api-keys.mdx @@ -1,5 +1,5 @@ --- -title: Managing your API keys +title: Managing API keys --- ## Overview diff --git a/website/src/pages/en/substreams/developing/sinks/sinks.mdx b/website/src/pages/ko/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/en/substreams/developing/sinks/sinks.mdx rename to website/src/pages/ko/substreams/developing/sinks.mdx diff --git a/website/src/pages/ko/substreams/developing/sinks/_meta.js b/website/src/pages/ko/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/ko/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/ko/substreams/quick-start.mdx b/website/src/pages/ko/substreams/quick-start.mdx index 34e59b54491b..b5eec572b00a 100644 --- a/website/src/pages/ko/substreams/quick-start.mdx +++ b/website/src/pages/ko/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/mr/resources/_meta-titles.json b/website/src/pages/mr/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/mr/resources/_meta-titles.json +++ b/website/src/pages/mr/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/mr/resources/_meta.js b/website/src/pages/mr/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/mr/resources/_meta.js +++ b/website/src/pages/mr/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/mr/resources/release-notes/_meta.js b/website/src/pages/mr/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/mr/resources/release-notes/_meta.js rename to website/src/pages/mr/resources/migration-guides/_meta.js diff --git a/website/src/pages/mr/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/mr/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/mr/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/mr/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/mr/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/mr/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 99% rename from website/src/pages/mr/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/mr/resources/migration-guides/graphql-validations-migration-guide.mdx index b0540fd8bbc8..b0910e65fc1b 100644 --- a/website/src/pages/mr/resources/release-notes/graphql-validations-migration-guide.mdx +++ b/website/src/pages/mr/resources/migration-guides/graphql-validations-migration-guide.mdx @@ -1,5 +1,5 @@ --- -title: GraphQL Validations migration guide +title: GraphQL Validations Migration Guide --- Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). diff --git a/website/src/pages/mr/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/mr/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/mr/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/mr/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/mr/sps/sps-faq.mdx b/website/src/pages/mr/sps/sps-faq.mdx index 537f29b09ea6..abc1f3906686 100644 --- a/website/src/pages/mr/sps/sps-faq.mdx +++ b/website/src/pages/mr/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/mr/subgraphs/_meta-titles.json b/website/src/pages/mr/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/mr/subgraphs/_meta-titles.json +++ b/website/src/pages/mr/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/mr/subgraphs/_meta.js b/website/src/pages/mr/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/mr/subgraphs/_meta.js +++ b/website/src/pages/mr/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/mr/subgraphs/best-practices/_meta.js b/website/src/pages/mr/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/mr/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/mr/subgraphs/best-practices/avoid-eth-calls.mdx b/website/src/pages/mr/subgraphs/best-practices/avoid-eth-calls.mdx new file mode 100644 index 000000000000..e40a7b3712e4 --- /dev/null +++ b/website/src/pages/mr/subgraphs/best-practices/avoid-eth-calls.mdx @@ -0,0 +1,117 @@ +--- +title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls +sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' +--- + +## TLDR + +`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. + +## Why Avoiding `eth_calls` Is a Best Practice + +Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. + +### What Does an eth_call Look Like? + +`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: + +```yaml +event Transfer(address indexed from, address indexed to, uint256 value); +``` + +Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, Transfer } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransfer(event: Transfer): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + // Bind the ERC20 contract instance to the given address: + let instance = ERC20.bind(event.address) + + // Retrieve pool information via eth_call + let poolInfo = instance.getPoolInfo(event.params.to) + + transaction.pool = poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is functional, however is not ideal as it slows down our subgraph’s indexing. + +## How to Eliminate `eth_calls` + +Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: + +``` +event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); +``` + +With this update, the subgraph can directly index the required data without external calls: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransferWithPool(event: TransferWithPool): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + transaction.pool = event.params.poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is much more performant as it has eliminated the need for `eth_calls`. + +## How to Optimize `eth_calls` + +If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. + +## Reducing the Runtime Overhead of `eth_calls` + +For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. + +Currently, `eth_calls` can only be declared for event handlers. In the manifest, write + +```yaml +event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) +handler: handleTransferWithPool +calls: + ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) +``` + +The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. + +The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. + +Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. + +## Conclusion + +You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/mr/subgraphs/best-practices/derivedfrom.mdx b/website/src/pages/mr/subgraphs/best-practices/derivedfrom.mdx new file mode 100644 index 000000000000..db3a49928c89 --- /dev/null +++ b/website/src/pages/mr/subgraphs/best-practices/derivedfrom.mdx @@ -0,0 +1,89 @@ +--- +title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom +sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' +--- + +## TLDR + +Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. + +## How to Use the `@derivedFrom` Directive + +You just need to add a `@derivedFrom` directive after your array in your schema. Like this: + +```graphql +comments: [Comment!]! @derivedFrom(field: "post") +``` + +`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. + +### Example Use Case for `@derivedFrom` + +An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. + +Let’s start with our two entities, `Post` and `Comment` + +Without optimization, you could implement it like this with an array: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! +} + +type Comment @entity { + id: Bytes! + content: String! +} +``` + +Arrays like these will effectively store extra Comments data on the Post side of the relationship. + +Here’s what an optimized version looks like using `@derivedFrom`: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! @derivedFrom(field: "post") +} + +type Comment @entity { + id: Bytes! + content: String! + post: Post! +} +``` + +Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. + +This will not only make our subgraph more efficient, but it will also unlock three features: + +1. We can query the `Post` and see all of its comments. + +2. We can do a reverse lookup and query any `Comment` and see which post it comes from. + +3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. + +## Conclusion + +Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. + +For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/mr/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/mr/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/mr/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/mr/subgraphs/best-practices/grafting-hotfix.mdx index b24622bf99f5..0989034a01a3 100644 --- a/website/src/pages/mr/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/mr/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/mr/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx b/website/src/pages/mr/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx new file mode 100644 index 000000000000..6ff60ec9ab34 --- /dev/null +++ b/website/src/pages/mr/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -0,0 +1,191 @@ +--- +title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs +sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' +--- + +## TLDR + +Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. + +## Immutable Entities + +To make an entity immutable, we simply add `(immutable: true)` to an entity. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. + +Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. + +### Under the hood + +Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. + +### When not to use Immutable Entities + +If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. + +## Bytes as IDs + +Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. + +### Reasons to Not Use Bytes as IDs + +1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. +2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. +3. Indexing and querying performance improvements are not desired. + +### Concatenating With Bytes as IDs + +It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. + +Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. + +```typescript +export function handleTransfer(event: TransferEvent): void { + let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) + entity.from = event.params.from + entity.to = event.params.to + entity.value = event.params.value + + entity.blockNumber = event.block.number + entity.blockTimestamp = event.block.timestamp + entity.transactionHash = event.transaction.hash + + entity.save() +} +``` + +### Sorting With Bytes as IDs + +Sorting using Bytes as IDs is not optimal as seen in this example query and response. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: id) { + id + from + to + value + } +} +``` + +Query response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x00010000", + "from": "0xabcd...", + "to": "0x1234...", + "value": "256" + }, + { + "id": "0x00020000", + "from": "0xefgh...", + "to": "0x5678...", + "value": "512" + }, + { + "id": "0x01000000", + "from": "0xijkl...", + "to": "0x9abc...", + "value": "1" + } + ] + } +} +``` + +The IDs are returned as hex. + +To improve sorting, we should create another field on the entity that is a BigInt. + +```graphql +type Transfer @entity { + id: Bytes! + from: Bytes! # address + to: Bytes! # address + value: BigInt! # unit256 + tokenId: BigInt! # uint256 +} +``` + +This will allow for sorting to be optimized sequentially. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: tokenId) { + id + tokenId + } +} +``` + +Query Response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x…", + "tokenId": "1" + }, + { + "id": "0x…", + "tokenId": "2" + }, + { + "id": "0x…", + "tokenId": "3" + } + ] + } +} +``` + +## Conclusion + +Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. + +Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/mr/subgraphs/best-practices/pruning.mdx b/website/src/pages/mr/subgraphs/best-practices/pruning.mdx new file mode 100644 index 000000000000..1b51dde8894f --- /dev/null +++ b/website/src/pages/mr/subgraphs/best-practices/pruning.mdx @@ -0,0 +1,56 @@ +--- +title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning +sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' +--- + +## TLDR + +[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. + +## How to Prune a Subgraph With `indexerHints` + +Add a section called `indexerHints` in the manifest. + +`indexerHints` has three `prune` options: + +- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. +- `prune: `: Sets a custom limit on the number of historical blocks to retain. +- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. + +We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: + +```yaml +specVersion: 1.0.0 +schema: + file: ./schema.graphql +indexerHints: + prune: auto +dataSources: + - kind: ethereum/contract + name: Contract + network: mainnet +``` + +## Important Considerations + +- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. + +- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). + +## Conclusion + +Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/mr/subgraphs/cookbook/timeseries.mdx b/website/src/pages/mr/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/mr/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/mr/subgraphs/best-practices/timeseries.mdx index a20fbdeccfd8..239c7e0158db 100644 --- a/website/src/pages/mr/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/mr/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/mr/subgraphs/cookbook/_meta.js b/website/src/pages/mr/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/mr/subgraphs/cookbook/_meta.js +++ b/website/src/pages/mr/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/mr/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/mr/subgraphs/cookbook/avoid-eth-calls.mdx deleted file mode 100644 index ae29cdf03a34..000000000000 --- a/website/src/pages/mr/subgraphs/cookbook/avoid-eth-calls.mdx +++ /dev/null @@ -1,117 +0,0 @@ ---- -title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls -sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' ---- - -## TLDR - -`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. - -## Why Avoiding `eth_calls` Is a Best Practice - -Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. - -### What Does an eth_call Look Like? - -`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: - -```yaml -event Transfer(address indexed from, address indexed to, uint256 value); -``` - -Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, Transfer } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransfer(event: Transfer): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - // Bind the ERC20 contract instance to the given address: - let instance = ERC20.bind(event.address) - - // Retrieve pool information via eth_call - let poolInfo = instance.getPoolInfo(event.params.to) - - transaction.pool = poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is functional, however is not ideal as it slows down our subgraph’s indexing. - -## How to Eliminate `eth_calls` - -Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: - -``` -event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); -``` - -With this update, the subgraph can directly index the required data without external calls: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransferWithPool(event: TransferWithPool): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - transaction.pool = event.params.poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is much more performant as it has eliminated the need for `eth_calls`. - -## How to Optimize `eth_calls` - -If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. - -## Reducing the Runtime Overhead of `eth_calls` - -For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. - -Currently, `eth_calls` can only be declared for event handlers. In the manifest, write - -```yaml -event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) -handler: handleTransferWithPool -calls: - ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) -``` - -The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. - -The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. - -Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. - -## Conclusion - -You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/mr/subgraphs/cookbook/cosmos.mdx b/website/src/pages/mr/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 16b5b216fd3a..000000000000 --- a/website/src/pages/mr/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: कॉसमॉस वर सबग्राफ तयार करणे ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## कॉसमॉस सबग्राफ काय आहेत? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -कॉसमॉस सबग्राफमध्ये चार प्रकारचे हँडलर समर्थित आहेत: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -जरी सर्व डेटा ब्लॉक हँडलरने ऍक्सेस केला जाऊ शकतो, इतर हँडलर्स सबग्राफ डेव्हलपरला डेटावर अधिक बारीक पद्धतीने प्रक्रिया करण्यास सक्षम करतात. - -## कॉसमॉस सबग्राफ तयार करणे - -### सबग्राफ अवलंबित्व - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### सबग्राफ मुख्य घटक - -सबग्राफ परिभाषित करताना तीन प्रमुख भाग आहेत: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### सबग्राफ मॅनिफेस्ट व्याख्या - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### स्कीमा व्याख्या - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### असेंबलीस्क्रिप्ट मॅपिंग - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -प्रत्येक हँडलर प्रकार त्याच्या स्वतःच्या डेटा स्ट्रक्चरसह येतो जो मॅपिंग फंक्शनला युक्तिवाद म्हणून पास केला जातो. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### संदेश डीकोडिंग - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## कॉसमॉस सबग्राफ तयार करणे आणि तयार करणे - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ आलेख कोडजेन -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ आलेख बिल्ड -``` - -## कॉसमॉस सबग्राफ तैनात करणे - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## कॉसमॉस सबग्राफची चौकशी करत आहे - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## समर्थित कॉसमॉस ब्लॉकचेन - -### कॉसमॉस हब - -#### कॉसमॉस हब म्हणजे काय? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### नेटवर्क्स - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### ऑस्मोसिस - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### ऑस्मोसिस म्हणजे काय? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### नेटवर्क्स - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## उदाहरणे सबग्राफ - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/mr/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/mr/subgraphs/cookbook/derivedfrom.mdx deleted file mode 100644 index a0942645c999..000000000000 --- a/website/src/pages/mr/subgraphs/cookbook/derivedfrom.mdx +++ /dev/null @@ -1,89 +0,0 @@ ---- -title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom -sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' ---- - -## TLDR - -Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. - -## How to Use the `@derivedFrom` Directive - -You just need to add a `@derivedFrom` directive after your array in your schema. Like this: - -```graphql -comments: [Comment!]! @derivedFrom(field: "post") -``` - -`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. - -### Example Use Case for `@derivedFrom` - -An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. - -Let’s start with our two entities, `Post` and `Comment` - -Without optimization, you could implement it like this with an array: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! -} - -type Comment @entity { - id: Bytes! - content: String! -} -``` - -Arrays like these will effectively store extra Comments data on the Post side of the relationship. - -Here’s what an optimized version looks like using `@derivedFrom`: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! @derivedFrom(field: "post") -} - -type Comment @entity { - id: Bytes! - content: String! - post: Post! -} -``` - -Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. - -This will not only make our subgraph more efficient, but it will also unlock three features: - -1. We can query the `Post` and see all of its comments. - -2. We can do a reverse lookup and query any `Comment` and see which post it comes from. - -3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. - -## Conclusion - -Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. - -For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/mr/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/mr/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx deleted file mode 100644 index 511565bb3dd4..000000000000 --- a/website/src/pages/mr/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ /dev/null @@ -1,191 +0,0 @@ ---- -title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs -sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' ---- - -## TLDR - -Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. - -## Immutable Entities - -To make an entity immutable, we simply add `(immutable: true)` to an entity. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. - -Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. - -### Under the hood - -Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. - -### When not to use Immutable Entities - -If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. - -## Bytes as IDs - -Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. - -### Reasons to Not Use Bytes as IDs - -1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. -2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. -3. Indexing and querying performance improvements are not desired. - -### Concatenating With Bytes as IDs - -It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. - -Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. - -```typescript -export function handleTransfer(event: TransferEvent): void { - let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) - entity.from = event.params.from - entity.to = event.params.to - entity.value = event.params.value - - entity.blockNumber = event.block.number - entity.blockTimestamp = event.block.timestamp - entity.transactionHash = event.transaction.hash - - entity.save() -} -``` - -### Sorting With Bytes as IDs - -Sorting using Bytes as IDs is not optimal as seen in this example query and response. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: id) { - id - from - to - value - } -} -``` - -Query response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x00010000", - "from": "0xabcd...", - "to": "0x1234...", - "value": "256" - }, - { - "id": "0x00020000", - "from": "0xefgh...", - "to": "0x5678...", - "value": "512" - }, - { - "id": "0x01000000", - "from": "0xijkl...", - "to": "0x9abc...", - "value": "1" - } - ] - } -} -``` - -The IDs are returned as hex. - -To improve sorting, we should create another field on the entity that is a BigInt. - -```graphql -type Transfer @entity { - id: Bytes! - from: Bytes! # address - to: Bytes! # address - value: BigInt! # unit256 - tokenId: BigInt! # uint256 -} -``` - -This will allow for sorting to be optimized sequentially. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: tokenId) { - id - tokenId - } -} -``` - -Query Response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x…", - "tokenId": "1" - }, - { - "id": "0x…", - "tokenId": "2" - }, - { - "id": "0x…", - "tokenId": "3" - } - ] - } -} -``` - -## Conclusion - -Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. - -Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/mr/subgraphs/cookbook/pruning.mdx b/website/src/pages/mr/subgraphs/cookbook/pruning.mdx deleted file mode 100644 index e212d5d02bc9..000000000000 --- a/website/src/pages/mr/subgraphs/cookbook/pruning.mdx +++ /dev/null @@ -1,56 +0,0 @@ ---- -title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning -sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' ---- - -## TLDR - -[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. - -## How to Prune a Subgraph With `indexerHints` - -Add a section called `indexerHints` in the manifest. - -`indexerHints` has three `prune` options: - -- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. -- `prune: `: Sets a custom limit on the number of historical blocks to retain. -- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. - -We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: - -```yaml -specVersion: 1.0.0 -schema: - file: ./schema.graphql -indexerHints: - prune: auto -dataSources: - - kind: ethereum/contract - name: Contract - network: mainnet -``` - -## Important Considerations - -- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. - -- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). - -## Conclusion - -Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/mr/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/mr/subgraphs/developing/creating/graph-ts/api.mdx index fabedbe85e2b..a807b884e30c 100644 --- a/website/src/pages/mr/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/mr/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: असेंबलीस्क्रिप्ट API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/mr/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/mr/subgraphs/developing/creating/install-the-cli.mdx index 210e247b2270..51dfb940edcb 100644 --- a/website/src/pages/mr/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/mr/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Install the Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## सविश्लेषण diff --git a/website/src/pages/mr/subgraphs/developing/deploying/_meta.js b/website/src/pages/mr/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/mr/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/mr/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/mr/subgraphs/querying/best-practices.mdx b/website/src/pages/mr/subgraphs/querying/best-practices.mdx index c2e39380c4fe..484f1a2d891a 100644 --- a/website/src/pages/mr/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/mr/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Sending a query to a GraphQL API diff --git a/website/src/pages/mr/subgraphs/querying/managing-api-keys.mdx b/website/src/pages/mr/subgraphs/querying/managing-api-keys.mdx index 945a4add2851..167edacef164 100644 --- a/website/src/pages/mr/subgraphs/querying/managing-api-keys.mdx +++ b/website/src/pages/mr/subgraphs/querying/managing-api-keys.mdx @@ -1,5 +1,5 @@ --- -title: Managing your API keys +title: Managing API keys --- ## सविश्लेषण diff --git a/website/src/pages/mr/substreams/developing/sinks/sinks.mdx b/website/src/pages/mr/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/mr/substreams/developing/sinks/sinks.mdx rename to website/src/pages/mr/substreams/developing/sinks.mdx diff --git a/website/src/pages/mr/substreams/developing/sinks/_meta.js b/website/src/pages/mr/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/mr/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/mr/substreams/quick-start.mdx b/website/src/pages/mr/substreams/quick-start.mdx index 54ead5d1caea..a2f7e3e938bd 100644 --- a/website/src/pages/mr/substreams/quick-start.mdx +++ b/website/src/pages/mr/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/nl/resources/_meta-titles.json b/website/src/pages/nl/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/nl/resources/_meta-titles.json +++ b/website/src/pages/nl/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/nl/resources/_meta.js b/website/src/pages/nl/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/nl/resources/_meta.js +++ b/website/src/pages/nl/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/nl/resources/release-notes/_meta.js b/website/src/pages/nl/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/nl/resources/release-notes/_meta.js rename to website/src/pages/nl/resources/migration-guides/_meta.js diff --git a/website/src/pages/nl/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/nl/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/nl/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/nl/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/ko/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/nl/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 99% rename from website/src/pages/ko/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/nl/resources/migration-guides/graphql-validations-migration-guide.mdx index 4d909e8970a8..29fed533ef8c 100644 --- a/website/src/pages/ko/resources/release-notes/graphql-validations-migration-guide.mdx +++ b/website/src/pages/nl/resources/migration-guides/graphql-validations-migration-guide.mdx @@ -1,5 +1,5 @@ --- -title: GraphQL Validations migration guide +title: GraphQL Validations Migration Guide --- Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). diff --git a/website/src/pages/nl/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/nl/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/nl/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/nl/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/nl/sps/sps-faq.mdx b/website/src/pages/nl/sps/sps-faq.mdx index 537f29b09ea6..abc1f3906686 100644 --- a/website/src/pages/nl/sps/sps-faq.mdx +++ b/website/src/pages/nl/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/nl/subgraphs/_meta-titles.json b/website/src/pages/nl/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/nl/subgraphs/_meta-titles.json +++ b/website/src/pages/nl/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/nl/subgraphs/_meta.js b/website/src/pages/nl/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/nl/subgraphs/_meta.js +++ b/website/src/pages/nl/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/nl/subgraphs/best-practices/_meta.js b/website/src/pages/nl/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/nl/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/nl/subgraphs/best-practices/avoid-eth-calls.mdx b/website/src/pages/nl/subgraphs/best-practices/avoid-eth-calls.mdx new file mode 100644 index 000000000000..e40a7b3712e4 --- /dev/null +++ b/website/src/pages/nl/subgraphs/best-practices/avoid-eth-calls.mdx @@ -0,0 +1,117 @@ +--- +title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls +sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' +--- + +## TLDR + +`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. + +## Why Avoiding `eth_calls` Is a Best Practice + +Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. + +### What Does an eth_call Look Like? + +`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: + +```yaml +event Transfer(address indexed from, address indexed to, uint256 value); +``` + +Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, Transfer } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransfer(event: Transfer): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + // Bind the ERC20 contract instance to the given address: + let instance = ERC20.bind(event.address) + + // Retrieve pool information via eth_call + let poolInfo = instance.getPoolInfo(event.params.to) + + transaction.pool = poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is functional, however is not ideal as it slows down our subgraph’s indexing. + +## How to Eliminate `eth_calls` + +Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: + +``` +event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); +``` + +With this update, the subgraph can directly index the required data without external calls: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransferWithPool(event: TransferWithPool): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + transaction.pool = event.params.poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is much more performant as it has eliminated the need for `eth_calls`. + +## How to Optimize `eth_calls` + +If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. + +## Reducing the Runtime Overhead of `eth_calls` + +For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. + +Currently, `eth_calls` can only be declared for event handlers. In the manifest, write + +```yaml +event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) +handler: handleTransferWithPool +calls: + ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) +``` + +The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. + +The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. + +Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. + +## Conclusion + +You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/nl/subgraphs/best-practices/derivedfrom.mdx b/website/src/pages/nl/subgraphs/best-practices/derivedfrom.mdx new file mode 100644 index 000000000000..db3a49928c89 --- /dev/null +++ b/website/src/pages/nl/subgraphs/best-practices/derivedfrom.mdx @@ -0,0 +1,89 @@ +--- +title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom +sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' +--- + +## TLDR + +Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. + +## How to Use the `@derivedFrom` Directive + +You just need to add a `@derivedFrom` directive after your array in your schema. Like this: + +```graphql +comments: [Comment!]! @derivedFrom(field: "post") +``` + +`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. + +### Example Use Case for `@derivedFrom` + +An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. + +Let’s start with our two entities, `Post` and `Comment` + +Without optimization, you could implement it like this with an array: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! +} + +type Comment @entity { + id: Bytes! + content: String! +} +``` + +Arrays like these will effectively store extra Comments data on the Post side of the relationship. + +Here’s what an optimized version looks like using `@derivedFrom`: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! @derivedFrom(field: "post") +} + +type Comment @entity { + id: Bytes! + content: String! + post: Post! +} +``` + +Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. + +This will not only make our subgraph more efficient, but it will also unlock three features: + +1. We can query the `Post` and see all of its comments. + +2. We can do a reverse lookup and query any `Comment` and see which post it comes from. + +3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. + +## Conclusion + +Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. + +For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ko/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/nl/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/ko/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/nl/subgraphs/best-practices/grafting-hotfix.mdx index 910e32cfacde..d514e1633c75 100644 --- a/website/src/pages/ko/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/nl/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/nl/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx b/website/src/pages/nl/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx new file mode 100644 index 000000000000..6ff60ec9ab34 --- /dev/null +++ b/website/src/pages/nl/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -0,0 +1,191 @@ +--- +title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs +sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' +--- + +## TLDR + +Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. + +## Immutable Entities + +To make an entity immutable, we simply add `(immutable: true)` to an entity. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. + +Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. + +### Under the hood + +Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. + +### When not to use Immutable Entities + +If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. + +## Bytes as IDs + +Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. + +### Reasons to Not Use Bytes as IDs + +1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. +2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. +3. Indexing and querying performance improvements are not desired. + +### Concatenating With Bytes as IDs + +It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. + +Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. + +```typescript +export function handleTransfer(event: TransferEvent): void { + let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) + entity.from = event.params.from + entity.to = event.params.to + entity.value = event.params.value + + entity.blockNumber = event.block.number + entity.blockTimestamp = event.block.timestamp + entity.transactionHash = event.transaction.hash + + entity.save() +} +``` + +### Sorting With Bytes as IDs + +Sorting using Bytes as IDs is not optimal as seen in this example query and response. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: id) { + id + from + to + value + } +} +``` + +Query response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x00010000", + "from": "0xabcd...", + "to": "0x1234...", + "value": "256" + }, + { + "id": "0x00020000", + "from": "0xefgh...", + "to": "0x5678...", + "value": "512" + }, + { + "id": "0x01000000", + "from": "0xijkl...", + "to": "0x9abc...", + "value": "1" + } + ] + } +} +``` + +The IDs are returned as hex. + +To improve sorting, we should create another field on the entity that is a BigInt. + +```graphql +type Transfer @entity { + id: Bytes! + from: Bytes! # address + to: Bytes! # address + value: BigInt! # unit256 + tokenId: BigInt! # uint256 +} +``` + +This will allow for sorting to be optimized sequentially. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: tokenId) { + id + tokenId + } +} +``` + +Query Response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x…", + "tokenId": "1" + }, + { + "id": "0x…", + "tokenId": "2" + }, + { + "id": "0x…", + "tokenId": "3" + } + ] + } +} +``` + +## Conclusion + +Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. + +Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/nl/subgraphs/best-practices/pruning.mdx b/website/src/pages/nl/subgraphs/best-practices/pruning.mdx new file mode 100644 index 000000000000..1b51dde8894f --- /dev/null +++ b/website/src/pages/nl/subgraphs/best-practices/pruning.mdx @@ -0,0 +1,56 @@ +--- +title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning +sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' +--- + +## TLDR + +[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. + +## How to Prune a Subgraph With `indexerHints` + +Add a section called `indexerHints` in the manifest. + +`indexerHints` has three `prune` options: + +- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. +- `prune: `: Sets a custom limit on the number of historical blocks to retain. +- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. + +We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: + +```yaml +specVersion: 1.0.0 +schema: + file: ./schema.graphql +indexerHints: + prune: auto +dataSources: + - kind: ethereum/contract + name: Contract + network: mainnet +``` + +## Important Considerations + +- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. + +- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). + +## Conclusion + +Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ko/subgraphs/cookbook/timeseries.mdx b/website/src/pages/nl/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/ko/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/nl/subgraphs/best-practices/timeseries.mdx index 7c1c41008d29..cacdc44711fe 100644 --- a/website/src/pages/ko/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/nl/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/nl/subgraphs/cookbook/_meta.js b/website/src/pages/nl/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/nl/subgraphs/cookbook/_meta.js +++ b/website/src/pages/nl/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/nl/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/nl/subgraphs/cookbook/avoid-eth-calls.mdx deleted file mode 100644 index ae29cdf03a34..000000000000 --- a/website/src/pages/nl/subgraphs/cookbook/avoid-eth-calls.mdx +++ /dev/null @@ -1,117 +0,0 @@ ---- -title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls -sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' ---- - -## TLDR - -`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. - -## Why Avoiding `eth_calls` Is a Best Practice - -Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. - -### What Does an eth_call Look Like? - -`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: - -```yaml -event Transfer(address indexed from, address indexed to, uint256 value); -``` - -Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, Transfer } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransfer(event: Transfer): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - // Bind the ERC20 contract instance to the given address: - let instance = ERC20.bind(event.address) - - // Retrieve pool information via eth_call - let poolInfo = instance.getPoolInfo(event.params.to) - - transaction.pool = poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is functional, however is not ideal as it slows down our subgraph’s indexing. - -## How to Eliminate `eth_calls` - -Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: - -``` -event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); -``` - -With this update, the subgraph can directly index the required data without external calls: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransferWithPool(event: TransferWithPool): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - transaction.pool = event.params.poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is much more performant as it has eliminated the need for `eth_calls`. - -## How to Optimize `eth_calls` - -If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. - -## Reducing the Runtime Overhead of `eth_calls` - -For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. - -Currently, `eth_calls` can only be declared for event handlers. In the manifest, write - -```yaml -event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) -handler: handleTransferWithPool -calls: - ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) -``` - -The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. - -The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. - -Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. - -## Conclusion - -You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/nl/subgraphs/cookbook/cosmos.mdx b/website/src/pages/nl/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 5ccf1025ca47..000000000000 --- a/website/src/pages/nl/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Building Subgraphs on Cosmos ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## What are Cosmos subgraphs? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -There are four types of handlers supported in Cosmos subgraphs: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Even though all data can be accessed with a block handler, other handlers enable subgraph developers to process data in a much more granular way. - -## Building a Cosmos subgraph - -### Subgraph Dependencies - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Subgraph Main Components - -There are three key parts when it comes to defining a subgraph: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### Subgraph Manifest Definition - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### Schema Definition - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript Mappings - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Each handler type comes with its own data structure that is passed as an argument to a mapping function. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Message decoding - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Creating and building a Cosmos subgraph - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Deploying a Cosmos subgraph - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Querying a Cosmos subgraph - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Supported Cosmos Blockchains - -### Cosmos Hub - -#### What is Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### Networks - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### What is Osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### Networks - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## Example Subgraphs - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/nl/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/nl/subgraphs/cookbook/derivedfrom.mdx deleted file mode 100644 index a0942645c999..000000000000 --- a/website/src/pages/nl/subgraphs/cookbook/derivedfrom.mdx +++ /dev/null @@ -1,89 +0,0 @@ ---- -title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom -sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' ---- - -## TLDR - -Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. - -## How to Use the `@derivedFrom` Directive - -You just need to add a `@derivedFrom` directive after your array in your schema. Like this: - -```graphql -comments: [Comment!]! @derivedFrom(field: "post") -``` - -`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. - -### Example Use Case for `@derivedFrom` - -An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. - -Let’s start with our two entities, `Post` and `Comment` - -Without optimization, you could implement it like this with an array: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! -} - -type Comment @entity { - id: Bytes! - content: String! -} -``` - -Arrays like these will effectively store extra Comments data on the Post side of the relationship. - -Here’s what an optimized version looks like using `@derivedFrom`: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! @derivedFrom(field: "post") -} - -type Comment @entity { - id: Bytes! - content: String! - post: Post! -} -``` - -Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. - -This will not only make our subgraph more efficient, but it will also unlock three features: - -1. We can query the `Post` and see all of its comments. - -2. We can do a reverse lookup and query any `Comment` and see which post it comes from. - -3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. - -## Conclusion - -Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. - -For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/nl/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/nl/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx deleted file mode 100644 index 511565bb3dd4..000000000000 --- a/website/src/pages/nl/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ /dev/null @@ -1,191 +0,0 @@ ---- -title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs -sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' ---- - -## TLDR - -Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. - -## Immutable Entities - -To make an entity immutable, we simply add `(immutable: true)` to an entity. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. - -Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. - -### Under the hood - -Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. - -### When not to use Immutable Entities - -If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. - -## Bytes as IDs - -Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. - -### Reasons to Not Use Bytes as IDs - -1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. -2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. -3. Indexing and querying performance improvements are not desired. - -### Concatenating With Bytes as IDs - -It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. - -Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. - -```typescript -export function handleTransfer(event: TransferEvent): void { - let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) - entity.from = event.params.from - entity.to = event.params.to - entity.value = event.params.value - - entity.blockNumber = event.block.number - entity.blockTimestamp = event.block.timestamp - entity.transactionHash = event.transaction.hash - - entity.save() -} -``` - -### Sorting With Bytes as IDs - -Sorting using Bytes as IDs is not optimal as seen in this example query and response. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: id) { - id - from - to - value - } -} -``` - -Query response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x00010000", - "from": "0xabcd...", - "to": "0x1234...", - "value": "256" - }, - { - "id": "0x00020000", - "from": "0xefgh...", - "to": "0x5678...", - "value": "512" - }, - { - "id": "0x01000000", - "from": "0xijkl...", - "to": "0x9abc...", - "value": "1" - } - ] - } -} -``` - -The IDs are returned as hex. - -To improve sorting, we should create another field on the entity that is a BigInt. - -```graphql -type Transfer @entity { - id: Bytes! - from: Bytes! # address - to: Bytes! # address - value: BigInt! # unit256 - tokenId: BigInt! # uint256 -} -``` - -This will allow for sorting to be optimized sequentially. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: tokenId) { - id - tokenId - } -} -``` - -Query Response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x…", - "tokenId": "1" - }, - { - "id": "0x…", - "tokenId": "2" - }, - { - "id": "0x…", - "tokenId": "3" - } - ] - } -} -``` - -## Conclusion - -Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. - -Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/nl/subgraphs/cookbook/pruning.mdx b/website/src/pages/nl/subgraphs/cookbook/pruning.mdx deleted file mode 100644 index e212d5d02bc9..000000000000 --- a/website/src/pages/nl/subgraphs/cookbook/pruning.mdx +++ /dev/null @@ -1,56 +0,0 @@ ---- -title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning -sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' ---- - -## TLDR - -[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. - -## How to Prune a Subgraph With `indexerHints` - -Add a section called `indexerHints` in the manifest. - -`indexerHints` has three `prune` options: - -- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. -- `prune: `: Sets a custom limit on the number of historical blocks to retain. -- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. - -We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: - -```yaml -specVersion: 1.0.0 -schema: - file: ./schema.graphql -indexerHints: - prune: auto -dataSources: - - kind: ethereum/contract - name: Contract - network: mainnet -``` - -## Important Considerations - -- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. - -- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). - -## Conclusion - -Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/nl/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/nl/subgraphs/developing/creating/graph-ts/api.mdx index b5cec3b091e4..35bb04826c98 100644 --- a/website/src/pages/nl/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/nl/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/nl/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/nl/subgraphs/developing/creating/install-the-cli.mdx index 87c33efe428e..8bf0b4dfca9f 100644 --- a/website/src/pages/nl/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/nl/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Install the Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Overview diff --git a/website/src/pages/nl/subgraphs/developing/deploying/_meta.js b/website/src/pages/nl/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/nl/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/nl/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/nl/subgraphs/querying/best-practices.mdx b/website/src/pages/nl/subgraphs/querying/best-practices.mdx index 3736fa32faeb..ff5f381e2993 100644 --- a/website/src/pages/nl/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/nl/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Sending a query to a GraphQL API diff --git a/website/src/pages/nl/subgraphs/querying/managing-api-keys.mdx b/website/src/pages/nl/subgraphs/querying/managing-api-keys.mdx index f7aff33ea926..6964b1a7ad9b 100644 --- a/website/src/pages/nl/subgraphs/querying/managing-api-keys.mdx +++ b/website/src/pages/nl/subgraphs/querying/managing-api-keys.mdx @@ -1,5 +1,5 @@ --- -title: Managing your API keys +title: Managing API keys --- ## Overview diff --git a/website/src/pages/ko/substreams/developing/sinks/sinks.mdx b/website/src/pages/nl/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/ko/substreams/developing/sinks/sinks.mdx rename to website/src/pages/nl/substreams/developing/sinks.mdx diff --git a/website/src/pages/nl/substreams/developing/sinks/_meta.js b/website/src/pages/nl/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/nl/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/nl/substreams/quick-start.mdx b/website/src/pages/nl/substreams/quick-start.mdx index d462af43307a..eaec3b713bfe 100644 --- a/website/src/pages/nl/substreams/quick-start.mdx +++ b/website/src/pages/nl/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/pl/resources/_meta-titles.json b/website/src/pages/pl/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/pl/resources/_meta-titles.json +++ b/website/src/pages/pl/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/pl/resources/_meta.js b/website/src/pages/pl/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/pl/resources/_meta.js +++ b/website/src/pages/pl/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/pl/resources/release-notes/_meta.js b/website/src/pages/pl/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/pl/resources/release-notes/_meta.js rename to website/src/pages/pl/resources/migration-guides/_meta.js diff --git a/website/src/pages/pl/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/pl/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/pl/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/pl/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/pl/resources/migration-guides/graphql-validations-migration-guide.mdx b/website/src/pages/pl/resources/migration-guides/graphql-validations-migration-guide.mdx new file mode 100644 index 000000000000..29fed533ef8c --- /dev/null +++ b/website/src/pages/pl/resources/migration-guides/graphql-validations-migration-guide.mdx @@ -0,0 +1,538 @@ +--- +title: GraphQL Validations Migration Guide +--- + +Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). + +Previous versions of `graph-node` did not support all validations and provided more graceful responses - so, in cases of ambiguity, `graph-node` was ignoring invalid GraphQL operations components. + +GraphQL Validations support is the pillar for the upcoming new features and the performance at scale of The Graph Network. + +It will also ensure determinism of query responses, a key requirement on The Graph Network. + +**Enabling the GraphQL Validations will break some existing queries** sent to The Graph API. + +To be compliant with those validations, please follow the migration guide. + +> ⚠️ If you do not migrate your queries before the validations are rolled out, they will return errors and possibly break your frontends/clients. + +## Migration guide + +You can use the CLI migration tool to find any issues in your GraphQL operations and fix them. Alternatively you can update the endpoint of your GraphQL client to use the `https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME` endpoint. Testing your queries against this endpoint will help you find the issues in your queries. + +> Not all subgraphs will need to be migrated, if you are using [GraphQL ESlint](https://the-guild.dev/graphql/eslint/docs) or [GraphQL Code Generator](https://the-guild.dev/graphql/codegen), they already ensure that your queries are valid. + +## Migration CLI tool + +**Most of the GraphQL operations errors can be found in your codebase ahead of time.** + +For this reason, we provide a smooth experience for validating your GraphQL operations during development or in CI. + +[`@graphql-validate/cli`](https://github.com/saihaj/graphql-validate) is a simple CLI tool that helps validate GraphQL operations against a given schema. + +### **Getting started** + +You can run the tool as follows: + +```bash +npx @graphql-validate/cli -s https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME -o *.graphql +``` + +**Notes:** + +- Set or replace $GITHUB_USER, $SUBGRAPH_NAME with the appropriate values. Like: [`artblocks/art-blocks`](https://api.thegraph.com/subgraphs/name/artblocks/art-blocks) +- The preview schema URL (https://api-next.thegraph.com/) provided is heavily rate-limited and will be sunset once all users have migrated to the new version. **Do not use it in production.** +- Operations are identified in files with the following extensions [`.graphql`,](https://www.graphql-tools.com/docs/schema-loading#graphql-file-loader)[`.ts`, `.tsx`, `.js`, `jsx`](https://www.graphql-tools.com/docs/schema-loading#code-file-loader) (`-o` option). + +### CLI output + +The `[@graphql-validate/cli](https://github.com/saihaj/graphql-validate)` CLI tool will output any GraphQL operations errors as follows: + +![Error output from CLI](https://i.imgur.com/x1cBdhq.png) + +For each error, you will find a description, file path and position, and a link to a solution example (see the following section). + +## Run your local queries against the preview schema + +We provide an endpoint `https://api-next.thegraph.com/` that runs a `graph-node` version that has validations turned on. + +You can try out queries by sending them to: + +- `https://api-next.thegraph.com/subgraphs/id/` + +or + +- `https://api-next.thegraph.com/subgraphs/name//` + +To work on queries that have been flagged as having validation errors, you can use your favorite GraphQL query tool, like Altair or [GraphiQL](https://cloud.hasura.io/public/graphiql), and try your query out. Those tools will also mark those errors in their UI, even before you run it. + +## How to solve issues + +Below, you will find all the GraphQL validations errors that could occur on your existing GraphQL operations. + +### GraphQL variables, operations, fragments, or arguments must be unique + +We applied rules for ensuring that an operation includes a unique set of GraphQL variables, operations, fragments, and arguments. + +A GraphQL operation is only valid if it does not contain any ambiguity. + +To achieve that, we need to ensure that some components in your GraphQL operation must be unique. + +Here's an example of a few invalid operations that violates these rules: + +**Duplicate Query name (#UniqueOperationNamesRule)** + +```graphql +# The following operation violated the UniqueOperationName +# rule, since we have a single operation with 2 queries +# with the same name +query myData { + id +} + +query myData { + name +} +``` + +_Solution:_ + +```graphql +query myData { + id +} + +query myData2 { + # rename the second query + name +} +``` + +**Duplicate Fragment name (#UniqueFragmentNamesRule)** + +```graphql +# The following operation violated the UniqueFragmentName +# rule. +query myData { + id + ...MyFields +} + +fragment MyFields { + metadata +} + +fragment MyFields { + name +} +``` + +_Solution:_ + +```graphql +query myData { + id + ...MyFieldsName + ...MyFieldsMetadata +} + +fragment MyFieldsMetadata { # assign a unique name to fragment + metadata +} + +fragment MyFieldsName { # assign a unique name to fragment + name +} +``` + +**Duplicate variable name (#UniqueVariableNamesRule)** + +```graphql +# The following operation violates the UniqueVariables +query myData($id: String, $id: Int) { + id + ...MyFields +} +``` + +_Solution:_ + +```graphql +query myData($id: String) { + # keep the relevant variable (here: `$id: String`) + id + ...MyFields +} +``` + +**Duplicate argument name (#UniqueArgument)** + +```graphql +# The following operation violated the UniqueArguments +query myData($id: ID!) { + userById(id: $id, id: "1") { + id + } +} +``` + +_Solution:_ + +```graphql +query myData($id: ID!) { + userById(id: $id) { + id + } +} +``` + +**Duplicate anonymous query (#LoneAnonymousOperationRule)** + +Also, using two anonymous operations will violate the `LoneAnonymousOperation` rule due to conflict in the response structure: + +```graphql +# This will fail if executed together in +# a single operation with the following two queries: +query { + someField +} + +query { + otherField +} +``` + +_Solution:_ + +```graphql +query { + someField + otherField +} +``` + +Or name the two queries: + +```graphql +query FirstQuery { + someField +} + +query SecondQuery { + otherField +} +``` + +### Overlapping Fields + +A GraphQL selection set is considered valid only if it correctly resolves the eventual result set. + +If a specific selection set, or a field, creates ambiguity either by the selected field or by the arguments used, the GraphQL service will fail to validate the operation. + +Here are a few examples of invalid operations that violate this rule: + +**Conflicting fields aliases (#OverlappingFieldsCanBeMergedRule)** + +```graphql +# Aliasing fields might cause conflicts, either with +# other aliases or other fields that exist on the +# GraphQL schema. +query { + dogs { + name: nickname + name + } +} +``` + +_Solution:_ + +```graphql +query { + dogs { + name: nickname + originalName: name # alias the original `name` field + } +} +``` + +**Conflicting fields with arguments (#OverlappingFieldsCanBeMergedRule)** + +```graphql +# Different arguments might lead to different data, +# so we can't assume the fields will be the same. +query { + dogs { + doesKnowCommand(dogCommand: SIT) + doesKnowCommand(dogCommand: HEEL) + } +} +``` + +_Solution:_ + +```graphql +query { + dogs { + knowsHowToSit: doesKnowCommand(dogCommand: SIT) + knowsHowToHeel: doesKnowCommand(dogCommand: HEEL) + } +} +``` + +Also, in more complex use-cases, you might violate this rule by using two fragments that might cause a conflict in the eventually expected set: + +```graphql +query { + # Eventually, we have two "x" definitions, pointing + # to different fields! + ...A + ...B +} + +fragment A on Type { + x: a +} + +fragment B on Type { + x: b +} +``` + +In addition to that, client-side GraphQL directives like `@skip` and `@include` might lead to ambiguity, for example: + +```graphql +fragment mergeSameFieldsWithSameDirectives on Dog { + name @include(if: true) + name @include(if: false) +} +``` + +[You can read more about the algorithm here.](https://spec.graphql.org/June2018/#sec-Field-Selection-Merging) + +### Unused Variables or Fragments + +A GraphQL operation is also considered valid only if all operation-defined components (variables, fragments) are used. + +Here are a few examples for GraphQL operations that violates these rules: + +**Unused variable** (#NoUnusedVariablesRule) + +```graphql +# Invalid, because $someVar is never used. +query something($someVar: String) { + someData +} +``` + +_Solution:_ + +```graphql +query something { + someData +} +``` + +**Unused Fragment** (#NoUnusedFragmentsRule) + +```graphql +# Invalid, because fragment AllFields is never used. +query something { + someData +} + +fragment AllFields { # unused :( + name + age +} +``` + +_Solution:_ + +```graphql +# Invalid, because fragment AllFields is never used. +query something { + someData +} + +# remove the `AllFields` fragment +``` + +### Invalid or missing Selection-Set (#ScalarLeafsRule) + +Also, a GraphQL field selection is only valid if the following is validated: + +- An object field must-have selection set specified. +- An edge field (scalar, enum) must not have a selection set specified. + +Here are a few examples of violations of these rules with the following Schema: + +```graphql +type Image { + url: String! +} + +type User { + id: ID! + avatar: Image! +} + +type Query { + user: User! +} +``` + +**Invalid Selection-Set** + +```graphql +query { + user { + id { # Invalid, because "id" is of type ID and does not have sub-fields + + } + } +} +``` + +_Solution:_ + +```graphql +query { + user { + id + } +} +``` + +**Missing Selection-Set** + +```graphql +query { + user { + id + image # `image` requires a Selection-Set for sub-fields! + } +} +``` + +_Solution:_ + +```graphql +query { + user { + id + image { + src + } + } +} +``` + +### Incorrect Arguments values (#VariablesInAllowedPositionRule) + +GraphQL operations that pass hard-coded values to arguments must be valid, based on the value defined in the schema. + +Here are a few examples of invalid operations that violate these rules: + +```graphql +query purposes { + # If "name" is defined as "String" in the schema, + # this query will fail during validation. + purpose(name: 1) { + id + } +} + +# This might also happen when an incorrect variable is defined: + +query purposes($name: Int!) { + # If "name" is defined as `String` in the schema, + # this query will fail during validation, because the + # variable used is of type `Int` + purpose(name: $name) { + id + } +} +``` + +### Unknown Type, Variable, Fragment, or Directive (#UnknownX) + +The GraphQL API will raise an error if any unknown type, variable, fragment, or directive is used. + +Those unknown references must be fixed: + +- rename if it was a typo +- otherwise, remove + +### Fragment: invalid spread or definition + +**Invalid Fragment spread (#PossibleFragmentSpreadsRule)** + +A Fragment cannot be spread on a non-applicable type. + +Example, we cannot apply a `Cat` fragment to the `Dog` type: + +```graphql +query { + dog { + ...CatSimple + } +} + +fragment CatSimple on Cat { + # ... +} +``` + +**Invalid Fragment definition (#FragmentsOnCompositeTypesRule)** + +All Fragment must be defined upon (using `on ...`) a composite type, in short: object, interface, or union. + +The following examples are invalid, since defining fragments on scalars is invalid. + +```graphql +fragment fragOnScalar on Int { + # we cannot define a fragment upon a scalar (`Int`) + something +} + +fragment inlineFragOnScalar on Dog { + ... on Boolean { + # `Boolean` is not a subtype of `Dog` + somethingElse + } +} +``` + +### Directives usage + +**Directive cannot be used at this location (#KnownDirectivesRule)** + +Only GraphQL directives (`@...`) supported by The Graph API can be used. + +Here is an example with The GraphQL supported directives: + +```graphql +query { + dog { + name @include(true) + age @skip(true) + } +} +``` + +_Note: `@stream`, `@live`, `@defer` are not supported._ + +**Directive can only be used once at this location (#UniqueDirectivesPerLocationRule)** + +The directives supported by The Graph can only be used once per location. + +The following is invalid (and redundant): + +```graphql +query { + dog { + name @include(true) @include(true) + } +} +``` diff --git a/website/src/pages/pl/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/pl/resources/release-notes/graphql-validations-migration-guide.mdx deleted file mode 100644 index 4d909e8970a8..000000000000 --- a/website/src/pages/pl/resources/release-notes/graphql-validations-migration-guide.mdx +++ /dev/null @@ -1,538 +0,0 @@ ---- -title: GraphQL Validations migration guide ---- - -Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). - -Previous versions of `graph-node` did not support all validations and provided more graceful responses - so, in cases of ambiguity, `graph-node` was ignoring invalid GraphQL operations components. - -GraphQL Validations support is the pillar for the upcoming new features and the performance at scale of The Graph Network. - -It will also ensure determinism of query responses, a key requirement on The Graph Network. - -**Enabling the GraphQL Validations will break some existing queries** sent to The Graph API. - -To be compliant with those validations, please follow the migration guide. - -> ⚠️ If you do not migrate your queries before the validations are rolled out, they will return errors and possibly break your frontends/clients. - -## Migration guide - -You can use the CLI migration tool to find any issues in your GraphQL operations and fix them. Alternatively you can update the endpoint of your GraphQL client to use the `https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME` endpoint. Testing your queries against this endpoint will help you find the issues in your queries. - -> Not all subgraphs will need to be migrated, if you are using [GraphQL ESlint](https://the-guild.dev/graphql/eslint/docs) or [GraphQL Code Generator](https://the-guild.dev/graphql/codegen), they already ensure that your queries are valid. - -## Migration CLI tool - -**Most of the GraphQL operations errors can be found in your codebase ahead of time.** - -For this reason, we provide a smooth experience for validating your GraphQL operations during development or in CI. - -[`@graphql-validate/cli`](https://github.com/saihaj/graphql-validate) is a simple CLI tool that helps validate GraphQL operations against a given schema. - -### **Getting started** - -You can run the tool as follows: - -```bash -npx @graphql-validate/cli -s https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME -o *.graphql -``` - -**Notes:** - -- Set or replace $GITHUB_USER, $SUBGRAPH_NAME with the appropriate values. Like: [`artblocks/art-blocks`](https://api.thegraph.com/subgraphs/name/artblocks/art-blocks) -- The preview schema URL (https://api-next.thegraph.com/) provided is heavily rate-limited and will be sunset once all users have migrated to the new version. **Do not use it in production.** -- Operations are identified in files with the following extensions [`.graphql`,](https://www.graphql-tools.com/docs/schema-loading#graphql-file-loader)[`.ts`, `.tsx`, `.js`, `jsx`](https://www.graphql-tools.com/docs/schema-loading#code-file-loader) (`-o` option). - -### CLI output - -The `[@graphql-validate/cli](https://github.com/saihaj/graphql-validate)` CLI tool will output any GraphQL operations errors as follows: - -![Error output from CLI](https://i.imgur.com/x1cBdhq.png) - -For each error, you will find a description, file path and position, and a link to a solution example (see the following section). - -## Run your local queries against the preview schema - -We provide an endpoint `https://api-next.thegraph.com/` that runs a `graph-node` version that has validations turned on. - -You can try out queries by sending them to: - -- `https://api-next.thegraph.com/subgraphs/id/` - -or - -- `https://api-next.thegraph.com/subgraphs/name//` - -To work on queries that have been flagged as having validation errors, you can use your favorite GraphQL query tool, like Altair or [GraphiQL](https://cloud.hasura.io/public/graphiql), and try your query out. Those tools will also mark those errors in their UI, even before you run it. - -## How to solve issues - -Below, you will find all the GraphQL validations errors that could occur on your existing GraphQL operations. - -### GraphQL variables, operations, fragments, or arguments must be unique - -We applied rules for ensuring that an operation includes a unique set of GraphQL variables, operations, fragments, and arguments. - -A GraphQL operation is only valid if it does not contain any ambiguity. - -To achieve that, we need to ensure that some components in your GraphQL operation must be unique. - -Here's an example of a few invalid operations that violates these rules: - -**Duplicate Query name (#UniqueOperationNamesRule)** - -```graphql -# The following operation violated the UniqueOperationName -# rule, since we have a single operation with 2 queries -# with the same name -query myData { - id -} - -query myData { - name -} -``` - -_Solution:_ - -```graphql -query myData { - id -} - -query myData2 { - # rename the second query - name -} -``` - -**Duplicate Fragment name (#UniqueFragmentNamesRule)** - -```graphql -# The following operation violated the UniqueFragmentName -# rule. -query myData { - id - ...MyFields -} - -fragment MyFields { - metadata -} - -fragment MyFields { - name -} -``` - -_Solution:_ - -```graphql -query myData { - id - ...MyFieldsName - ...MyFieldsMetadata -} - -fragment MyFieldsMetadata { # assign a unique name to fragment - metadata -} - -fragment MyFieldsName { # assign a unique name to fragment - name -} -``` - -**Duplicate variable name (#UniqueVariableNamesRule)** - -```graphql -# The following operation violates the UniqueVariables -query myData($id: String, $id: Int) { - id - ...MyFields -} -``` - -_Solution:_ - -```graphql -query myData($id: String) { - # keep the relevant variable (here: `$id: String`) - id - ...MyFields -} -``` - -**Duplicate argument name (#UniqueArgument)** - -```graphql -# The following operation violated the UniqueArguments -query myData($id: ID!) { - userById(id: $id, id: "1") { - id - } -} -``` - -_Solution:_ - -```graphql -query myData($id: ID!) { - userById(id: $id) { - id - } -} -``` - -**Duplicate anonymous query (#LoneAnonymousOperationRule)** - -Also, using two anonymous operations will violate the `LoneAnonymousOperation` rule due to conflict in the response structure: - -```graphql -# This will fail if executed together in -# a single operation with the following two queries: -query { - someField -} - -query { - otherField -} -``` - -_Solution:_ - -```graphql -query { - someField - otherField -} -``` - -Or name the two queries: - -```graphql -query FirstQuery { - someField -} - -query SecondQuery { - otherField -} -``` - -### Overlapping Fields - -A GraphQL selection set is considered valid only if it correctly resolves the eventual result set. - -If a specific selection set, or a field, creates ambiguity either by the selected field or by the arguments used, the GraphQL service will fail to validate the operation. - -Here are a few examples of invalid operations that violate this rule: - -**Conflicting fields aliases (#OverlappingFieldsCanBeMergedRule)** - -```graphql -# Aliasing fields might cause conflicts, either with -# other aliases or other fields that exist on the -# GraphQL schema. -query { - dogs { - name: nickname - name - } -} -``` - -_Solution:_ - -```graphql -query { - dogs { - name: nickname - originalName: name # alias the original `name` field - } -} -``` - -**Conflicting fields with arguments (#OverlappingFieldsCanBeMergedRule)** - -```graphql -# Different arguments might lead to different data, -# so we can't assume the fields will be the same. -query { - dogs { - doesKnowCommand(dogCommand: SIT) - doesKnowCommand(dogCommand: HEEL) - } -} -``` - -_Solution:_ - -```graphql -query { - dogs { - knowsHowToSit: doesKnowCommand(dogCommand: SIT) - knowsHowToHeel: doesKnowCommand(dogCommand: HEEL) - } -} -``` - -Also, in more complex use-cases, you might violate this rule by using two fragments that might cause a conflict in the eventually expected set: - -```graphql -query { - # Eventually, we have two "x" definitions, pointing - # to different fields! - ...A - ...B -} - -fragment A on Type { - x: a -} - -fragment B on Type { - x: b -} -``` - -In addition to that, client-side GraphQL directives like `@skip` and `@include` might lead to ambiguity, for example: - -```graphql -fragment mergeSameFieldsWithSameDirectives on Dog { - name @include(if: true) - name @include(if: false) -} -``` - -[You can read more about the algorithm here.](https://spec.graphql.org/June2018/#sec-Field-Selection-Merging) - -### Unused Variables or Fragments - -A GraphQL operation is also considered valid only if all operation-defined components (variables, fragments) are used. - -Here are a few examples for GraphQL operations that violates these rules: - -**Unused variable** (#NoUnusedVariablesRule) - -```graphql -# Invalid, because $someVar is never used. -query something($someVar: String) { - someData -} -``` - -_Solution:_ - -```graphql -query something { - someData -} -``` - -**Unused Fragment** (#NoUnusedFragmentsRule) - -```graphql -# Invalid, because fragment AllFields is never used. -query something { - someData -} - -fragment AllFields { # unused :( - name - age -} -``` - -_Solution:_ - -```graphql -# Invalid, because fragment AllFields is never used. -query something { - someData -} - -# remove the `AllFields` fragment -``` - -### Invalid or missing Selection-Set (#ScalarLeafsRule) - -Also, a GraphQL field selection is only valid if the following is validated: - -- An object field must-have selection set specified. -- An edge field (scalar, enum) must not have a selection set specified. - -Here are a few examples of violations of these rules with the following Schema: - -```graphql -type Image { - url: String! -} - -type User { - id: ID! - avatar: Image! -} - -type Query { - user: User! -} -``` - -**Invalid Selection-Set** - -```graphql -query { - user { - id { # Invalid, because "id" is of type ID and does not have sub-fields - - } - } -} -``` - -_Solution:_ - -```graphql -query { - user { - id - } -} -``` - -**Missing Selection-Set** - -```graphql -query { - user { - id - image # `image` requires a Selection-Set for sub-fields! - } -} -``` - -_Solution:_ - -```graphql -query { - user { - id - image { - src - } - } -} -``` - -### Incorrect Arguments values (#VariablesInAllowedPositionRule) - -GraphQL operations that pass hard-coded values to arguments must be valid, based on the value defined in the schema. - -Here are a few examples of invalid operations that violate these rules: - -```graphql -query purposes { - # If "name" is defined as "String" in the schema, - # this query will fail during validation. - purpose(name: 1) { - id - } -} - -# This might also happen when an incorrect variable is defined: - -query purposes($name: Int!) { - # If "name" is defined as `String` in the schema, - # this query will fail during validation, because the - # variable used is of type `Int` - purpose(name: $name) { - id - } -} -``` - -### Unknown Type, Variable, Fragment, or Directive (#UnknownX) - -The GraphQL API will raise an error if any unknown type, variable, fragment, or directive is used. - -Those unknown references must be fixed: - -- rename if it was a typo -- otherwise, remove - -### Fragment: invalid spread or definition - -**Invalid Fragment spread (#PossibleFragmentSpreadsRule)** - -A Fragment cannot be spread on a non-applicable type. - -Example, we cannot apply a `Cat` fragment to the `Dog` type: - -```graphql -query { - dog { - ...CatSimple - } -} - -fragment CatSimple on Cat { - # ... -} -``` - -**Invalid Fragment definition (#FragmentsOnCompositeTypesRule)** - -All Fragment must be defined upon (using `on ...`) a composite type, in short: object, interface, or union. - -The following examples are invalid, since defining fragments on scalars is invalid. - -```graphql -fragment fragOnScalar on Int { - # we cannot define a fragment upon a scalar (`Int`) - something -} - -fragment inlineFragOnScalar on Dog { - ... on Boolean { - # `Boolean` is not a subtype of `Dog` - somethingElse - } -} -``` - -### Directives usage - -**Directive cannot be used at this location (#KnownDirectivesRule)** - -Only GraphQL directives (`@...`) supported by The Graph API can be used. - -Here is an example with The GraphQL supported directives: - -```graphql -query { - dog { - name @include(true) - age @skip(true) - } -} -``` - -_Note: `@stream`, `@live`, `@defer` are not supported._ - -**Directive can only be used once at this location (#UniqueDirectivesPerLocationRule)** - -The directives supported by The Graph can only be used once per location. - -The following is invalid (and redundant): - -```graphql -query { - dog { - name @include(true) @include(true) - } -} -``` diff --git a/website/src/pages/pl/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/pl/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/pl/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/pl/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/pl/sps/sps-faq.mdx b/website/src/pages/pl/sps/sps-faq.mdx index 537f29b09ea6..abc1f3906686 100644 --- a/website/src/pages/pl/sps/sps-faq.mdx +++ b/website/src/pages/pl/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/pl/subgraphs/_meta-titles.json b/website/src/pages/pl/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/pl/subgraphs/_meta-titles.json +++ b/website/src/pages/pl/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/pl/subgraphs/_meta.js b/website/src/pages/pl/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/pl/subgraphs/_meta.js +++ b/website/src/pages/pl/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/pl/subgraphs/best-practices/_meta.js b/website/src/pages/pl/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/pl/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/pl/subgraphs/best-practices/avoid-eth-calls.mdx b/website/src/pages/pl/subgraphs/best-practices/avoid-eth-calls.mdx new file mode 100644 index 000000000000..e40a7b3712e4 --- /dev/null +++ b/website/src/pages/pl/subgraphs/best-practices/avoid-eth-calls.mdx @@ -0,0 +1,117 @@ +--- +title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls +sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' +--- + +## TLDR + +`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. + +## Why Avoiding `eth_calls` Is a Best Practice + +Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. + +### What Does an eth_call Look Like? + +`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: + +```yaml +event Transfer(address indexed from, address indexed to, uint256 value); +``` + +Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, Transfer } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransfer(event: Transfer): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + // Bind the ERC20 contract instance to the given address: + let instance = ERC20.bind(event.address) + + // Retrieve pool information via eth_call + let poolInfo = instance.getPoolInfo(event.params.to) + + transaction.pool = poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is functional, however is not ideal as it slows down our subgraph’s indexing. + +## How to Eliminate `eth_calls` + +Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: + +``` +event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); +``` + +With this update, the subgraph can directly index the required data without external calls: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransferWithPool(event: TransferWithPool): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + transaction.pool = event.params.poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is much more performant as it has eliminated the need for `eth_calls`. + +## How to Optimize `eth_calls` + +If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. + +## Reducing the Runtime Overhead of `eth_calls` + +For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. + +Currently, `eth_calls` can only be declared for event handlers. In the manifest, write + +```yaml +event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) +handler: handleTransferWithPool +calls: + ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) +``` + +The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. + +The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. + +Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. + +## Conclusion + +You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/pl/subgraphs/best-practices/derivedfrom.mdx b/website/src/pages/pl/subgraphs/best-practices/derivedfrom.mdx new file mode 100644 index 000000000000..db3a49928c89 --- /dev/null +++ b/website/src/pages/pl/subgraphs/best-practices/derivedfrom.mdx @@ -0,0 +1,89 @@ +--- +title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom +sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' +--- + +## TLDR + +Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. + +## How to Use the `@derivedFrom` Directive + +You just need to add a `@derivedFrom` directive after your array in your schema. Like this: + +```graphql +comments: [Comment!]! @derivedFrom(field: "post") +``` + +`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. + +### Example Use Case for `@derivedFrom` + +An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. + +Let’s start with our two entities, `Post` and `Comment` + +Without optimization, you could implement it like this with an array: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! +} + +type Comment @entity { + id: Bytes! + content: String! +} +``` + +Arrays like these will effectively store extra Comments data on the Post side of the relationship. + +Here’s what an optimized version looks like using `@derivedFrom`: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! @derivedFrom(field: "post") +} + +type Comment @entity { + id: Bytes! + content: String! + post: Post! +} +``` + +Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. + +This will not only make our subgraph more efficient, but it will also unlock three features: + +1. We can query the `Post` and see all of its comments. + +2. We can do a reverse lookup and query any `Comment` and see which post it comes from. + +3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. + +## Conclusion + +Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. + +For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/nl/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/pl/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/nl/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/pl/subgraphs/best-practices/grafting-hotfix.mdx index 910e32cfacde..d514e1633c75 100644 --- a/website/src/pages/nl/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/pl/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/pl/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx b/website/src/pages/pl/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx new file mode 100644 index 000000000000..6ff60ec9ab34 --- /dev/null +++ b/website/src/pages/pl/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -0,0 +1,191 @@ +--- +title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs +sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' +--- + +## TLDR + +Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. + +## Immutable Entities + +To make an entity immutable, we simply add `(immutable: true)` to an entity. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. + +Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. + +### Under the hood + +Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. + +### When not to use Immutable Entities + +If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. + +## Bytes as IDs + +Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. + +### Reasons to Not Use Bytes as IDs + +1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. +2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. +3. Indexing and querying performance improvements are not desired. + +### Concatenating With Bytes as IDs + +It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. + +Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. + +```typescript +export function handleTransfer(event: TransferEvent): void { + let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) + entity.from = event.params.from + entity.to = event.params.to + entity.value = event.params.value + + entity.blockNumber = event.block.number + entity.blockTimestamp = event.block.timestamp + entity.transactionHash = event.transaction.hash + + entity.save() +} +``` + +### Sorting With Bytes as IDs + +Sorting using Bytes as IDs is not optimal as seen in this example query and response. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: id) { + id + from + to + value + } +} +``` + +Query response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x00010000", + "from": "0xabcd...", + "to": "0x1234...", + "value": "256" + }, + { + "id": "0x00020000", + "from": "0xefgh...", + "to": "0x5678...", + "value": "512" + }, + { + "id": "0x01000000", + "from": "0xijkl...", + "to": "0x9abc...", + "value": "1" + } + ] + } +} +``` + +The IDs are returned as hex. + +To improve sorting, we should create another field on the entity that is a BigInt. + +```graphql +type Transfer @entity { + id: Bytes! + from: Bytes! # address + to: Bytes! # address + value: BigInt! # unit256 + tokenId: BigInt! # uint256 +} +``` + +This will allow for sorting to be optimized sequentially. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: tokenId) { + id + tokenId + } +} +``` + +Query Response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x…", + "tokenId": "1" + }, + { + "id": "0x…", + "tokenId": "2" + }, + { + "id": "0x…", + "tokenId": "3" + } + ] + } +} +``` + +## Conclusion + +Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. + +Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/pl/subgraphs/best-practices/pruning.mdx b/website/src/pages/pl/subgraphs/best-practices/pruning.mdx new file mode 100644 index 000000000000..1b51dde8894f --- /dev/null +++ b/website/src/pages/pl/subgraphs/best-practices/pruning.mdx @@ -0,0 +1,56 @@ +--- +title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning +sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' +--- + +## TLDR + +[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. + +## How to Prune a Subgraph With `indexerHints` + +Add a section called `indexerHints` in the manifest. + +`indexerHints` has three `prune` options: + +- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. +- `prune: `: Sets a custom limit on the number of historical blocks to retain. +- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. + +We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: + +```yaml +specVersion: 1.0.0 +schema: + file: ./schema.graphql +indexerHints: + prune: auto +dataSources: + - kind: ethereum/contract + name: Contract + network: mainnet +``` + +## Important Considerations + +- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. + +- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). + +## Conclusion + +Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/pl/subgraphs/cookbook/timeseries.mdx b/website/src/pages/pl/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/pl/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/pl/subgraphs/best-practices/timeseries.mdx index 7c1c41008d29..cacdc44711fe 100644 --- a/website/src/pages/pl/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/pl/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/pl/subgraphs/cookbook/_meta.js b/website/src/pages/pl/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/pl/subgraphs/cookbook/_meta.js +++ b/website/src/pages/pl/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/pl/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/pl/subgraphs/cookbook/avoid-eth-calls.mdx deleted file mode 100644 index ae29cdf03a34..000000000000 --- a/website/src/pages/pl/subgraphs/cookbook/avoid-eth-calls.mdx +++ /dev/null @@ -1,117 +0,0 @@ ---- -title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls -sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' ---- - -## TLDR - -`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. - -## Why Avoiding `eth_calls` Is a Best Practice - -Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. - -### What Does an eth_call Look Like? - -`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: - -```yaml -event Transfer(address indexed from, address indexed to, uint256 value); -``` - -Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, Transfer } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransfer(event: Transfer): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - // Bind the ERC20 contract instance to the given address: - let instance = ERC20.bind(event.address) - - // Retrieve pool information via eth_call - let poolInfo = instance.getPoolInfo(event.params.to) - - transaction.pool = poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is functional, however is not ideal as it slows down our subgraph’s indexing. - -## How to Eliminate `eth_calls` - -Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: - -``` -event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); -``` - -With this update, the subgraph can directly index the required data without external calls: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransferWithPool(event: TransferWithPool): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - transaction.pool = event.params.poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is much more performant as it has eliminated the need for `eth_calls`. - -## How to Optimize `eth_calls` - -If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. - -## Reducing the Runtime Overhead of `eth_calls` - -For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. - -Currently, `eth_calls` can only be declared for event handlers. In the manifest, write - -```yaml -event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) -handler: handleTransferWithPool -calls: - ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) -``` - -The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. - -The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. - -Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. - -## Conclusion - -You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/pl/subgraphs/cookbook/cosmos.mdx b/website/src/pages/pl/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 5ccf1025ca47..000000000000 --- a/website/src/pages/pl/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Building Subgraphs on Cosmos ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## What are Cosmos subgraphs? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -There are four types of handlers supported in Cosmos subgraphs: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Even though all data can be accessed with a block handler, other handlers enable subgraph developers to process data in a much more granular way. - -## Building a Cosmos subgraph - -### Subgraph Dependencies - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Subgraph Main Components - -There are three key parts when it comes to defining a subgraph: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### Subgraph Manifest Definition - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### Schema Definition - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript Mappings - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Each handler type comes with its own data structure that is passed as an argument to a mapping function. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Message decoding - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Creating and building a Cosmos subgraph - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Deploying a Cosmos subgraph - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Querying a Cosmos subgraph - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Supported Cosmos Blockchains - -### Cosmos Hub - -#### What is Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### Networks - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### What is Osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### Networks - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## Example Subgraphs - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/pl/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/pl/subgraphs/cookbook/derivedfrom.mdx deleted file mode 100644 index a0942645c999..000000000000 --- a/website/src/pages/pl/subgraphs/cookbook/derivedfrom.mdx +++ /dev/null @@ -1,89 +0,0 @@ ---- -title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom -sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' ---- - -## TLDR - -Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. - -## How to Use the `@derivedFrom` Directive - -You just need to add a `@derivedFrom` directive after your array in your schema. Like this: - -```graphql -comments: [Comment!]! @derivedFrom(field: "post") -``` - -`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. - -### Example Use Case for `@derivedFrom` - -An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. - -Let’s start with our two entities, `Post` and `Comment` - -Without optimization, you could implement it like this with an array: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! -} - -type Comment @entity { - id: Bytes! - content: String! -} -``` - -Arrays like these will effectively store extra Comments data on the Post side of the relationship. - -Here’s what an optimized version looks like using `@derivedFrom`: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! @derivedFrom(field: "post") -} - -type Comment @entity { - id: Bytes! - content: String! - post: Post! -} -``` - -Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. - -This will not only make our subgraph more efficient, but it will also unlock three features: - -1. We can query the `Post` and see all of its comments. - -2. We can do a reverse lookup and query any `Comment` and see which post it comes from. - -3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. - -## Conclusion - -Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. - -For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/pl/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/pl/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx deleted file mode 100644 index 511565bb3dd4..000000000000 --- a/website/src/pages/pl/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ /dev/null @@ -1,191 +0,0 @@ ---- -title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs -sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' ---- - -## TLDR - -Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. - -## Immutable Entities - -To make an entity immutable, we simply add `(immutable: true)` to an entity. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. - -Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. - -### Under the hood - -Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. - -### When not to use Immutable Entities - -If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. - -## Bytes as IDs - -Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. - -### Reasons to Not Use Bytes as IDs - -1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. -2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. -3. Indexing and querying performance improvements are not desired. - -### Concatenating With Bytes as IDs - -It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. - -Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. - -```typescript -export function handleTransfer(event: TransferEvent): void { - let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) - entity.from = event.params.from - entity.to = event.params.to - entity.value = event.params.value - - entity.blockNumber = event.block.number - entity.blockTimestamp = event.block.timestamp - entity.transactionHash = event.transaction.hash - - entity.save() -} -``` - -### Sorting With Bytes as IDs - -Sorting using Bytes as IDs is not optimal as seen in this example query and response. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: id) { - id - from - to - value - } -} -``` - -Query response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x00010000", - "from": "0xabcd...", - "to": "0x1234...", - "value": "256" - }, - { - "id": "0x00020000", - "from": "0xefgh...", - "to": "0x5678...", - "value": "512" - }, - { - "id": "0x01000000", - "from": "0xijkl...", - "to": "0x9abc...", - "value": "1" - } - ] - } -} -``` - -The IDs are returned as hex. - -To improve sorting, we should create another field on the entity that is a BigInt. - -```graphql -type Transfer @entity { - id: Bytes! - from: Bytes! # address - to: Bytes! # address - value: BigInt! # unit256 - tokenId: BigInt! # uint256 -} -``` - -This will allow for sorting to be optimized sequentially. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: tokenId) { - id - tokenId - } -} -``` - -Query Response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x…", - "tokenId": "1" - }, - { - "id": "0x…", - "tokenId": "2" - }, - { - "id": "0x…", - "tokenId": "3" - } - ] - } -} -``` - -## Conclusion - -Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. - -Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/pl/subgraphs/cookbook/pruning.mdx b/website/src/pages/pl/subgraphs/cookbook/pruning.mdx deleted file mode 100644 index e212d5d02bc9..000000000000 --- a/website/src/pages/pl/subgraphs/cookbook/pruning.mdx +++ /dev/null @@ -1,56 +0,0 @@ ---- -title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning -sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' ---- - -## TLDR - -[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. - -## How to Prune a Subgraph With `indexerHints` - -Add a section called `indexerHints` in the manifest. - -`indexerHints` has three `prune` options: - -- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. -- `prune: `: Sets a custom limit on the number of historical blocks to retain. -- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. - -We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: - -```yaml -specVersion: 1.0.0 -schema: - file: ./schema.graphql -indexerHints: - prune: auto -dataSources: - - kind: ethereum/contract - name: Contract - network: mainnet -``` - -## Important Considerations - -- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. - -- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). - -## Conclusion - -Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/pl/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/pl/subgraphs/developing/creating/graph-ts/api.mdx index b5cec3b091e4..35bb04826c98 100644 --- a/website/src/pages/pl/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/pl/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/pl/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/pl/subgraphs/developing/creating/install-the-cli.mdx index 72001c551547..d4509815a845 100644 --- a/website/src/pages/pl/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/pl/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Install the Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Overview diff --git a/website/src/pages/pl/subgraphs/developing/deploying/_meta.js b/website/src/pages/pl/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/pl/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/pl/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/pl/subgraphs/querying/best-practices.mdx b/website/src/pages/pl/subgraphs/querying/best-practices.mdx index 3736fa32faeb..ff5f381e2993 100644 --- a/website/src/pages/pl/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/pl/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Sending a query to a GraphQL API diff --git a/website/src/pages/pl/subgraphs/querying/managing-api-keys.mdx b/website/src/pages/pl/subgraphs/querying/managing-api-keys.mdx index f7aff33ea926..6964b1a7ad9b 100644 --- a/website/src/pages/pl/subgraphs/querying/managing-api-keys.mdx +++ b/website/src/pages/pl/subgraphs/querying/managing-api-keys.mdx @@ -1,5 +1,5 @@ --- -title: Managing your API keys +title: Managing API keys --- ## Overview diff --git a/website/src/pages/nl/substreams/developing/sinks/sinks.mdx b/website/src/pages/pl/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/nl/substreams/developing/sinks/sinks.mdx rename to website/src/pages/pl/substreams/developing/sinks.mdx diff --git a/website/src/pages/pl/substreams/developing/sinks/_meta.js b/website/src/pages/pl/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/pl/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/pl/substreams/quick-start.mdx b/website/src/pages/pl/substreams/quick-start.mdx index e6dfee78304f..96846fccaf05 100644 --- a/website/src/pages/pl/substreams/quick-start.mdx +++ b/website/src/pages/pl/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/pt/resources/_meta-titles.json b/website/src/pages/pt/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/pt/resources/_meta-titles.json +++ b/website/src/pages/pt/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/pt/resources/_meta.js b/website/src/pages/pt/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/pt/resources/_meta.js +++ b/website/src/pages/pt/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/pt/resources/release-notes/_meta.js b/website/src/pages/pt/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/pt/resources/release-notes/_meta.js rename to website/src/pages/pt/resources/migration-guides/_meta.js diff --git a/website/src/pages/pt/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/pt/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/pt/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/pt/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/pt/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/pt/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 100% rename from website/src/pages/pt/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/pt/resources/migration-guides/graphql-validations-migration-guide.mdx diff --git a/website/src/pages/pt/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/pt/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/pt/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/pt/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/pt/sps/sps-faq.mdx b/website/src/pages/pt/sps/sps-faq.mdx index b0fdbf0f4452..2991b30adbe3 100644 --- a/website/src/pages/pt/sps/sps-faq.mdx +++ b/website/src/pages/pt/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/pt/subgraphs/_meta-titles.json b/website/src/pages/pt/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/pt/subgraphs/_meta-titles.json +++ b/website/src/pages/pt/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/pt/subgraphs/_meta.js b/website/src/pages/pt/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/pt/subgraphs/_meta.js +++ b/website/src/pages/pt/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/pt/subgraphs/best-practices/_meta.js b/website/src/pages/pt/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/pt/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/pt/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/pt/subgraphs/best-practices/avoid-eth-calls.mdx similarity index 93% rename from website/src/pages/pt/subgraphs/cookbook/avoid-eth-calls.mdx rename to website/src/pages/pt/subgraphs/best-practices/avoid-eth-calls.mdx index c8e7f1b974e2..f8f0fc8dedab 100644 --- a/website/src/pages/pt/subgraphs/cookbook/avoid-eth-calls.mdx +++ b/website/src/pages/pt/subgraphs/best-practices/avoid-eth-calls.mdx @@ -104,14 +104,14 @@ O desempenho da indexação pode melhorar muito ao minimizar ou eliminar `eth_ca ## Melhores Práticas para um Subgraph 1 – 6 -1. [Pruning: Reduza o Excesso de Dados do Seu Subgraph para Acelerar Queries](/subgraphs/cookbook/pruning/) +1. [Pruning: Reduza o Excesso de Dados do Seu Subgraph para Acelerar Queries](/subgraphs/best-practices/pruning/) -2. [Use o @derivedFrom para Melhorar a Resposta da Indexação e de Queries](/subgraphs/cookbook/derivedfrom/) +2. [Use o @derivedFrom para Melhorar a Resposta da Indexação e de Queries](/subgraphs/best-practices/derivedfrom/) -3. [Melhore o Desempenho da Indexação e de Queries com o Uso de Bytes como IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Melhore o Desempenho da Indexação e de Queries com o Uso de Bytes como IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Evite `eth-calls` para Acelerar a Indexação](/subgraphs/cookbook/avoid-eth-calls/) +4. [Evite `eth-calls` para Acelerar a Indexação](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplifique e Otimize com Séries Temporais e Agregações](/subgraphs/cookbook/timeseries/) +5. [Simplifique e Otimize com Séries Temporais e Agregações](/subgraphs/best-practices/timeseries/) -6. [Lance Hotfixes Mais Rápido com Enxertos](/subgraphs/cookbook/grafting-hotfix/) +6. [Lance Hotfixes Mais Rápido com Enxertos](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/pt/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/pt/subgraphs/best-practices/derivedfrom.mdx similarity index 90% rename from website/src/pages/pt/subgraphs/cookbook/derivedfrom.mdx rename to website/src/pages/pt/subgraphs/best-practices/derivedfrom.mdx index da524e0c4590..dedf0bf2ffe2 100644 --- a/website/src/pages/pt/subgraphs/cookbook/derivedfrom.mdx +++ b/website/src/pages/pt/subgraphs/best-practices/derivedfrom.mdx @@ -76,14 +76,14 @@ Para aprender mais estratégias detalhadas sobre evitar arranjos grandes, leia e ## Melhores Práticas para um Subgraph 1 – 6 -1. [Pruning: Reduza o Excesso de Dados do Seu Subgraph para Acelerar Queries](/subgraphs/cookbook/pruning/) +1. [Pruning: Reduza o Excesso de Dados do Seu Subgraph para Acelerar Queries](/subgraphs/best-practices/pruning/) -2. [Use o @derivedFrom para Melhorar a Resposta da Indexação e de Queries](/subgraphs/cookbook/derivedfrom/) +2. [Use o @derivedFrom para Melhorar a Resposta da Indexação e de Queries](/subgraphs/best-practices/derivedfrom/) -3. [Melhore o Desempenho da Indexação e de Queries com o Uso de Bytes como IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Melhore o Desempenho da Indexação e de Queries com o Uso de Bytes como IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Evite `eth-calls` para Acelerar a Indexação](/subgraphs/cookbook/avoid-eth-calls/) +4. [Evite `eth-calls` para Acelerar a Indexação](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplifique e Otimize com Séries Temporais e Agregações](/subgraphs/cookbook/timeseries/) +5. [Simplifique e Otimize com Séries Temporais e Agregações](/subgraphs/best-practices/timeseries/) -6. [Lance Hotfixes Mais Rápido com Enxertos](/subgraphs/cookbook/grafting-hotfix/) +6. [Lance Hotfixes Mais Rápido com Enxertos](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/pt/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/pt/subgraphs/best-practices/grafting-hotfix.mdx similarity index 96% rename from website/src/pages/pt/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/pt/subgraphs/best-practices/grafting-hotfix.mdx index 21c7f4bd8e1e..d9f463501e94 100644 --- a/website/src/pages/pt/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/pt/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ Ao incorporar enxertos ao seu fluxo de programação de subgraphs, é possível ## Melhores Práticas para um Subgraph 1 – 6 -1. [Pruning: Reduza o Excesso de Dados do Seu Subgraph para Acelerar Queries](/subgraphs/cookbook/pruning/) +1. [Pruning: Reduza o Excesso de Dados do Seu Subgraph para Acelerar Queries](/subgraphs/best-practices/pruning/) -2. [Use o @derivedFrom para Melhorar a Resposta da Indexação e de Queries](/subgraphs/cookbook/derivedfrom/) +2. [Use o @derivedFrom para Melhorar a Resposta da Indexação e de Queries](/subgraphs/best-practices/derivedfrom/) -3. [Melhore o Desempenho da Indexação e de Queries com o Uso de Bytes como IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Melhore o Desempenho da Indexação e de Queries com o Uso de Bytes como IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Evite `eth-calls` para Acelerar a Indexação](/subgraphs/cookbook/avoid-eth-calls/) +4. [Evite `eth-calls` para Acelerar a Indexação](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplifique e Otimize com Séries Temporais e Agregações](/subgraphs/cookbook/timeseries/) +5. [Simplifique e Otimize com Séries Temporais e Agregações](/subgraphs/best-practices/timeseries/) -6. [Lance Hotfixes Mais Rápido com Enxertos](/subgraphs/cookbook/grafting-hotfix/) +6. [Lance Hotfixes Mais Rápido com Enxertos](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/pt/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/pt/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx similarity index 93% rename from website/src/pages/pt/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx rename to website/src/pages/pt/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx index d1ca08327289..4124d0504cde 100644 --- a/website/src/pages/pt/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ b/website/src/pages/pt/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -178,14 +178,14 @@ Leia mais sobre o uso de Entidades Imutáveis e Bytes como IDs nesta publicaçã ## Melhores Práticas para um Subgraph 1 – 6 -1. [Pruning: Reduza o Excesso de Dados do Seu Subgraph para Acelerar Queries](/subgraphs/cookbook/pruning/) +1. [Pruning: Reduza o Excesso de Dados do Seu Subgraph para Acelerar Queries](/subgraphs/best-practices/pruning/) -2. [Use o @derivedFrom para Melhorar a Resposta da Indexação e de Queries](/subgraphs/cookbook/derivedfrom/) +2. [Use o @derivedFrom para Melhorar a Resposta da Indexação e de Queries](/subgraphs/best-practices/derivedfrom/) -3. [Melhore o Desempenho da Indexação e de Queries com o Uso de Bytes como IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Melhore o Desempenho da Indexação e de Queries com o Uso de Bytes como IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Evite `eth-calls` para Acelerar a Indexação](/subgraphs/cookbook/avoid-eth-calls/) +4. [Evite `eth-calls` para Acelerar a Indexação](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplifique e Otimize com Séries Temporais e Agregações](/subgraphs/cookbook/timeseries/) +5. [Simplifique e Otimize com Séries Temporais e Agregações](/subgraphs/best-practices/timeseries/) -6. [Lance Hotfixes Mais Rápido com Enxertos](/subgraphs/cookbook/grafting-hotfix/) +6. [Lance Hotfixes Mais Rápido com Enxertos](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/pt/subgraphs/cookbook/pruning.mdx b/website/src/pages/pt/subgraphs/best-practices/pruning.mdx similarity index 88% rename from website/src/pages/pt/subgraphs/cookbook/pruning.mdx rename to website/src/pages/pt/subgraphs/best-practices/pruning.mdx index 76dd01baadf3..eb6afc85791f 100644 --- a/website/src/pages/pt/subgraphs/cookbook/pruning.mdx +++ b/website/src/pages/pt/subgraphs/best-practices/pruning.mdx @@ -43,14 +43,14 @@ O pruning com `indexerHints` é uma boa prática para o desenvolvimento de subgr ## Melhores Práticas para um Subgraph 1 – 6 -1. [Pruning: Reduza o Excesso de Dados do Seu Subgraph para Acelerar Queries](/subgraphs/cookbook/pruning/) +1. [Pruning: Reduza o Excesso de Dados do Seu Subgraph para Acelerar Queries](/subgraphs/best-practices/pruning/) -2. [Use o @derivedFrom para Melhorar a Resposta da Indexação e de Queries](/subgraphs/cookbook/derivedfrom/) +2. [Use o @derivedFrom para Melhorar a Resposta da Indexação e de Queries](/subgraphs/best-practices/derivedfrom/) -3. [Melhore o Desempenho da Indexação e de Queries com o Uso de Bytes como IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Melhore o Desempenho da Indexação e de Queries com o Uso de Bytes como IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Evite `eth-calls` para Acelerar a Indexação](/subgraphs/cookbook/avoid-eth-calls/) +4. [Evite `eth-calls` para Acelerar a Indexação](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplifique e Otimize com Séries Temporais e Agregações](/subgraphs/cookbook/timeseries/) +5. [Simplifique e Otimize com Séries Temporais e Agregações](/subgraphs/best-practices/timeseries/) -6. [Lance Hotfixes Mais Rápido com Enxertos](/subgraphs/cookbook/grafting-hotfix/) +6. [Lance Hotfixes Mais Rápido com Enxertos](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/pt/subgraphs/cookbook/timeseries.mdx b/website/src/pages/pt/subgraphs/best-practices/timeseries.mdx similarity index 94% rename from website/src/pages/pt/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/pt/subgraphs/best-practices/timeseries.mdx index 2438e9819300..b0228580d20f 100644 --- a/website/src/pages/pt/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/pt/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ Ao adotar esse padrão, os programadores podem criar subgraphs mais eficientes e ## Melhores Práticas para um Subgraph 1 – 6 -1. [Pruning: Reduza o Excesso de Dados do Seu Subgraph para Acelerar Queries](/subgraphs/cookbook/pruning/) +1. [Pruning: Reduza o Excesso de Dados do Seu Subgraph para Acelerar Queries](/subgraphs/best-practices/pruning/) -2. [Use o @derivedFrom para Melhorar a Resposta da Indexação e de Queries](/subgraphs/cookbook/derivedfrom/) +2. [Use o @derivedFrom para Melhorar a Resposta da Indexação e de Queries](/subgraphs/best-practices/derivedfrom/) -3. [Melhore o Desempenho da Indexação e de Queries com o Uso de Bytes como IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Melhore o Desempenho da Indexação e de Queries com o Uso de Bytes como IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Evite `eth-calls` para Acelerar a Indexação](/subgraphs/cookbook/avoid-eth-calls/) +4. [Evite `eth-calls` para Acelerar a Indexação](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplifique e Otimize com Séries Temporais e Agregações](/subgraphs/cookbook/timeseries/) +5. [Simplifique e Otimize com Séries Temporais e Agregações](/subgraphs/best-practices/timeseries/) -6. [Lance Hotfixes Mais Rápido com Enxertos](/subgraphs/cookbook/grafting-hotfix/) +6. [Lance Hotfixes Mais Rápido com Enxertos](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/pt/subgraphs/cookbook/_meta.js b/website/src/pages/pt/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/pt/subgraphs/cookbook/_meta.js +++ b/website/src/pages/pt/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/pt/subgraphs/cookbook/cosmos.mdx b/website/src/pages/pt/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 106301863698..000000000000 --- a/website/src/pages/pt/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Construção de Subgraphs no Cosmos ---- - -Este guia é uma introdução à construção de subgraphs através da indexação de blockchains baseadas no [Cosmos](https://cosmos.network/). - -## O que são subgraphs no Cosmos? - -The Graph permite que os programadores processem eventos em blockchain e façam dos dados resultantes facilmente disponíveis através de uma API aberta do GraphQL, conhecida como um subgraph. O [Graph Node](https://github.com/graphprotocol/graph-node) agora pode processar eventos no Cosmos, o que significa que programadores no Cosmos agora podem construir subgraphs para indexar com facilidade eventos on-chain. - -Existem quatro categorias de handlers apoiados em subgraphs no Cosmos: - -- **Handlers de bloco** são executados quando um novo bloco é anexado à chain. -- **Handlers de evento** são executados quando um evento específico é emitido. -- **Handlers de transação** são executados quando ocorre uma transação. -- **Handlers de mensagem** são executados quando ocorre uma mensagem específica. - -Com base na [documentação oficial do Cosmos](https://docs.cosmos.network/): - -> [Eventos](https://docs.cosmos.network/main/learn/advanced/events) são objetos que contém informação sobre a execução do aplicativo. São principalmente usados por provedores de serviço, como exploradores de blocos e carteiras, para rastrear a execução de várias mensagens e transações de índices. -> -> [Transações](https://docs.cosmos.network/main/learn/advanced/transactions) são objetos criados por utilizadores finais para ativar mudanças de estado no aplicativo. -> -> [Mensagens](https://docs.cosmos.network/main/learn/advanced/transactions#messages) são objetos específicos a um módulo que ativam transições de estado, no alcance desse módulo. - -Apesar de todos os dados poderem ser acessados com um block handler, outros handlers permitem a programadores de subgraphs processar dados de uma maneira muito mais granular. - -## Como construir um subgraph no Cosmos - -### Dependências de Subgraph - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) é uma ferramenta de CLI para construir e lançar subgraphs. A versão `>=0.30.0` é necessária para funcionar com subgraphs do Cosmos. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) é uma biblioteca de tipos de dados específicos a um subgraph. Subgraphs do Cosmos exigem a versão `>=0.27.0`. - -### Componentes Principais de Subgraph - -Quando definir um subgraph, estes três componentes serão muito importantes: - -**subgraph.yaml:** um arquivo YAML que contém o manifest do subgraph, e identifica quais eventos rastrear e como processá-los. - -**schema.graphql:** um schema da GraphQL que define quais dados são armazenados para o seu subgraph, e como consultá-los em query via GraphQL. - -**Mapeamentos do AssemblyScript**: Código do [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) que traduz de dados da blockchain para as entidades definidas no seu schema. - -### Definição de Manifest de Subgraph - -O manifest do subgraph (`subgraph.yaml`) identifica as fontes de dados para o subgraph, os gatilhos de interesse, e as funções (`handlers`) a executar em resposta àqueles gatilhos. Veja abaixo um exemplo de um manifest para um subgraph no Cosmos: - -```yaml -specVersion: 0.0.5 -description: Exemplo de Subgraph no Cosmos -schema: - file: ./schema.graphql # link ao arquivo schema -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # Isto mudará para cada blockchain baseada no Cosmos. Neste caso, o exemplo usa a mainnet Cosmos Hub. - source: - startBlock: 0 # Exigido para o Cosmos, coloque o valor de 0 para começar a indexar desde o gênese da chain - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # o nome da função no arquivo de mapeamento - eventHandlers: - - event: rewards # o tipo de evento que será lidado - handler: handleReward # o nome da função no arquivo de mapeamento - transactionHandlers: - - handler: handleTransaction # o nome da função no arquivo de mapeamento - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # o tipo de uma mensagem - handler: handleMsgDelegate # o nome da função no arquivo de mapeamento - file: ./src/mapping.ts # link ao arquivo com os mapeamentos em AssemblyScript -``` - -- Subgraphs no Cosmos introduzem um novo tipo de fonte de dados (`cosmos`). -- A rede (`network`) deve corresponder a uma chain no ecossistema Cosmos. O exemplo acima usa a mainnet do Cosmos Hub. - -### Definição de Schema - -A definição de Schema descreve a estrutura do banco de dados resultado do subgraph, e os relacionamentos entre entidades. Isto é agnóstico da fonte de dados original. Para mais detalhes na definição de schema de subgraph, [clique aqui](/developing/creating-a-subgraph/#the-graphql-schema). - -### Mapeamentos em AssemblyScript - -Os handlers para processamento de eventos estão escritos em [AssemblyScript](https://www.assemblyscript.org/). - -A indexação do Cosmos introduz tipos de dados específicos para esse ecossistema à [API do AssemblyScript](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Cada tipo de handler vem com a sua própria estrutura de dados, a ser passada como argumento a uma função de mapeamento. - -- Handlers de blocos recebem o tipo `Block`. -- Handlers de eventos recebem o tipo `EventData`. -- Handlers de transações recebem o tipo `TransactionData`. -- Handlers de mensagens recebem o tipo `MessageData`. - -Como parte do `MessageData`, o handler de mensagens recebe um contexto de transação, que contém as informações mais importantes sobre uma transação a compor uma mensagem. O contexto da transação também está disponível no tipo `EventData`, mas só quando o evento correspondente é associado a uma transação. Além disso, todos os handlers recebem uma referência a um bloco (`HeaderOnlyBlock`). - -Veja a lista completa de tipos para integração do Cosmos [aqui](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Descodificação de mensagens - -Repare que mensagens no Cosmos são específicas a chains, e são passadas a um subgraph na forma de um payload serializado de [Buffers de Protocolo](https://protobuf.dev/). Portanto, os dados das mensagens devem ser decodificados numa função de mapeamento antes que possam ser processados. - -Veja um exemplo de como decodificar dados de mensagem em um subgraph [aqui](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Criação e construção de um subgraph no Cosmos - -Antes de começar a escrever os mapeamentos do subgraph, o primeiro passo é gerar os vínculos baseados nas entidades definidas no arquivo de schema do subgraph (`schema.graphql`). Assim, as funções de mapeamento criarão novos objetos destes tipos e os salvarão ao armazenamento. Isto é feito com o seguinte comando de CLI `codegen`: - -```bash -$ graph codegen -``` - -Quando os mapeamentos estiverem prontos, o subgraph precisará ser construído. Este passo destacará quaisquer erros possíveis no manifest ou nos mapeamentos. Um subgraph deve ser construído com êxito para ser implantado no Graph Node. Isto é possível com o seguinte comando de CLI `build`: - -```bash -$ graph build -``` - -## Lançamento de um subgraph no Cosmos - -Quando o seu subgraph estiver pronto, lance o seu subgraph com o comando de CLI `graph deploy`: - -**Subgraph Studio** - -Crie um novo subgraph no Subgraph Studio. - -```bash -graph deploy subgraph-name -``` - -**Graph Node local (baseado na configuração padrão):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Consulta a um subgraph no Cosmos - -O ponto final do GraphQL para subgraphs no Arweave é determinado pela definição do schema, com a interface existente da API. Visite a [documentação da API da GraphQL](/subgraphs/querying/graphql-api/) para mais informações. - -## Apoio a Blockchains no Cosmos - -### Cosmos Hub - -#### O que é Cosmos Hub? - -A [blockchain Cosmos Hub](https://hub.cosmos.network/) é a primeira blockchain no ecossistema [Cosmos](https://cosmos.network/). Para mais informações, veja a [documentação oficial](https://docs.cosmos.network/). - -#### Redes - -A mainnet atual do Cosmos Hub é `cosmoshub-4`, e a testnet atual do Cosmos Hub é `theta-testnet-001`.
Outras redes do Cosmos Hub, por ex. `cosmoshub-3`, estão em hiato; portanto, elas não recebem dados. - -### Osmosis - -> O apoio ao Osmosis no Graph Node e no Subgraph Studio está em beta. Caso tenha dúvidas sobre construir subgraphs no Osmosis, por favor contacte a equipa do Graph! - -#### O que é Osmosis? - -O [Osmosis](https://osmosis.zone/) é um protocolo AMM (formador de mercado automatizado) cross-chain, construído sobre o kit de programão Cosmos. Este permite que os utilizadores criem pools customizadas de liquidez e troquem tokens com apoio a protocolos IBC (comunicação inter-blockchain). Para mais informações, veja a [documentação oficial](https://docs.osmosis.zone/). - -#### Redes - -A mainnet do Osmosis é `osmosis-1`, e a testnet atual do Osmosis é `osmo-test-4`. - -## Exemplos de Subgraphs - -Aqui estão alguns exemplos de subgraphs para referência: - -[Exemplo de Filtração de Blocos](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Exemplo de Recompensas de Validador](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Exemplo de Delegações de Validador](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Exemplo de Trocas de Token no Osmosis](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/pt/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/pt/subgraphs/developing/creating/graph-ts/api.mdx index d3f36297c31e..c9069e51a627 100644 --- a/website/src/pages/pt/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/pt/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: API AssemblyScript --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ No manifest do subgraph, `apiVersion` especifica a versão da API de mapeamento, | 0.0.8 | Adiciona validação para existência de campos no schema ao salvar uma entidade. | | 0.0.7 | Classes `TransactionReceipt` e `Log` adicionadas aos tipos do EthereumCampo
Campo `receipt` adicionado ao objeto Ethereum Event | | 0.0.6 | Campo `nonce` adicionado ao objeto Ethereum TransactionCampo
`baseFeePerGas` adicionado ao objeto Ethereum Block | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Campo `functionSignature` adicionado ao objeto Ethereum SmartContractCall | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Campo `input` adicionado ao objeto Ethereum Transaction | diff --git a/website/src/pages/pt/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/pt/subgraphs/developing/creating/install-the-cli.mdx index eda8ead451ae..ca436b6eef1b 100644 --- a/website/src/pages/pt/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/pt/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Como instalar o Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Visão geral diff --git a/website/src/pages/pt/subgraphs/developing/deploying/_meta.js b/website/src/pages/pt/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/pt/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/pt/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/pt/subgraphs/querying/best-practices.mdx b/website/src/pages/pt/subgraphs/querying/best-practices.mdx index 9d31851bddea..e389cf93e893 100644 --- a/website/src/pages/pt/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/pt/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Não seguir as regras acima causará um erro da API do The Graph. -Para uma lista completa de regras com exemplos de código, veja o [guia de Validações da GraphQL](/resources/release-notes/graphql-validations-migration-guide/). +Para uma lista completa de regras com exemplos de código, veja o [guia de Validações da GraphQL](/resources/migration-guides/graphql-validations-migration-guide/). ### Como enviar um query a uma API GraphQL diff --git a/website/src/pages/pt/substreams/developing/sinks/sinks.mdx b/website/src/pages/pt/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/pt/substreams/developing/sinks/sinks.mdx rename to website/src/pages/pt/substreams/developing/sinks.mdx diff --git a/website/src/pages/pt/substreams/developing/sinks/_meta.js b/website/src/pages/pt/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/pt/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/pt/substreams/quick-start.mdx b/website/src/pages/pt/substreams/quick-start.mdx index 718ebf344ed1..5419ecb42667 100644 --- a/website/src/pages/pt/substreams/quick-start.mdx +++ b/website/src/pages/pt/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/ro/resources/_meta-titles.json b/website/src/pages/ro/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/ro/resources/_meta-titles.json +++ b/website/src/pages/ro/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/ro/resources/_meta.js b/website/src/pages/ro/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/ro/resources/_meta.js +++ b/website/src/pages/ro/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/ro/resources/release-notes/_meta.js b/website/src/pages/ro/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/ro/resources/release-notes/_meta.js rename to website/src/pages/ro/resources/migration-guides/_meta.js diff --git a/website/src/pages/ro/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/ro/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/ro/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/ro/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/ro/resources/migration-guides/graphql-validations-migration-guide.mdx b/website/src/pages/ro/resources/migration-guides/graphql-validations-migration-guide.mdx new file mode 100644 index 000000000000..29fed533ef8c --- /dev/null +++ b/website/src/pages/ro/resources/migration-guides/graphql-validations-migration-guide.mdx @@ -0,0 +1,538 @@ +--- +title: GraphQL Validations Migration Guide +--- + +Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). + +Previous versions of `graph-node` did not support all validations and provided more graceful responses - so, in cases of ambiguity, `graph-node` was ignoring invalid GraphQL operations components. + +GraphQL Validations support is the pillar for the upcoming new features and the performance at scale of The Graph Network. + +It will also ensure determinism of query responses, a key requirement on The Graph Network. + +**Enabling the GraphQL Validations will break some existing queries** sent to The Graph API. + +To be compliant with those validations, please follow the migration guide. + +> ⚠️ If you do not migrate your queries before the validations are rolled out, they will return errors and possibly break your frontends/clients. + +## Migration guide + +You can use the CLI migration tool to find any issues in your GraphQL operations and fix them. Alternatively you can update the endpoint of your GraphQL client to use the `https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME` endpoint. Testing your queries against this endpoint will help you find the issues in your queries. + +> Not all subgraphs will need to be migrated, if you are using [GraphQL ESlint](https://the-guild.dev/graphql/eslint/docs) or [GraphQL Code Generator](https://the-guild.dev/graphql/codegen), they already ensure that your queries are valid. + +## Migration CLI tool + +**Most of the GraphQL operations errors can be found in your codebase ahead of time.** + +For this reason, we provide a smooth experience for validating your GraphQL operations during development or in CI. + +[`@graphql-validate/cli`](https://github.com/saihaj/graphql-validate) is a simple CLI tool that helps validate GraphQL operations against a given schema. + +### **Getting started** + +You can run the tool as follows: + +```bash +npx @graphql-validate/cli -s https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME -o *.graphql +``` + +**Notes:** + +- Set or replace $GITHUB_USER, $SUBGRAPH_NAME with the appropriate values. Like: [`artblocks/art-blocks`](https://api.thegraph.com/subgraphs/name/artblocks/art-blocks) +- The preview schema URL (https://api-next.thegraph.com/) provided is heavily rate-limited and will be sunset once all users have migrated to the new version. **Do not use it in production.** +- Operations are identified in files with the following extensions [`.graphql`,](https://www.graphql-tools.com/docs/schema-loading#graphql-file-loader)[`.ts`, `.tsx`, `.js`, `jsx`](https://www.graphql-tools.com/docs/schema-loading#code-file-loader) (`-o` option). + +### CLI output + +The `[@graphql-validate/cli](https://github.com/saihaj/graphql-validate)` CLI tool will output any GraphQL operations errors as follows: + +![Error output from CLI](https://i.imgur.com/x1cBdhq.png) + +For each error, you will find a description, file path and position, and a link to a solution example (see the following section). + +## Run your local queries against the preview schema + +We provide an endpoint `https://api-next.thegraph.com/` that runs a `graph-node` version that has validations turned on. + +You can try out queries by sending them to: + +- `https://api-next.thegraph.com/subgraphs/id/` + +or + +- `https://api-next.thegraph.com/subgraphs/name//` + +To work on queries that have been flagged as having validation errors, you can use your favorite GraphQL query tool, like Altair or [GraphiQL](https://cloud.hasura.io/public/graphiql), and try your query out. Those tools will also mark those errors in their UI, even before you run it. + +## How to solve issues + +Below, you will find all the GraphQL validations errors that could occur on your existing GraphQL operations. + +### GraphQL variables, operations, fragments, or arguments must be unique + +We applied rules for ensuring that an operation includes a unique set of GraphQL variables, operations, fragments, and arguments. + +A GraphQL operation is only valid if it does not contain any ambiguity. + +To achieve that, we need to ensure that some components in your GraphQL operation must be unique. + +Here's an example of a few invalid operations that violates these rules: + +**Duplicate Query name (#UniqueOperationNamesRule)** + +```graphql +# The following operation violated the UniqueOperationName +# rule, since we have a single operation with 2 queries +# with the same name +query myData { + id +} + +query myData { + name +} +``` + +_Solution:_ + +```graphql +query myData { + id +} + +query myData2 { + # rename the second query + name +} +``` + +**Duplicate Fragment name (#UniqueFragmentNamesRule)** + +```graphql +# The following operation violated the UniqueFragmentName +# rule. +query myData { + id + ...MyFields +} + +fragment MyFields { + metadata +} + +fragment MyFields { + name +} +``` + +_Solution:_ + +```graphql +query myData { + id + ...MyFieldsName + ...MyFieldsMetadata +} + +fragment MyFieldsMetadata { # assign a unique name to fragment + metadata +} + +fragment MyFieldsName { # assign a unique name to fragment + name +} +``` + +**Duplicate variable name (#UniqueVariableNamesRule)** + +```graphql +# The following operation violates the UniqueVariables +query myData($id: String, $id: Int) { + id + ...MyFields +} +``` + +_Solution:_ + +```graphql +query myData($id: String) { + # keep the relevant variable (here: `$id: String`) + id + ...MyFields +} +``` + +**Duplicate argument name (#UniqueArgument)** + +```graphql +# The following operation violated the UniqueArguments +query myData($id: ID!) { + userById(id: $id, id: "1") { + id + } +} +``` + +_Solution:_ + +```graphql +query myData($id: ID!) { + userById(id: $id) { + id + } +} +``` + +**Duplicate anonymous query (#LoneAnonymousOperationRule)** + +Also, using two anonymous operations will violate the `LoneAnonymousOperation` rule due to conflict in the response structure: + +```graphql +# This will fail if executed together in +# a single operation with the following two queries: +query { + someField +} + +query { + otherField +} +``` + +_Solution:_ + +```graphql +query { + someField + otherField +} +``` + +Or name the two queries: + +```graphql +query FirstQuery { + someField +} + +query SecondQuery { + otherField +} +``` + +### Overlapping Fields + +A GraphQL selection set is considered valid only if it correctly resolves the eventual result set. + +If a specific selection set, or a field, creates ambiguity either by the selected field or by the arguments used, the GraphQL service will fail to validate the operation. + +Here are a few examples of invalid operations that violate this rule: + +**Conflicting fields aliases (#OverlappingFieldsCanBeMergedRule)** + +```graphql +# Aliasing fields might cause conflicts, either with +# other aliases or other fields that exist on the +# GraphQL schema. +query { + dogs { + name: nickname + name + } +} +``` + +_Solution:_ + +```graphql +query { + dogs { + name: nickname + originalName: name # alias the original `name` field + } +} +``` + +**Conflicting fields with arguments (#OverlappingFieldsCanBeMergedRule)** + +```graphql +# Different arguments might lead to different data, +# so we can't assume the fields will be the same. +query { + dogs { + doesKnowCommand(dogCommand: SIT) + doesKnowCommand(dogCommand: HEEL) + } +} +``` + +_Solution:_ + +```graphql +query { + dogs { + knowsHowToSit: doesKnowCommand(dogCommand: SIT) + knowsHowToHeel: doesKnowCommand(dogCommand: HEEL) + } +} +``` + +Also, in more complex use-cases, you might violate this rule by using two fragments that might cause a conflict in the eventually expected set: + +```graphql +query { + # Eventually, we have two "x" definitions, pointing + # to different fields! + ...A + ...B +} + +fragment A on Type { + x: a +} + +fragment B on Type { + x: b +} +``` + +In addition to that, client-side GraphQL directives like `@skip` and `@include` might lead to ambiguity, for example: + +```graphql +fragment mergeSameFieldsWithSameDirectives on Dog { + name @include(if: true) + name @include(if: false) +} +``` + +[You can read more about the algorithm here.](https://spec.graphql.org/June2018/#sec-Field-Selection-Merging) + +### Unused Variables or Fragments + +A GraphQL operation is also considered valid only if all operation-defined components (variables, fragments) are used. + +Here are a few examples for GraphQL operations that violates these rules: + +**Unused variable** (#NoUnusedVariablesRule) + +```graphql +# Invalid, because $someVar is never used. +query something($someVar: String) { + someData +} +``` + +_Solution:_ + +```graphql +query something { + someData +} +``` + +**Unused Fragment** (#NoUnusedFragmentsRule) + +```graphql +# Invalid, because fragment AllFields is never used. +query something { + someData +} + +fragment AllFields { # unused :( + name + age +} +``` + +_Solution:_ + +```graphql +# Invalid, because fragment AllFields is never used. +query something { + someData +} + +# remove the `AllFields` fragment +``` + +### Invalid or missing Selection-Set (#ScalarLeafsRule) + +Also, a GraphQL field selection is only valid if the following is validated: + +- An object field must-have selection set specified. +- An edge field (scalar, enum) must not have a selection set specified. + +Here are a few examples of violations of these rules with the following Schema: + +```graphql +type Image { + url: String! +} + +type User { + id: ID! + avatar: Image! +} + +type Query { + user: User! +} +``` + +**Invalid Selection-Set** + +```graphql +query { + user { + id { # Invalid, because "id" is of type ID and does not have sub-fields + + } + } +} +``` + +_Solution:_ + +```graphql +query { + user { + id + } +} +``` + +**Missing Selection-Set** + +```graphql +query { + user { + id + image # `image` requires a Selection-Set for sub-fields! + } +} +``` + +_Solution:_ + +```graphql +query { + user { + id + image { + src + } + } +} +``` + +### Incorrect Arguments values (#VariablesInAllowedPositionRule) + +GraphQL operations that pass hard-coded values to arguments must be valid, based on the value defined in the schema. + +Here are a few examples of invalid operations that violate these rules: + +```graphql +query purposes { + # If "name" is defined as "String" in the schema, + # this query will fail during validation. + purpose(name: 1) { + id + } +} + +# This might also happen when an incorrect variable is defined: + +query purposes($name: Int!) { + # If "name" is defined as `String` in the schema, + # this query will fail during validation, because the + # variable used is of type `Int` + purpose(name: $name) { + id + } +} +``` + +### Unknown Type, Variable, Fragment, or Directive (#UnknownX) + +The GraphQL API will raise an error if any unknown type, variable, fragment, or directive is used. + +Those unknown references must be fixed: + +- rename if it was a typo +- otherwise, remove + +### Fragment: invalid spread or definition + +**Invalid Fragment spread (#PossibleFragmentSpreadsRule)** + +A Fragment cannot be spread on a non-applicable type. + +Example, we cannot apply a `Cat` fragment to the `Dog` type: + +```graphql +query { + dog { + ...CatSimple + } +} + +fragment CatSimple on Cat { + # ... +} +``` + +**Invalid Fragment definition (#FragmentsOnCompositeTypesRule)** + +All Fragment must be defined upon (using `on ...`) a composite type, in short: object, interface, or union. + +The following examples are invalid, since defining fragments on scalars is invalid. + +```graphql +fragment fragOnScalar on Int { + # we cannot define a fragment upon a scalar (`Int`) + something +} + +fragment inlineFragOnScalar on Dog { + ... on Boolean { + # `Boolean` is not a subtype of `Dog` + somethingElse + } +} +``` + +### Directives usage + +**Directive cannot be used at this location (#KnownDirectivesRule)** + +Only GraphQL directives (`@...`) supported by The Graph API can be used. + +Here is an example with The GraphQL supported directives: + +```graphql +query { + dog { + name @include(true) + age @skip(true) + } +} +``` + +_Note: `@stream`, `@live`, `@defer` are not supported._ + +**Directive can only be used once at this location (#UniqueDirectivesPerLocationRule)** + +The directives supported by The Graph can only be used once per location. + +The following is invalid (and redundant): + +```graphql +query { + dog { + name @include(true) @include(true) + } +} +``` diff --git a/website/src/pages/ro/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/ro/resources/release-notes/graphql-validations-migration-guide.mdx deleted file mode 100644 index 4d909e8970a8..000000000000 --- a/website/src/pages/ro/resources/release-notes/graphql-validations-migration-guide.mdx +++ /dev/null @@ -1,538 +0,0 @@ ---- -title: GraphQL Validations migration guide ---- - -Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). - -Previous versions of `graph-node` did not support all validations and provided more graceful responses - so, in cases of ambiguity, `graph-node` was ignoring invalid GraphQL operations components. - -GraphQL Validations support is the pillar for the upcoming new features and the performance at scale of The Graph Network. - -It will also ensure determinism of query responses, a key requirement on The Graph Network. - -**Enabling the GraphQL Validations will break some existing queries** sent to The Graph API. - -To be compliant with those validations, please follow the migration guide. - -> ⚠️ If you do not migrate your queries before the validations are rolled out, they will return errors and possibly break your frontends/clients. - -## Migration guide - -You can use the CLI migration tool to find any issues in your GraphQL operations and fix them. Alternatively you can update the endpoint of your GraphQL client to use the `https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME` endpoint. Testing your queries against this endpoint will help you find the issues in your queries. - -> Not all subgraphs will need to be migrated, if you are using [GraphQL ESlint](https://the-guild.dev/graphql/eslint/docs) or [GraphQL Code Generator](https://the-guild.dev/graphql/codegen), they already ensure that your queries are valid. - -## Migration CLI tool - -**Most of the GraphQL operations errors can be found in your codebase ahead of time.** - -For this reason, we provide a smooth experience for validating your GraphQL operations during development or in CI. - -[`@graphql-validate/cli`](https://github.com/saihaj/graphql-validate) is a simple CLI tool that helps validate GraphQL operations against a given schema. - -### **Getting started** - -You can run the tool as follows: - -```bash -npx @graphql-validate/cli -s https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME -o *.graphql -``` - -**Notes:** - -- Set or replace $GITHUB_USER, $SUBGRAPH_NAME with the appropriate values. Like: [`artblocks/art-blocks`](https://api.thegraph.com/subgraphs/name/artblocks/art-blocks) -- The preview schema URL (https://api-next.thegraph.com/) provided is heavily rate-limited and will be sunset once all users have migrated to the new version. **Do not use it in production.** -- Operations are identified in files with the following extensions [`.graphql`,](https://www.graphql-tools.com/docs/schema-loading#graphql-file-loader)[`.ts`, `.tsx`, `.js`, `jsx`](https://www.graphql-tools.com/docs/schema-loading#code-file-loader) (`-o` option). - -### CLI output - -The `[@graphql-validate/cli](https://github.com/saihaj/graphql-validate)` CLI tool will output any GraphQL operations errors as follows: - -![Error output from CLI](https://i.imgur.com/x1cBdhq.png) - -For each error, you will find a description, file path and position, and a link to a solution example (see the following section). - -## Run your local queries against the preview schema - -We provide an endpoint `https://api-next.thegraph.com/` that runs a `graph-node` version that has validations turned on. - -You can try out queries by sending them to: - -- `https://api-next.thegraph.com/subgraphs/id/` - -or - -- `https://api-next.thegraph.com/subgraphs/name//` - -To work on queries that have been flagged as having validation errors, you can use your favorite GraphQL query tool, like Altair or [GraphiQL](https://cloud.hasura.io/public/graphiql), and try your query out. Those tools will also mark those errors in their UI, even before you run it. - -## How to solve issues - -Below, you will find all the GraphQL validations errors that could occur on your existing GraphQL operations. - -### GraphQL variables, operations, fragments, or arguments must be unique - -We applied rules for ensuring that an operation includes a unique set of GraphQL variables, operations, fragments, and arguments. - -A GraphQL operation is only valid if it does not contain any ambiguity. - -To achieve that, we need to ensure that some components in your GraphQL operation must be unique. - -Here's an example of a few invalid operations that violates these rules: - -**Duplicate Query name (#UniqueOperationNamesRule)** - -```graphql -# The following operation violated the UniqueOperationName -# rule, since we have a single operation with 2 queries -# with the same name -query myData { - id -} - -query myData { - name -} -``` - -_Solution:_ - -```graphql -query myData { - id -} - -query myData2 { - # rename the second query - name -} -``` - -**Duplicate Fragment name (#UniqueFragmentNamesRule)** - -```graphql -# The following operation violated the UniqueFragmentName -# rule. -query myData { - id - ...MyFields -} - -fragment MyFields { - metadata -} - -fragment MyFields { - name -} -``` - -_Solution:_ - -```graphql -query myData { - id - ...MyFieldsName - ...MyFieldsMetadata -} - -fragment MyFieldsMetadata { # assign a unique name to fragment - metadata -} - -fragment MyFieldsName { # assign a unique name to fragment - name -} -``` - -**Duplicate variable name (#UniqueVariableNamesRule)** - -```graphql -# The following operation violates the UniqueVariables -query myData($id: String, $id: Int) { - id - ...MyFields -} -``` - -_Solution:_ - -```graphql -query myData($id: String) { - # keep the relevant variable (here: `$id: String`) - id - ...MyFields -} -``` - -**Duplicate argument name (#UniqueArgument)** - -```graphql -# The following operation violated the UniqueArguments -query myData($id: ID!) { - userById(id: $id, id: "1") { - id - } -} -``` - -_Solution:_ - -```graphql -query myData($id: ID!) { - userById(id: $id) { - id - } -} -``` - -**Duplicate anonymous query (#LoneAnonymousOperationRule)** - -Also, using two anonymous operations will violate the `LoneAnonymousOperation` rule due to conflict in the response structure: - -```graphql -# This will fail if executed together in -# a single operation with the following two queries: -query { - someField -} - -query { - otherField -} -``` - -_Solution:_ - -```graphql -query { - someField - otherField -} -``` - -Or name the two queries: - -```graphql -query FirstQuery { - someField -} - -query SecondQuery { - otherField -} -``` - -### Overlapping Fields - -A GraphQL selection set is considered valid only if it correctly resolves the eventual result set. - -If a specific selection set, or a field, creates ambiguity either by the selected field or by the arguments used, the GraphQL service will fail to validate the operation. - -Here are a few examples of invalid operations that violate this rule: - -**Conflicting fields aliases (#OverlappingFieldsCanBeMergedRule)** - -```graphql -# Aliasing fields might cause conflicts, either with -# other aliases or other fields that exist on the -# GraphQL schema. -query { - dogs { - name: nickname - name - } -} -``` - -_Solution:_ - -```graphql -query { - dogs { - name: nickname - originalName: name # alias the original `name` field - } -} -``` - -**Conflicting fields with arguments (#OverlappingFieldsCanBeMergedRule)** - -```graphql -# Different arguments might lead to different data, -# so we can't assume the fields will be the same. -query { - dogs { - doesKnowCommand(dogCommand: SIT) - doesKnowCommand(dogCommand: HEEL) - } -} -``` - -_Solution:_ - -```graphql -query { - dogs { - knowsHowToSit: doesKnowCommand(dogCommand: SIT) - knowsHowToHeel: doesKnowCommand(dogCommand: HEEL) - } -} -``` - -Also, in more complex use-cases, you might violate this rule by using two fragments that might cause a conflict in the eventually expected set: - -```graphql -query { - # Eventually, we have two "x" definitions, pointing - # to different fields! - ...A - ...B -} - -fragment A on Type { - x: a -} - -fragment B on Type { - x: b -} -``` - -In addition to that, client-side GraphQL directives like `@skip` and `@include` might lead to ambiguity, for example: - -```graphql -fragment mergeSameFieldsWithSameDirectives on Dog { - name @include(if: true) - name @include(if: false) -} -``` - -[You can read more about the algorithm here.](https://spec.graphql.org/June2018/#sec-Field-Selection-Merging) - -### Unused Variables or Fragments - -A GraphQL operation is also considered valid only if all operation-defined components (variables, fragments) are used. - -Here are a few examples for GraphQL operations that violates these rules: - -**Unused variable** (#NoUnusedVariablesRule) - -```graphql -# Invalid, because $someVar is never used. -query something($someVar: String) { - someData -} -``` - -_Solution:_ - -```graphql -query something { - someData -} -``` - -**Unused Fragment** (#NoUnusedFragmentsRule) - -```graphql -# Invalid, because fragment AllFields is never used. -query something { - someData -} - -fragment AllFields { # unused :( - name - age -} -``` - -_Solution:_ - -```graphql -# Invalid, because fragment AllFields is never used. -query something { - someData -} - -# remove the `AllFields` fragment -``` - -### Invalid or missing Selection-Set (#ScalarLeafsRule) - -Also, a GraphQL field selection is only valid if the following is validated: - -- An object field must-have selection set specified. -- An edge field (scalar, enum) must not have a selection set specified. - -Here are a few examples of violations of these rules with the following Schema: - -```graphql -type Image { - url: String! -} - -type User { - id: ID! - avatar: Image! -} - -type Query { - user: User! -} -``` - -**Invalid Selection-Set** - -```graphql -query { - user { - id { # Invalid, because "id" is of type ID and does not have sub-fields - - } - } -} -``` - -_Solution:_ - -```graphql -query { - user { - id - } -} -``` - -**Missing Selection-Set** - -```graphql -query { - user { - id - image # `image` requires a Selection-Set for sub-fields! - } -} -``` - -_Solution:_ - -```graphql -query { - user { - id - image { - src - } - } -} -``` - -### Incorrect Arguments values (#VariablesInAllowedPositionRule) - -GraphQL operations that pass hard-coded values to arguments must be valid, based on the value defined in the schema. - -Here are a few examples of invalid operations that violate these rules: - -```graphql -query purposes { - # If "name" is defined as "String" in the schema, - # this query will fail during validation. - purpose(name: 1) { - id - } -} - -# This might also happen when an incorrect variable is defined: - -query purposes($name: Int!) { - # If "name" is defined as `String` in the schema, - # this query will fail during validation, because the - # variable used is of type `Int` - purpose(name: $name) { - id - } -} -``` - -### Unknown Type, Variable, Fragment, or Directive (#UnknownX) - -The GraphQL API will raise an error if any unknown type, variable, fragment, or directive is used. - -Those unknown references must be fixed: - -- rename if it was a typo -- otherwise, remove - -### Fragment: invalid spread or definition - -**Invalid Fragment spread (#PossibleFragmentSpreadsRule)** - -A Fragment cannot be spread on a non-applicable type. - -Example, we cannot apply a `Cat` fragment to the `Dog` type: - -```graphql -query { - dog { - ...CatSimple - } -} - -fragment CatSimple on Cat { - # ... -} -``` - -**Invalid Fragment definition (#FragmentsOnCompositeTypesRule)** - -All Fragment must be defined upon (using `on ...`) a composite type, in short: object, interface, or union. - -The following examples are invalid, since defining fragments on scalars is invalid. - -```graphql -fragment fragOnScalar on Int { - # we cannot define a fragment upon a scalar (`Int`) - something -} - -fragment inlineFragOnScalar on Dog { - ... on Boolean { - # `Boolean` is not a subtype of `Dog` - somethingElse - } -} -``` - -### Directives usage - -**Directive cannot be used at this location (#KnownDirectivesRule)** - -Only GraphQL directives (`@...`) supported by The Graph API can be used. - -Here is an example with The GraphQL supported directives: - -```graphql -query { - dog { - name @include(true) - age @skip(true) - } -} -``` - -_Note: `@stream`, `@live`, `@defer` are not supported._ - -**Directive can only be used once at this location (#UniqueDirectivesPerLocationRule)** - -The directives supported by The Graph can only be used once per location. - -The following is invalid (and redundant): - -```graphql -query { - dog { - name @include(true) @include(true) - } -} -``` diff --git a/website/src/pages/ro/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/ro/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/ro/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/ro/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/ro/sps/sps-faq.mdx b/website/src/pages/ro/sps/sps-faq.mdx index 537f29b09ea6..abc1f3906686 100644 --- a/website/src/pages/ro/sps/sps-faq.mdx +++ b/website/src/pages/ro/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/ro/subgraphs/_meta-titles.json b/website/src/pages/ro/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/ro/subgraphs/_meta-titles.json +++ b/website/src/pages/ro/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/ro/subgraphs/_meta.js b/website/src/pages/ro/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/ro/subgraphs/_meta.js +++ b/website/src/pages/ro/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/ro/subgraphs/best-practices/_meta.js b/website/src/pages/ro/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/ro/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/ro/subgraphs/best-practices/avoid-eth-calls.mdx b/website/src/pages/ro/subgraphs/best-practices/avoid-eth-calls.mdx new file mode 100644 index 000000000000..e40a7b3712e4 --- /dev/null +++ b/website/src/pages/ro/subgraphs/best-practices/avoid-eth-calls.mdx @@ -0,0 +1,117 @@ +--- +title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls +sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' +--- + +## TLDR + +`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. + +## Why Avoiding `eth_calls` Is a Best Practice + +Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. + +### What Does an eth_call Look Like? + +`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: + +```yaml +event Transfer(address indexed from, address indexed to, uint256 value); +``` + +Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, Transfer } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransfer(event: Transfer): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + // Bind the ERC20 contract instance to the given address: + let instance = ERC20.bind(event.address) + + // Retrieve pool information via eth_call + let poolInfo = instance.getPoolInfo(event.params.to) + + transaction.pool = poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is functional, however is not ideal as it slows down our subgraph’s indexing. + +## How to Eliminate `eth_calls` + +Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: + +``` +event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); +``` + +With this update, the subgraph can directly index the required data without external calls: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransferWithPool(event: TransferWithPool): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + transaction.pool = event.params.poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is much more performant as it has eliminated the need for `eth_calls`. + +## How to Optimize `eth_calls` + +If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. + +## Reducing the Runtime Overhead of `eth_calls` + +For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. + +Currently, `eth_calls` can only be declared for event handlers. In the manifest, write + +```yaml +event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) +handler: handleTransferWithPool +calls: + ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) +``` + +The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. + +The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. + +Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. + +## Conclusion + +You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ro/subgraphs/best-practices/derivedfrom.mdx b/website/src/pages/ro/subgraphs/best-practices/derivedfrom.mdx new file mode 100644 index 000000000000..db3a49928c89 --- /dev/null +++ b/website/src/pages/ro/subgraphs/best-practices/derivedfrom.mdx @@ -0,0 +1,89 @@ +--- +title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom +sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' +--- + +## TLDR + +Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. + +## How to Use the `@derivedFrom` Directive + +You just need to add a `@derivedFrom` directive after your array in your schema. Like this: + +```graphql +comments: [Comment!]! @derivedFrom(field: "post") +``` + +`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. + +### Example Use Case for `@derivedFrom` + +An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. + +Let’s start with our two entities, `Post` and `Comment` + +Without optimization, you could implement it like this with an array: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! +} + +type Comment @entity { + id: Bytes! + content: String! +} +``` + +Arrays like these will effectively store extra Comments data on the Post side of the relationship. + +Here’s what an optimized version looks like using `@derivedFrom`: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! @derivedFrom(field: "post") +} + +type Comment @entity { + id: Bytes! + content: String! + post: Post! +} +``` + +Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. + +This will not only make our subgraph more efficient, but it will also unlock three features: + +1. We can query the `Post` and see all of its comments. + +2. We can do a reverse lookup and query any `Comment` and see which post it comes from. + +3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. + +## Conclusion + +Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. + +For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/pl/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/ro/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/pl/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/ro/subgraphs/best-practices/grafting-hotfix.mdx index 910e32cfacde..d514e1633c75 100644 --- a/website/src/pages/pl/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/ro/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ro/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx b/website/src/pages/ro/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx new file mode 100644 index 000000000000..6ff60ec9ab34 --- /dev/null +++ b/website/src/pages/ro/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -0,0 +1,191 @@ +--- +title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs +sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' +--- + +## TLDR + +Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. + +## Immutable Entities + +To make an entity immutable, we simply add `(immutable: true)` to an entity. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. + +Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. + +### Under the hood + +Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. + +### When not to use Immutable Entities + +If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. + +## Bytes as IDs + +Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. + +### Reasons to Not Use Bytes as IDs + +1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. +2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. +3. Indexing and querying performance improvements are not desired. + +### Concatenating With Bytes as IDs + +It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. + +Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. + +```typescript +export function handleTransfer(event: TransferEvent): void { + let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) + entity.from = event.params.from + entity.to = event.params.to + entity.value = event.params.value + + entity.blockNumber = event.block.number + entity.blockTimestamp = event.block.timestamp + entity.transactionHash = event.transaction.hash + + entity.save() +} +``` + +### Sorting With Bytes as IDs + +Sorting using Bytes as IDs is not optimal as seen in this example query and response. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: id) { + id + from + to + value + } +} +``` + +Query response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x00010000", + "from": "0xabcd...", + "to": "0x1234...", + "value": "256" + }, + { + "id": "0x00020000", + "from": "0xefgh...", + "to": "0x5678...", + "value": "512" + }, + { + "id": "0x01000000", + "from": "0xijkl...", + "to": "0x9abc...", + "value": "1" + } + ] + } +} +``` + +The IDs are returned as hex. + +To improve sorting, we should create another field on the entity that is a BigInt. + +```graphql +type Transfer @entity { + id: Bytes! + from: Bytes! # address + to: Bytes! # address + value: BigInt! # unit256 + tokenId: BigInt! # uint256 +} +``` + +This will allow for sorting to be optimized sequentially. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: tokenId) { + id + tokenId + } +} +``` + +Query Response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x…", + "tokenId": "1" + }, + { + "id": "0x…", + "tokenId": "2" + }, + { + "id": "0x…", + "tokenId": "3" + } + ] + } +} +``` + +## Conclusion + +Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. + +Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ro/subgraphs/best-practices/pruning.mdx b/website/src/pages/ro/subgraphs/best-practices/pruning.mdx new file mode 100644 index 000000000000..1b51dde8894f --- /dev/null +++ b/website/src/pages/ro/subgraphs/best-practices/pruning.mdx @@ -0,0 +1,56 @@ +--- +title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning +sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' +--- + +## TLDR + +[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. + +## How to Prune a Subgraph With `indexerHints` + +Add a section called `indexerHints` in the manifest. + +`indexerHints` has three `prune` options: + +- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. +- `prune: `: Sets a custom limit on the number of historical blocks to retain. +- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. + +We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: + +```yaml +specVersion: 1.0.0 +schema: + file: ./schema.graphql +indexerHints: + prune: auto +dataSources: + - kind: ethereum/contract + name: Contract + network: mainnet +``` + +## Important Considerations + +- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. + +- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). + +## Conclusion + +Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ro/subgraphs/cookbook/timeseries.mdx b/website/src/pages/ro/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/ro/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/ro/subgraphs/best-practices/timeseries.mdx index 7c1c41008d29..cacdc44711fe 100644 --- a/website/src/pages/ro/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/ro/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ro/subgraphs/cookbook/_meta.js b/website/src/pages/ro/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/ro/subgraphs/cookbook/_meta.js +++ b/website/src/pages/ro/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/ro/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/ro/subgraphs/cookbook/avoid-eth-calls.mdx deleted file mode 100644 index ae29cdf03a34..000000000000 --- a/website/src/pages/ro/subgraphs/cookbook/avoid-eth-calls.mdx +++ /dev/null @@ -1,117 +0,0 @@ ---- -title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls -sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' ---- - -## TLDR - -`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. - -## Why Avoiding `eth_calls` Is a Best Practice - -Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. - -### What Does an eth_call Look Like? - -`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: - -```yaml -event Transfer(address indexed from, address indexed to, uint256 value); -``` - -Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, Transfer } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransfer(event: Transfer): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - // Bind the ERC20 contract instance to the given address: - let instance = ERC20.bind(event.address) - - // Retrieve pool information via eth_call - let poolInfo = instance.getPoolInfo(event.params.to) - - transaction.pool = poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is functional, however is not ideal as it slows down our subgraph’s indexing. - -## How to Eliminate `eth_calls` - -Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: - -``` -event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); -``` - -With this update, the subgraph can directly index the required data without external calls: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransferWithPool(event: TransferWithPool): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - transaction.pool = event.params.poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is much more performant as it has eliminated the need for `eth_calls`. - -## How to Optimize `eth_calls` - -If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. - -## Reducing the Runtime Overhead of `eth_calls` - -For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. - -Currently, `eth_calls` can only be declared for event handlers. In the manifest, write - -```yaml -event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) -handler: handleTransferWithPool -calls: - ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) -``` - -The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. - -The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. - -Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. - -## Conclusion - -You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ro/subgraphs/cookbook/cosmos.mdx b/website/src/pages/ro/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 5ccf1025ca47..000000000000 --- a/website/src/pages/ro/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Building Subgraphs on Cosmos ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## What are Cosmos subgraphs? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -There are four types of handlers supported in Cosmos subgraphs: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Even though all data can be accessed with a block handler, other handlers enable subgraph developers to process data in a much more granular way. - -## Building a Cosmos subgraph - -### Subgraph Dependencies - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Subgraph Main Components - -There are three key parts when it comes to defining a subgraph: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### Subgraph Manifest Definition - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### Schema Definition - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript Mappings - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Each handler type comes with its own data structure that is passed as an argument to a mapping function. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Message decoding - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Creating and building a Cosmos subgraph - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Deploying a Cosmos subgraph - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Querying a Cosmos subgraph - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Supported Cosmos Blockchains - -### Cosmos Hub - -#### What is Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### Networks - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### What is Osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### Networks - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## Example Subgraphs - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/ro/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/ro/subgraphs/cookbook/derivedfrom.mdx deleted file mode 100644 index a0942645c999..000000000000 --- a/website/src/pages/ro/subgraphs/cookbook/derivedfrom.mdx +++ /dev/null @@ -1,89 +0,0 @@ ---- -title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom -sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' ---- - -## TLDR - -Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. - -## How to Use the `@derivedFrom` Directive - -You just need to add a `@derivedFrom` directive after your array in your schema. Like this: - -```graphql -comments: [Comment!]! @derivedFrom(field: "post") -``` - -`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. - -### Example Use Case for `@derivedFrom` - -An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. - -Let’s start with our two entities, `Post` and `Comment` - -Without optimization, you could implement it like this with an array: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! -} - -type Comment @entity { - id: Bytes! - content: String! -} -``` - -Arrays like these will effectively store extra Comments data on the Post side of the relationship. - -Here’s what an optimized version looks like using `@derivedFrom`: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! @derivedFrom(field: "post") -} - -type Comment @entity { - id: Bytes! - content: String! - post: Post! -} -``` - -Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. - -This will not only make our subgraph more efficient, but it will also unlock three features: - -1. We can query the `Post` and see all of its comments. - -2. We can do a reverse lookup and query any `Comment` and see which post it comes from. - -3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. - -## Conclusion - -Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. - -For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ro/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/ro/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx deleted file mode 100644 index 511565bb3dd4..000000000000 --- a/website/src/pages/ro/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ /dev/null @@ -1,191 +0,0 @@ ---- -title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs -sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' ---- - -## TLDR - -Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. - -## Immutable Entities - -To make an entity immutable, we simply add `(immutable: true)` to an entity. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. - -Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. - -### Under the hood - -Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. - -### When not to use Immutable Entities - -If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. - -## Bytes as IDs - -Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. - -### Reasons to Not Use Bytes as IDs - -1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. -2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. -3. Indexing and querying performance improvements are not desired. - -### Concatenating With Bytes as IDs - -It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. - -Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. - -```typescript -export function handleTransfer(event: TransferEvent): void { - let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) - entity.from = event.params.from - entity.to = event.params.to - entity.value = event.params.value - - entity.blockNumber = event.block.number - entity.blockTimestamp = event.block.timestamp - entity.transactionHash = event.transaction.hash - - entity.save() -} -``` - -### Sorting With Bytes as IDs - -Sorting using Bytes as IDs is not optimal as seen in this example query and response. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: id) { - id - from - to - value - } -} -``` - -Query response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x00010000", - "from": "0xabcd...", - "to": "0x1234...", - "value": "256" - }, - { - "id": "0x00020000", - "from": "0xefgh...", - "to": "0x5678...", - "value": "512" - }, - { - "id": "0x01000000", - "from": "0xijkl...", - "to": "0x9abc...", - "value": "1" - } - ] - } -} -``` - -The IDs are returned as hex. - -To improve sorting, we should create another field on the entity that is a BigInt. - -```graphql -type Transfer @entity { - id: Bytes! - from: Bytes! # address - to: Bytes! # address - value: BigInt! # unit256 - tokenId: BigInt! # uint256 -} -``` - -This will allow for sorting to be optimized sequentially. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: tokenId) { - id - tokenId - } -} -``` - -Query Response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x…", - "tokenId": "1" - }, - { - "id": "0x…", - "tokenId": "2" - }, - { - "id": "0x…", - "tokenId": "3" - } - ] - } -} -``` - -## Conclusion - -Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. - -Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ro/subgraphs/cookbook/pruning.mdx b/website/src/pages/ro/subgraphs/cookbook/pruning.mdx deleted file mode 100644 index e212d5d02bc9..000000000000 --- a/website/src/pages/ro/subgraphs/cookbook/pruning.mdx +++ /dev/null @@ -1,56 +0,0 @@ ---- -title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning -sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' ---- - -## TLDR - -[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. - -## How to Prune a Subgraph With `indexerHints` - -Add a section called `indexerHints` in the manifest. - -`indexerHints` has three `prune` options: - -- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. -- `prune: `: Sets a custom limit on the number of historical blocks to retain. -- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. - -We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: - -```yaml -specVersion: 1.0.0 -schema: - file: ./schema.graphql -indexerHints: - prune: auto -dataSources: - - kind: ethereum/contract - name: Contract - network: mainnet -``` - -## Important Considerations - -- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. - -- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). - -## Conclusion - -Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ro/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/ro/subgraphs/developing/creating/graph-ts/api.mdx index b5cec3b091e4..35bb04826c98 100644 --- a/website/src/pages/ro/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/ro/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/ro/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/ro/subgraphs/developing/creating/install-the-cli.mdx index a60f181e9a50..f98ef589aaef 100644 --- a/website/src/pages/ro/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/ro/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Install the Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Overview diff --git a/website/src/pages/ro/subgraphs/developing/deploying/_meta.js b/website/src/pages/ro/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/ro/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/ro/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/ro/subgraphs/querying/best-practices.mdx b/website/src/pages/ro/subgraphs/querying/best-practices.mdx index 3736fa32faeb..ff5f381e2993 100644 --- a/website/src/pages/ro/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/ro/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Sending a query to a GraphQL API diff --git a/website/src/pages/ro/subgraphs/querying/managing-api-keys.mdx b/website/src/pages/ro/subgraphs/querying/managing-api-keys.mdx index f7aff33ea926..6964b1a7ad9b 100644 --- a/website/src/pages/ro/subgraphs/querying/managing-api-keys.mdx +++ b/website/src/pages/ro/subgraphs/querying/managing-api-keys.mdx @@ -1,5 +1,5 @@ --- -title: Managing your API keys +title: Managing API keys --- ## Overview diff --git a/website/src/pages/pl/substreams/developing/sinks/sinks.mdx b/website/src/pages/ro/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/pl/substreams/developing/sinks/sinks.mdx rename to website/src/pages/ro/substreams/developing/sinks.mdx diff --git a/website/src/pages/ro/substreams/developing/sinks/_meta.js b/website/src/pages/ro/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/ro/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/ro/substreams/quick-start.mdx b/website/src/pages/ro/substreams/quick-start.mdx index 34e59b54491b..b5eec572b00a 100644 --- a/website/src/pages/ro/substreams/quick-start.mdx +++ b/website/src/pages/ro/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/ru/resources/_meta-titles.json b/website/src/pages/ru/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/ru/resources/_meta-titles.json +++ b/website/src/pages/ru/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/ru/resources/_meta.js b/website/src/pages/ru/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/ru/resources/_meta.js +++ b/website/src/pages/ru/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/ru/resources/release-notes/_meta.js b/website/src/pages/ru/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/ru/resources/release-notes/_meta.js rename to website/src/pages/ru/resources/migration-guides/_meta.js diff --git a/website/src/pages/ru/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/ru/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/ru/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/ru/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/ru/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/ru/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 100% rename from website/src/pages/ru/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/ru/resources/migration-guides/graphql-validations-migration-guide.mdx diff --git a/website/src/pages/ru/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/ru/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/ru/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/ru/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/ru/sps/sps-faq.mdx b/website/src/pages/ru/sps/sps-faq.mdx index ed89b05d26f6..fc2d9862921f 100644 --- a/website/src/pages/ru/sps/sps-faq.mdx +++ b/website/src/pages/ru/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/ru/subgraphs/_meta-titles.json b/website/src/pages/ru/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/ru/subgraphs/_meta-titles.json +++ b/website/src/pages/ru/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/ru/subgraphs/_meta.js b/website/src/pages/ru/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/ru/subgraphs/_meta.js +++ b/website/src/pages/ru/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/ru/subgraphs/best-practices/_meta.js b/website/src/pages/ru/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/ru/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/ru/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/ru/subgraphs/best-practices/avoid-eth-calls.mdx similarity index 96% rename from website/src/pages/ru/subgraphs/cookbook/avoid-eth-calls.mdx rename to website/src/pages/ru/subgraphs/best-practices/avoid-eth-calls.mdx index 55f3377b2f9a..f44611137483 100644 --- a/website/src/pages/ru/subgraphs/cookbook/avoid-eth-calls.mdx +++ b/website/src/pages/ru/subgraphs/best-practices/avoid-eth-calls.mdx @@ -104,14 +104,14 @@ calls: ## Лучшие практики для субграфов 1-6 -1. [Увеличение скорости запросов с помощью обрезки субграфов](/subgraphs/cookbook/pruning/) +1. [Увеличение скорости запросов с помощью обрезки субграфов](/subgraphs/best-practices/pruning/) -2. [Улучшение индексирования и отклика запросов с использованием @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Улучшение индексирования и отклика запросов с использованием @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Улучшение индексирования и производительности запросов с использованием неизменяемых объектов и байтов в качестве идентификаторов](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Улучшение индексирования и производительности запросов с использованием неизменяемых объектов и байтов в качестве идентификаторов](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Увеличение скорости индексирования путем избегания `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Увеличение скорости индексирования путем избегания `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Упрощение и оптимизация с помощью временных рядов и агрегаций](/subgraphs/cookbook/timeseries/) +5. [Упрощение и оптимизация с помощью временных рядов и агрегаций](/subgraphs/best-practices/timeseries/) -6. [Использование переноса (графтинга) для быстрого развертывания исправлений](/subgraphs/cookbook/grafting-hotfix/) +6. [Использование переноса (графтинга) для быстрого развертывания исправлений](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ru/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/ru/subgraphs/best-practices/derivedfrom.mdx similarity index 94% rename from website/src/pages/ru/subgraphs/cookbook/derivedfrom.mdx rename to website/src/pages/ru/subgraphs/best-practices/derivedfrom.mdx index 6dc72b24be00..3e918462a606 100644 --- a/website/src/pages/ru/subgraphs/cookbook/derivedfrom.mdx +++ b/website/src/pages/ru/subgraphs/best-practices/derivedfrom.mdx @@ -76,14 +76,14 @@ type Comment @entity { ## Лучшие практики для субграфов 1-6 -1. [Увеличение скорости запросов с помощью обрезки субграфов](/subgraphs/cookbook/pruning/) +1. [Увеличение скорости запросов с помощью обрезки субграфов](/subgraphs/best-practices/pruning/) -2. [Улучшение индексирования и отклика запросов с использованием @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Улучшение индексирования и отклика запросов с использованием @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Улучшение индексирования и производительности запросов с использованием неизменяемых объектов и байтов в качестве идентификаторов](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Улучшение индексирования и производительности запросов с использованием неизменяемых объектов и байтов в качестве идентификаторов](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Увеличение скорости индексирования путем избегания `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Увеличение скорости индексирования путем избегания `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Упрощение и оптимизация с помощью временных рядов и агрегаций](/subgraphs/cookbook/timeseries/) +5. [Упрощение и оптимизация с помощью временных рядов и агрегаций](/subgraphs/best-practices/timeseries/) -6. [Использование переноса (графтинга) для быстрого развертывания исправлений](/subgraphs/cookbook/grafting-hotfix/) +6. [Использование переноса (графтинга) для быстрого развертывания исправлений](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ru/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/ru/subgraphs/best-practices/grafting-hotfix.mdx similarity index 97% rename from website/src/pages/ru/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/ru/subgraphs/best-practices/grafting-hotfix.mdx index 0bfd55555d50..ebb6b49ea9bf 100644 --- a/website/src/pages/ru/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/ru/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ sidebarTitle: 'Subgraph Best Practice 6: Grafting and Hotfixing' ## Лучшие практики для субграфов 1-6 -1. [Увеличение скорости запросов с помощью обрезки субграфов](/subgraphs/cookbook/pruning/) +1. [Увеличение скорости запросов с помощью обрезки субграфов](/subgraphs/best-practices/pruning/) -2. [Улучшение индексирования и отклика запросов с использованием @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Улучшение индексирования и отклика запросов с использованием @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Улучшение индексирования и производительности запросов с использованием неизменяемых объектов и байтов в качестве идентификаторов](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Улучшение индексирования и производительности запросов с использованием неизменяемых объектов и байтов в качестве идентификаторов](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Увеличение скорости индексирования путем избегания `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Увеличение скорости индексирования путем избегания `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Упрощение и оптимизация с помощью временных рядов и агрегаций](/subgraphs/cookbook/timeseries/) +5. [Упрощение и оптимизация с помощью временных рядов и агрегаций](/subgraphs/best-practices/timeseries/) -6. [Использование переноса (графтинга) для быстрого развертывания исправлений](/subgraphs/cookbook/grafting-hotfix/) +6. [Использование переноса (графтинга) для быстрого развертывания исправлений](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ru/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/ru/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx similarity index 96% rename from website/src/pages/ru/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx rename to website/src/pages/ru/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx index 9628878ea3c0..194240e032c3 100644 --- a/website/src/pages/ru/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ b/website/src/pages/ru/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -178,14 +178,14 @@ type Transfer @entity { ## Лучшие практики для субграфов 1-6 -1. [Увеличение скорости запросов с помощью обрезки субграфов](/subgraphs/cookbook/pruning/) +1. [Увеличение скорости запросов с помощью обрезки субграфов](/subgraphs/best-practices/pruning/) -2. [Улучшение индексирования и отклика запросов с использованием @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Улучшение индексирования и отклика запросов с использованием @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Улучшение индексирования и производительности запросов с использованием неизменяемых объектов и байтов в качестве идентификаторов](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Улучшение индексирования и производительности запросов с использованием неизменяемых объектов и байтов в качестве идентификаторов](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Увеличение скорости индексирования путем избегания `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Увеличение скорости индексирования путем избегания `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Упрощение и оптимизация с помощью временных рядов и агрегаций](/subgraphs/cookbook/timeseries/) +5. [Упрощение и оптимизация с помощью временных рядов и агрегаций](/subgraphs/best-practices/timeseries/) -6. [Использование переноса (графтинга) для быстрого развертывания исправлений](/subgraphs/cookbook/grafting-hotfix/) +6. [Использование переноса (графтинга) для быстрого развертывания исправлений](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ru/subgraphs/cookbook/pruning.mdx b/website/src/pages/ru/subgraphs/best-practices/pruning.mdx similarity index 93% rename from website/src/pages/ru/subgraphs/cookbook/pruning.mdx rename to website/src/pages/ru/subgraphs/best-practices/pruning.mdx index be3c6f1178b8..f99ae4861ec4 100644 --- a/website/src/pages/ru/subgraphs/cookbook/pruning.mdx +++ b/website/src/pages/ru/subgraphs/best-practices/pruning.mdx @@ -43,14 +43,14 @@ dataSources: ## Лучшие практики для субграфов 1-6 -1. [Увеличение скорости запросов с помощью обрезки субграфов](/subgraphs/cookbook/pruning/) +1. [Увеличение скорости запросов с помощью обрезки субграфов](/subgraphs/best-practices/pruning/) -2. [Улучшение индексирования и отклика запросов с использованием @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Улучшение индексирования и отклика запросов с использованием @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Улучшение индексирования и производительности запросов с использованием неизменяемых объектов и байтов в качестве идентификаторов](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Улучшение индексирования и производительности запросов с использованием неизменяемых объектов и байтов в качестве идентификаторов](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Увеличение скорости индексирования путем избегания `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Увеличение скорости индексирования путем избегания `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Упрощение и оптимизация с помощью временных рядов и агрегаций](/subgraphs/cookbook/timeseries/) +5. [Упрощение и оптимизация с помощью временных рядов и агрегаций](/subgraphs/best-practices/timeseries/) -6. [Использование переноса (графтинга) для быстрого развертывания исправлений](/subgraphs/cookbook/grafting-hotfix/) +6. [Использование переноса (графтинга) для быстрого развертывания исправлений](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ru/subgraphs/cookbook/timeseries.mdx b/website/src/pages/ru/subgraphs/best-practices/timeseries.mdx similarity index 97% rename from website/src/pages/ru/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/ru/subgraphs/best-practices/timeseries.mdx index 050baaad81b1..5520d80a970a 100644 --- a/website/src/pages/ru/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/ru/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ type TokenStats @aggregation(intervals: ["hour", "day"], source: "TokenData") { ## Лучшие практики для субграфов 1-6 -1. [Увеличение скорости запросов с помощью обрезки субграфов](/subgraphs/cookbook/pruning/) +1. [Увеличение скорости запросов с помощью обрезки субграфов](/subgraphs/best-practices/pruning/) -2. [Улучшение индексирования и отклика запросов с использованием @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Улучшение индексирования и отклика запросов с использованием @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Улучшение индексирования и производительности запросов с использованием неизменяемых объектов и байтов в качестве идентификаторов](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Улучшение индексирования и производительности запросов с использованием неизменяемых объектов и байтов в качестве идентификаторов](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Увеличение скорости индексирования путем избегания `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Увеличение скорости индексирования путем избегания `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Упрощение и оптимизация с помощью временных рядов и агрегаций](/subgraphs/cookbook/timeseries/) +5. [Упрощение и оптимизация с помощью временных рядов и агрегаций](/subgraphs/best-practices/timeseries/) -6. [Использование переноса (графтинга) для быстрого развертывания исправлений](/subgraphs/cookbook/grafting-hotfix/) +6. [Использование переноса (графтинга) для быстрого развертывания исправлений](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ru/subgraphs/cookbook/_meta.js b/website/src/pages/ru/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/ru/subgraphs/cookbook/_meta.js +++ b/website/src/pages/ru/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/ru/subgraphs/cookbook/cosmos.mdx b/website/src/pages/ru/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index cfa4b94b970f..000000000000 --- a/website/src/pages/ru/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Создание субграфов на Cosmos ---- - -Это руководство служит введением в создание субграфов для индексирования блокчейнов, основанных на экосистеме [Cosmos](https://cosmos.network/). - -## Что такое субграфы на Cosmos? - -The Graph позволяет разработчикам обрабатывать события блокчейна и предоставлять полученные данные через открытый GraphQL API, называемый субграфом. [Graph Node](https://github.com/graphprotocol/graph-node) теперь способен обрабатывать события Cosmos, что означает, что разработчики Cosmos могут создавать субграфы для удобного индексирования событий на чейне. - -Существует четыре типа обработчиков, поддерживаемых в субграфах Cosmos: - -- **Обработчики блоков** запускаются каждый раз, когда новый блок добавляется в чейн. -- **Обработчики событий** запускаются, когда происходит определённое событие. -- **Обработчики транзакций** запускаются при выполнении транзакции. -- **Обработчики сообщений** запускаются при появлении определённого сообщения. - -На основе [официальной документации Cosmos](https://docs.cosmos.network/): - -> [События](https://docs.cosmos.network/main/learn/advanced/events) — это объекты, содержащие информацию о выполнении приложения. Они используются в основном сервисами, такими как сервисы для отслеживания блоков и кошельки, для отслеживания выполнения различных сообщений и индексирования транзакций. -> -> [Транзакции](https://docs.cosmos.network/main/learn/advanced/transactions) — это объекты, создаваемые конечными пользователями для инициирования изменений состояния в приложении. -> -> [Сообщения](https://docs.cosmos.network/main/learn/advanced/transactions#messages) — это специфичные для модулей объекты, которые инициируют переходы состояния в рамках модуля, к которому они относятся. - -Хотя доступ ко всем данным можно получить с помощью обработчика блоков, другие обработчики позволяют разработчикам субграфов обрабатывать данные гораздо более детально. - -## Создание субграфа на Cosmos - -### Зависимости субграфа - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) — это инструмент командной строки для создания и развертывания субграфов. Для работы с субграфами Cosmos требуется версия `>=0.30.0`. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) — это библиотека типов, специфичных для субграфов, для работы с субграфами Cosmos требуется версия `>=0.27.0`. - -### Основные компоненты субграфа - -Когда дело доходит до определения субграфа, имеется три ключевых момента: - -**subgraph.yaml**: файл YAML, содержащий манифест субграфа, который определяет, какие события отслеживать и как их обрабатывать. - -**schema.graphql**: схема GraphQL, которая определяет, какие данные хранятся для Вашего субграфа и как их можно запрашивать через GraphQL. - -**Мэппинги на AssemblyScript**: код на [AssemblyScript](https://github.com/AssemblyScript/assemblyscript), который преобразует данные блокчейна в объекты, определенные в Вашей схеме. - -### Определение манифеста субграфа - -Манифест субграфа (`subgraph.yaml`) идентифицирует источники данных для субграфа, триггеры, представляющие интерес, и функции (`handlers`), которые должны быть выполнены в ответ на эти триггеры. Ниже приведен пример манифеста субграфа для субграфа Cosmos: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # ссылка на файл схемы -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # это будет меняться для каждого блокчейна, основанного на Cosmos. В данном случае в примере используется основная сеть Cosmos Hub. - source: - startBlock: 0 # требуется для Cosmos, установите для этого параметра значение 0, чтобы начать индексирование с начального блока генезиса чейна. - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # имя функции в мэппинг-файле - eventHandlers: - - event: rewards # тип события, которое будет обрабатываться - handler: handleReward # имя функции в мэппинг-файле - transactionHandlers: - - handler: handleTransaction # имя функции в мэппинг-файле - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # тип сообщения - handler: handleMsgDelegate # имя функции в мэппинг-файле - file: ./src/mapping.ts # ссылка на мэппинг-файл скрипта сборки -``` - -- Субграфы Cosmos вводят новый `kind` (тип) источника данных (`cosmos`). -- `network` (сеть) должна соответствовать чейну в экосистеме Cosmos. В этом примере используется майннет Cosmos Hub. - -### Определение схемы - -Определение схемы описывает структуру итоговой базы данных субграфа и отношения между объектами. Это не зависит от исходного источника данных. Более подробную информацию об определении схемы субграфа можно найти [здесь](/developing/creating-a-subgraph/#the-graphql-schema). - -### Мэппинги AssemblyScript - -Обработчики для обработки событий написаны на [AssemblyScript](https://www.assemblyscript.org/). - -Индексирование Cosmos вводит специфичные для Cosmos типы данных в [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Каждый тип обработчика имеет свою собственную структуру данных, которая передается в качестве аргумента функции мэппинга. - -- Обработчики блоков получают тип `Block`. -- Обработчики событий получают тип `EventData`. -- Обработчики транзакций получают тип `TransactionData`. -- Обработчики сообщений получают тип `MessageData`. - -Как часть `MessageData`, обработчик сообщений получает контекст транзакции, который содержит наиболее важную информацию о транзакции, в рамках которой было выполнено сообщение. Контекст транзакции также доступен в типе `EventData`, но только когда соответствующее событие связано с транзакцией. Кроме того, все обработчики получают ссылку на блок (`HeaderOnlyBlock`). - -Полный список типов для интеграции с Cosmos можно найти [здесь](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Расшифровка сообщений - -Важно отметить, что сообщения Cosmos специфичны для каждого чейна и передаются в субграф в виде сериализованного полезного груза [Protocol Buffers](https://protobuf.dev/). В результате, данные сообщения необходимо декодировать в функции мэппинга, прежде чем они смогут быть обработаны. - -Пример того, как декодировать данные сообщений в субграфе, можно найти [здесь](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Создание и построение субграфа на Cosmos - -Первым шагом перед написанием мэппингов субграфа является генерация привязок типов на основе объектов, определённых в файле схемы субграфа (`schema.graphql`). Это позволит функциям мэппинга создавать новые объекты этих типов и сохранять их в хранилище. Это делается с помощью команды CLI `codegen`: - -```bash -$ graph codegen -``` - -Как только мэппинги будут готовы, нужно построить субграф. Этот шаг выявит все ошибки, которые могут быть в манифесте или мэппингах. Субграф должен успешно построиться, чтобы его можно было развернуть на Graph Node. Это делается с помощью команды CLI `build`: - -```bash -$ graph build -``` - -## Развертывание субграфа на Cosmos - -После того как субграф создан, его можно развернуть с помощью команды `graph deploy` в CLI: - -**Subgraph Studio** - -Посетите Subgraph Studio, чтобы создать новый субграф. - -```bash -graph deploy subgraph-name -``` - -**Локальный Graph Node (на основе конфигурации по умолчанию):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Запрос субграфа на Cosmos - -Конечная точка GraphQL для субграфов Cosmos определяется схемой, с использованием существующего интерфейса API. Пожалуйста, изучите [документацию по GraphQL API](/subgraphs/querying/graphql-api/) для получения дополнительной информации. - -## Поддерживаемые блокчейны Cosmos - -### Cosmos Hub - -#### Что такое Cosmos Hub? - -[Блокчейн Cosmos Hub](https://hub.cosmos.network/) — это первый блокчейн в экосистеме [Cosmos](https://cosmos.network/). Для получения дополнительной информации Вы можете ознакомиться с [официальной документацией](https://docs.cosmos.network/). - -#### Сети - -Майннет Cosmos Hub называется `cosmoshub-4`. Текущий тестнет Cosmos Hub — `theta-testnet-001`.
Другие сети Cosmos Hub, такие как `cosmoshub-3`, приостановлены, поэтому данные для них не предоставляются. - -### Osmosis - -> Поддержка Osmosis в Graph Node и Subgraph Studio находится в стадии бета-тестирования: обращайтесь к команде the Graph по любым вопросам, касающимся создания субграфов Osmosis! - -#### Что такое Osmosis? - -[Osmosis](https://osmosis.zone/) — это децентрализованный протокол автоматизированного маркет-мейкера (AMM), построенный на основе Cosmos SDK. Он позволяет пользователям создавать собственные пулы ликвидности и торговать токенами, поддерживающими IBC. Для получения дополнительной информации, Вы можете ознакомиться с [официальной документацией](https://docs.osmosis.zone/). - -#### Сети - -Майннет Osmosis — это `osmosis-1`. Текущий тестнет Osmosis — это `osmo-test-4`. - -## Примеры субграфов - -Вот несколько примеров субграфов для справки: - -[Пример фильтрации блоков](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Пример вознаграждений валидатора](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Пример делегирования валидатора](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Пример обмена токенов Osmosis](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/ru/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/ru/subgraphs/developing/creating/graph-ts/api.mdx index 94db3f66da8a..88bfcafe7af0 100644 --- a/website/src/pages/ru/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/ru/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Узнайте, какие встроенные API можно использовать при написании мэппингов субграфов. По умолчанию доступны два типа API: @@ -35,7 +35,7 @@ title: AssemblyScript API | 0.0.8 | Добавлена проверка наличия полей в схеме при сохранении объекта. | | 0.0.7 | К типам Ethereum добавлены классы `TransactionReceipt` и `Log`
К объекту Ethereum Event добавлено поле `receipt` | | 0.0.6 | В объект Ethereum Transaction добавлено поле `nonce`
В объект Ethereum Block добавлено поле `baseFeePerGas` | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | В объект Ethereum SmartContractCall добавлено поле `functionSignature` | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | В объект Ethereum Transaction добавлено поле `input` | diff --git a/website/src/pages/ru/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/ru/subgraphs/developing/creating/install-the-cli.mdx index bff4ca3d0b23..b48104c2ff0d 100644 --- a/website/src/pages/ru/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/ru/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Установка Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Обзор diff --git a/website/src/pages/ru/subgraphs/developing/deploying/_meta.js b/website/src/pages/ru/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/ru/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/ru/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/ru/subgraphs/querying/best-practices.mdx b/website/src/pages/ru/subgraphs/querying/best-practices.mdx index 8b9721a393e8..e7ecc1795d98 100644 --- a/website/src/pages/ru/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/ru/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Sending a query to a GraphQL API diff --git a/website/src/pages/ru/substreams/developing/sinks/sinks.mdx b/website/src/pages/ru/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/ru/substreams/developing/sinks/sinks.mdx rename to website/src/pages/ru/substreams/developing/sinks.mdx diff --git a/website/src/pages/ru/substreams/developing/sinks/_meta.js b/website/src/pages/ru/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/ru/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/ru/substreams/quick-start.mdx b/website/src/pages/ru/substreams/quick-start.mdx index f5600a771d23..c74623e3c753 100644 --- a/website/src/pages/ru/substreams/quick-start.mdx +++ b/website/src/pages/ru/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/sv/resources/_meta-titles.json b/website/src/pages/sv/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/sv/resources/_meta-titles.json +++ b/website/src/pages/sv/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/sv/resources/_meta.js b/website/src/pages/sv/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/sv/resources/_meta.js +++ b/website/src/pages/sv/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/sv/resources/release-notes/_meta.js b/website/src/pages/sv/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/sv/resources/release-notes/_meta.js rename to website/src/pages/sv/resources/migration-guides/_meta.js diff --git a/website/src/pages/sv/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/sv/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/sv/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/sv/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/sv/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/sv/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 100% rename from website/src/pages/sv/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/sv/resources/migration-guides/graphql-validations-migration-guide.mdx diff --git a/website/src/pages/sv/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/sv/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/sv/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/sv/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/sv/sps/sps-faq.mdx b/website/src/pages/sv/sps/sps-faq.mdx index 267d39f5fc3d..74ae7af82977 100644 --- a/website/src/pages/sv/sps/sps-faq.mdx +++ b/website/src/pages/sv/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/sv/subgraphs/_meta-titles.json b/website/src/pages/sv/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/sv/subgraphs/_meta-titles.json +++ b/website/src/pages/sv/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/sv/subgraphs/_meta.js b/website/src/pages/sv/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/sv/subgraphs/_meta.js +++ b/website/src/pages/sv/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/sv/subgraphs/best-practices/_meta.js b/website/src/pages/sv/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/sv/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/sv/subgraphs/best-practices/avoid-eth-calls.mdx b/website/src/pages/sv/subgraphs/best-practices/avoid-eth-calls.mdx new file mode 100644 index 000000000000..e40a7b3712e4 --- /dev/null +++ b/website/src/pages/sv/subgraphs/best-practices/avoid-eth-calls.mdx @@ -0,0 +1,117 @@ +--- +title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls +sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' +--- + +## TLDR + +`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. + +## Why Avoiding `eth_calls` Is a Best Practice + +Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. + +### What Does an eth_call Look Like? + +`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: + +```yaml +event Transfer(address indexed from, address indexed to, uint256 value); +``` + +Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, Transfer } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransfer(event: Transfer): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + // Bind the ERC20 contract instance to the given address: + let instance = ERC20.bind(event.address) + + // Retrieve pool information via eth_call + let poolInfo = instance.getPoolInfo(event.params.to) + + transaction.pool = poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is functional, however is not ideal as it slows down our subgraph’s indexing. + +## How to Eliminate `eth_calls` + +Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: + +``` +event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); +``` + +With this update, the subgraph can directly index the required data without external calls: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransferWithPool(event: TransferWithPool): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + transaction.pool = event.params.poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is much more performant as it has eliminated the need for `eth_calls`. + +## How to Optimize `eth_calls` + +If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. + +## Reducing the Runtime Overhead of `eth_calls` + +For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. + +Currently, `eth_calls` can only be declared for event handlers. In the manifest, write + +```yaml +event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) +handler: handleTransferWithPool +calls: + ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) +``` + +The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. + +The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. + +Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. + +## Conclusion + +You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/sv/subgraphs/best-practices/derivedfrom.mdx b/website/src/pages/sv/subgraphs/best-practices/derivedfrom.mdx new file mode 100644 index 000000000000..db3a49928c89 --- /dev/null +++ b/website/src/pages/sv/subgraphs/best-practices/derivedfrom.mdx @@ -0,0 +1,89 @@ +--- +title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom +sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' +--- + +## TLDR + +Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. + +## How to Use the `@derivedFrom` Directive + +You just need to add a `@derivedFrom` directive after your array in your schema. Like this: + +```graphql +comments: [Comment!]! @derivedFrom(field: "post") +``` + +`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. + +### Example Use Case for `@derivedFrom` + +An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. + +Let’s start with our two entities, `Post` and `Comment` + +Without optimization, you could implement it like this with an array: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! +} + +type Comment @entity { + id: Bytes! + content: String! +} +``` + +Arrays like these will effectively store extra Comments data on the Post side of the relationship. + +Here’s what an optimized version looks like using `@derivedFrom`: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! @derivedFrom(field: "post") +} + +type Comment @entity { + id: Bytes! + content: String! + post: Post! +} +``` + +Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. + +This will not only make our subgraph more efficient, but it will also unlock three features: + +1. We can query the `Post` and see all of its comments. + +2. We can do a reverse lookup and query any `Comment` and see which post it comes from. + +3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. + +## Conclusion + +Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. + +For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/sv/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/sv/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/sv/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/sv/subgraphs/best-practices/grafting-hotfix.mdx index 5bf9f2e61e23..2fea7d3f3239 100644 --- a/website/src/pages/sv/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/sv/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/sv/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx b/website/src/pages/sv/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx new file mode 100644 index 000000000000..6ff60ec9ab34 --- /dev/null +++ b/website/src/pages/sv/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -0,0 +1,191 @@ +--- +title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs +sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' +--- + +## TLDR + +Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. + +## Immutable Entities + +To make an entity immutable, we simply add `(immutable: true)` to an entity. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. + +Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. + +### Under the hood + +Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. + +### When not to use Immutable Entities + +If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. + +## Bytes as IDs + +Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. + +### Reasons to Not Use Bytes as IDs + +1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. +2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. +3. Indexing and querying performance improvements are not desired. + +### Concatenating With Bytes as IDs + +It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. + +Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. + +```typescript +export function handleTransfer(event: TransferEvent): void { + let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) + entity.from = event.params.from + entity.to = event.params.to + entity.value = event.params.value + + entity.blockNumber = event.block.number + entity.blockTimestamp = event.block.timestamp + entity.transactionHash = event.transaction.hash + + entity.save() +} +``` + +### Sorting With Bytes as IDs + +Sorting using Bytes as IDs is not optimal as seen in this example query and response. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: id) { + id + from + to + value + } +} +``` + +Query response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x00010000", + "from": "0xabcd...", + "to": "0x1234...", + "value": "256" + }, + { + "id": "0x00020000", + "from": "0xefgh...", + "to": "0x5678...", + "value": "512" + }, + { + "id": "0x01000000", + "from": "0xijkl...", + "to": "0x9abc...", + "value": "1" + } + ] + } +} +``` + +The IDs are returned as hex. + +To improve sorting, we should create another field on the entity that is a BigInt. + +```graphql +type Transfer @entity { + id: Bytes! + from: Bytes! # address + to: Bytes! # address + value: BigInt! # unit256 + tokenId: BigInt! # uint256 +} +``` + +This will allow for sorting to be optimized sequentially. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: tokenId) { + id + tokenId + } +} +``` + +Query Response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x…", + "tokenId": "1" + }, + { + "id": "0x…", + "tokenId": "2" + }, + { + "id": "0x…", + "tokenId": "3" + } + ] + } +} +``` + +## Conclusion + +Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. + +Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/sv/subgraphs/best-practices/pruning.mdx b/website/src/pages/sv/subgraphs/best-practices/pruning.mdx new file mode 100644 index 000000000000..1b51dde8894f --- /dev/null +++ b/website/src/pages/sv/subgraphs/best-practices/pruning.mdx @@ -0,0 +1,56 @@ +--- +title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning +sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' +--- + +## TLDR + +[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. + +## How to Prune a Subgraph With `indexerHints` + +Add a section called `indexerHints` in the manifest. + +`indexerHints` has three `prune` options: + +- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. +- `prune: `: Sets a custom limit on the number of historical blocks to retain. +- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. + +We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: + +```yaml +specVersion: 1.0.0 +schema: + file: ./schema.graphql +indexerHints: + prune: auto +dataSources: + - kind: ethereum/contract + name: Contract + network: mainnet +``` + +## Important Considerations + +- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. + +- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). + +## Conclusion + +Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/sv/subgraphs/cookbook/timeseries.mdx b/website/src/pages/sv/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/sv/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/sv/subgraphs/best-practices/timeseries.mdx index f707f57e173c..63786a945971 100644 --- a/website/src/pages/sv/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/sv/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/sv/subgraphs/cookbook/_meta.js b/website/src/pages/sv/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/sv/subgraphs/cookbook/_meta.js +++ b/website/src/pages/sv/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/sv/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/sv/subgraphs/cookbook/avoid-eth-calls.mdx deleted file mode 100644 index ae29cdf03a34..000000000000 --- a/website/src/pages/sv/subgraphs/cookbook/avoid-eth-calls.mdx +++ /dev/null @@ -1,117 +0,0 @@ ---- -title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls -sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' ---- - -## TLDR - -`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. - -## Why Avoiding `eth_calls` Is a Best Practice - -Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. - -### What Does an eth_call Look Like? - -`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: - -```yaml -event Transfer(address indexed from, address indexed to, uint256 value); -``` - -Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, Transfer } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransfer(event: Transfer): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - // Bind the ERC20 contract instance to the given address: - let instance = ERC20.bind(event.address) - - // Retrieve pool information via eth_call - let poolInfo = instance.getPoolInfo(event.params.to) - - transaction.pool = poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is functional, however is not ideal as it slows down our subgraph’s indexing. - -## How to Eliminate `eth_calls` - -Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: - -``` -event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); -``` - -With this update, the subgraph can directly index the required data without external calls: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransferWithPool(event: TransferWithPool): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - transaction.pool = event.params.poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is much more performant as it has eliminated the need for `eth_calls`. - -## How to Optimize `eth_calls` - -If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. - -## Reducing the Runtime Overhead of `eth_calls` - -For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. - -Currently, `eth_calls` can only be declared for event handlers. In the manifest, write - -```yaml -event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) -handler: handleTransferWithPool -calls: - ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) -``` - -The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. - -The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. - -Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. - -## Conclusion - -You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/sv/subgraphs/cookbook/cosmos.mdx b/website/src/pages/sv/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 75e5475585f3..000000000000 --- a/website/src/pages/sv/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Bygga subgrafer på Cosmos ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## Vad är Cosmos subgrafer? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -Det finns fyra typer av hanterare som stöds i Cosmos subgrafer: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Även om all data kan nås med en blockhanterare, gör andra hanterare det möjligt för subgraf utvecklare att behandla data på ett mycket mer detaljerat sätt. - -## Bygga en Cosmos subgraf - -### Subgraf beroenden - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Subgraf Huvudkomponenter - -Det finns tre viktiga delar när det gäller att definiera en subgraf: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### Definition av subgraf manifestet - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### Schema Definition - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript mappningar - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Varje hanterartyp kommer med sin egen datastruktur som skickas som ett argument till en mappningsfunktion. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Meddelan avkodning - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Skapa och bygga en Cosmos subgraf - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Distribuera en Cosmos subgraf - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Fråga efter en Cosmos subgraf - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Stöds Cosmos Blockchains - -### Cosmos Hub - -#### Vad är Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### Nätverk - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### Vad är Osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### Nätverk - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## Exempel på subgrafer - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/sv/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/sv/subgraphs/cookbook/derivedfrom.mdx deleted file mode 100644 index a0942645c999..000000000000 --- a/website/src/pages/sv/subgraphs/cookbook/derivedfrom.mdx +++ /dev/null @@ -1,89 +0,0 @@ ---- -title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom -sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' ---- - -## TLDR - -Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. - -## How to Use the `@derivedFrom` Directive - -You just need to add a `@derivedFrom` directive after your array in your schema. Like this: - -```graphql -comments: [Comment!]! @derivedFrom(field: "post") -``` - -`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. - -### Example Use Case for `@derivedFrom` - -An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. - -Let’s start with our two entities, `Post` and `Comment` - -Without optimization, you could implement it like this with an array: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! -} - -type Comment @entity { - id: Bytes! - content: String! -} -``` - -Arrays like these will effectively store extra Comments data on the Post side of the relationship. - -Here’s what an optimized version looks like using `@derivedFrom`: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! @derivedFrom(field: "post") -} - -type Comment @entity { - id: Bytes! - content: String! - post: Post! -} -``` - -Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. - -This will not only make our subgraph more efficient, but it will also unlock three features: - -1. We can query the `Post` and see all of its comments. - -2. We can do a reverse lookup and query any `Comment` and see which post it comes from. - -3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. - -## Conclusion - -Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. - -For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/sv/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/sv/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx deleted file mode 100644 index 511565bb3dd4..000000000000 --- a/website/src/pages/sv/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ /dev/null @@ -1,191 +0,0 @@ ---- -title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs -sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' ---- - -## TLDR - -Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. - -## Immutable Entities - -To make an entity immutable, we simply add `(immutable: true)` to an entity. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. - -Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. - -### Under the hood - -Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. - -### When not to use Immutable Entities - -If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. - -## Bytes as IDs - -Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. - -### Reasons to Not Use Bytes as IDs - -1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. -2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. -3. Indexing and querying performance improvements are not desired. - -### Concatenating With Bytes as IDs - -It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. - -Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. - -```typescript -export function handleTransfer(event: TransferEvent): void { - let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) - entity.from = event.params.from - entity.to = event.params.to - entity.value = event.params.value - - entity.blockNumber = event.block.number - entity.blockTimestamp = event.block.timestamp - entity.transactionHash = event.transaction.hash - - entity.save() -} -``` - -### Sorting With Bytes as IDs - -Sorting using Bytes as IDs is not optimal as seen in this example query and response. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: id) { - id - from - to - value - } -} -``` - -Query response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x00010000", - "from": "0xabcd...", - "to": "0x1234...", - "value": "256" - }, - { - "id": "0x00020000", - "from": "0xefgh...", - "to": "0x5678...", - "value": "512" - }, - { - "id": "0x01000000", - "from": "0xijkl...", - "to": "0x9abc...", - "value": "1" - } - ] - } -} -``` - -The IDs are returned as hex. - -To improve sorting, we should create another field on the entity that is a BigInt. - -```graphql -type Transfer @entity { - id: Bytes! - from: Bytes! # address - to: Bytes! # address - value: BigInt! # unit256 - tokenId: BigInt! # uint256 -} -``` - -This will allow for sorting to be optimized sequentially. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: tokenId) { - id - tokenId - } -} -``` - -Query Response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x…", - "tokenId": "1" - }, - { - "id": "0x…", - "tokenId": "2" - }, - { - "id": "0x…", - "tokenId": "3" - } - ] - } -} -``` - -## Conclusion - -Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. - -Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/sv/subgraphs/cookbook/pruning.mdx b/website/src/pages/sv/subgraphs/cookbook/pruning.mdx deleted file mode 100644 index e212d5d02bc9..000000000000 --- a/website/src/pages/sv/subgraphs/cookbook/pruning.mdx +++ /dev/null @@ -1,56 +0,0 @@ ---- -title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning -sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' ---- - -## TLDR - -[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. - -## How to Prune a Subgraph With `indexerHints` - -Add a section called `indexerHints` in the manifest. - -`indexerHints` has three `prune` options: - -- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. -- `prune: `: Sets a custom limit on the number of historical blocks to retain. -- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. - -We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: - -```yaml -specVersion: 1.0.0 -schema: - file: ./schema.graphql -indexerHints: - prune: auto -dataSources: - - kind: ethereum/contract - name: Contract - network: mainnet -``` - -## Important Considerations - -- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. - -- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). - -## Conclusion - -Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/sv/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/sv/subgraphs/developing/creating/graph-ts/api.mdx index a8dc795ffba1..dd9fb343dd68 100644 --- a/website/src/pages/sv/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/sv/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: API för AssemblyScript --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/sv/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/sv/subgraphs/developing/creating/install-the-cli.mdx index 1e917f1a7cc8..8905ec3abf61 100644 --- a/website/src/pages/sv/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/sv/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Installera Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Översikt diff --git a/website/src/pages/sv/subgraphs/developing/deploying/_meta.js b/website/src/pages/sv/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/sv/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/sv/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/sv/subgraphs/querying/best-practices.mdx b/website/src/pages/sv/subgraphs/querying/best-practices.mdx index c591ad5c28fd..906948273d5f 100644 --- a/website/src/pages/sv/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/sv/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Att skicka en fråga till ett GraphQL API diff --git a/website/src/pages/sv/substreams/developing/sinks/sinks.mdx b/website/src/pages/sv/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/sv/substreams/developing/sinks/sinks.mdx rename to website/src/pages/sv/substreams/developing/sinks.mdx diff --git a/website/src/pages/sv/substreams/developing/sinks/_meta.js b/website/src/pages/sv/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/sv/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/sv/substreams/quick-start.mdx b/website/src/pages/sv/substreams/quick-start.mdx index bef423ee4d15..8a1d453f56a9 100644 --- a/website/src/pages/sv/substreams/quick-start.mdx +++ b/website/src/pages/sv/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/tr/resources/_meta-titles.json b/website/src/pages/tr/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/tr/resources/_meta-titles.json +++ b/website/src/pages/tr/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/tr/resources/_meta.js b/website/src/pages/tr/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/tr/resources/_meta.js +++ b/website/src/pages/tr/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/tr/resources/release-notes/_meta.js b/website/src/pages/tr/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/tr/resources/release-notes/_meta.js rename to website/src/pages/tr/resources/migration-guides/_meta.js diff --git a/website/src/pages/tr/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/tr/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/tr/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/tr/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/tr/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/tr/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 100% rename from website/src/pages/tr/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/tr/resources/migration-guides/graphql-validations-migration-guide.mdx diff --git a/website/src/pages/tr/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/tr/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/tr/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/tr/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/tr/sps/sps-faq.mdx b/website/src/pages/tr/sps/sps-faq.mdx index 2dc26b8ca1f5..1f627d451a98 100644 --- a/website/src/pages/tr/sps/sps-faq.mdx +++ b/website/src/pages/tr/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/tr/subgraphs/_meta-titles.json b/website/src/pages/tr/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/tr/subgraphs/_meta-titles.json +++ b/website/src/pages/tr/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/tr/subgraphs/_meta.js b/website/src/pages/tr/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/tr/subgraphs/_meta.js +++ b/website/src/pages/tr/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/tr/subgraphs/best-practices/_meta.js b/website/src/pages/tr/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/tr/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/tr/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/tr/subgraphs/best-practices/avoid-eth-calls.mdx similarity index 95% rename from website/src/pages/tr/subgraphs/cookbook/avoid-eth-calls.mdx rename to website/src/pages/tr/subgraphs/best-practices/avoid-eth-calls.mdx index 5fa223a07fe7..5bea3a40a54e 100644 --- a/website/src/pages/tr/subgraphs/cookbook/avoid-eth-calls.mdx +++ b/website/src/pages/tr/subgraphs/best-practices/avoid-eth-calls.mdx @@ -104,14 +104,14 @@ Subgraph'lerinizde `eth_calls`'ı en aza indirerek endeksleme performansını ö ## Subgraph Örnek Uygulamalar 1-6 -1. [Subgraph Budama ile Sorgu Hızını İyileştirin](/subgraphs/cookbook/pruning/) +1. [Subgraph Budama ile Sorgu Hızını İyileştirin](/subgraphs/best-practices/pruning/) -2. [@derivedFrom Kullanarak Endeksleme ve Sorgu Yanıt Hızını Artırın](/subgraphs/cookbook/derivedfrom/) +2. [@derivedFrom Kullanarak Endeksleme ve Sorgu Yanıt Hızını Artırın](/subgraphs/best-practices/derivedfrom/) -3. [Değişmez Varlıklar ve Bytes ID'ler Kullanarak Endeksleme ve Sorgu Performansını Artırın](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Değişmez Varlıklar ve Bytes ID'ler Kullanarak Endeksleme ve Sorgu Performansını Artırın](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Endeksleme Hızını `eth_calls`'den Kaçınarak İyileştirin](/subgraphs/cookbook/avoid-eth-calls/) +4. [Endeksleme Hızını `eth_calls`'den Kaçınarak İyileştirin](/subgraphs/best-practices/avoid-eth-calls/) -5. [Zaman Serileri ve Bütünleştirme ile Basitleştirin ve Optimize Edin](/subgraphs/cookbook/timeseries/) +5. [Zaman Serileri ve Bütünleştirme ile Basitleştirin ve Optimize Edin](/subgraphs/best-practices/timeseries/) -6. [Hızlı Düzeltme Dağıtımı için Aşılama Kullanın](/subgraphs/cookbook/grafting-hotfix/) +6. [Hızlı Düzeltme Dağıtımı için Aşılama Kullanın](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/tr/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/tr/subgraphs/best-practices/derivedfrom.mdx similarity index 92% rename from website/src/pages/tr/subgraphs/cookbook/derivedfrom.mdx rename to website/src/pages/tr/subgraphs/best-practices/derivedfrom.mdx index fe4734f45527..9c2356837602 100644 --- a/website/src/pages/tr/subgraphs/cookbook/derivedfrom.mdx +++ b/website/src/pages/tr/subgraphs/best-practices/derivedfrom.mdx @@ -76,14 +76,14 @@ Büyük dizilerden kaçınma stratejilerinin daha ayrıntılı bir açıklaması ## Subgraph Örnek Uygulamalar 1-6 -1. [Subgraph Budama ile Sorgu Hızını İyileştirin](/subgraphs/cookbook/pruning/) +1. [Subgraph Budama ile Sorgu Hızını İyileştirin](/subgraphs/best-practices/pruning/) -2. [@derivedFrom Kullanarak Endeksleme ve Sorgu Yanıt Hızını Artırın](/subgraphs/cookbook/derivedfrom/) +2. [@derivedFrom Kullanarak Endeksleme ve Sorgu Yanıt Hızını Artırın](/subgraphs/best-practices/derivedfrom/) -3. [Değişmez Varlıklar ve Bytes ID'ler Kullanarak Endeksleme ve Sorgu Performansını Artırın](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Değişmez Varlıklar ve Bytes ID'ler Kullanarak Endeksleme ve Sorgu Performansını Artırın](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Endeksleme Hızını `eth_calls`'den Kaçınarak İyileştirin](/subgraphs/cookbook/avoid-eth-calls/) +4. [Endeksleme Hızını `eth_calls`'den Kaçınarak İyileştirin](/subgraphs/best-practices/avoid-eth-calls/) -5. [Zaman Serileri ve Bütünleştirme ile Basitleştirin ve Optimize Edin](/subgraphs/cookbook/timeseries/) +5. [Zaman Serileri ve Bütünleştirme ile Basitleştirin ve Optimize Edin](/subgraphs/best-practices/timeseries/) -6. [Hızlı Düzeltme Dağıtımı için Aşılama Kullanın](/subgraphs/cookbook/grafting-hotfix/) +6. [Hızlı Düzeltme Dağıtımı için Aşılama Kullanın](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/tr/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/tr/subgraphs/best-practices/grafting-hotfix.mdx similarity index 97% rename from website/src/pages/tr/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/tr/subgraphs/best-practices/grafting-hotfix.mdx index 954ecd05e3ee..6b2be11b98f4 100644 --- a/website/src/pages/tr/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/tr/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ Subgraph geliştirme iş akışınıza aşılamayı dahil ederek, sorunlara hız ## Subgraph Örnek Uygulamalar 1-6 -1. [Subgraph Budama ile Sorgu Hızını İyileştirin](/subgraphs/cookbook/pruning/) +1. [Subgraph Budama ile Sorgu Hızını İyileştirin](/subgraphs/best-practices/pruning/) -2. [@derivedFrom Kullanarak Endeksleme ve Sorgu Yanıt Hızını Artırın](/subgraphs/cookbook/derivedfrom/) +2. [@derivedFrom Kullanarak Endeksleme ve Sorgu Yanıt Hızını Artırın](/subgraphs/best-practices/derivedfrom/) -3. [Değişmez Varlıklar ve Bytes ID'ler Kullanarak Endeksleme ve Sorgu Performansını Artırın](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Değişmez Varlıklar ve Bytes ID'ler Kullanarak Endeksleme ve Sorgu Performansını Artırın](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Endeksleme Hızını `eth_calls`'den Kaçınarak İyileştirin](/subgraphs/cookbook/avoid-eth-calls/) +4. [Endeksleme Hızını `eth_calls`'den Kaçınarak İyileştirin](/subgraphs/best-practices/avoid-eth-calls/) -5. [Zaman Serileri ve Bütünleştirme ile Basitleştirin ve Optimize Edin](/subgraphs/cookbook/timeseries/) +5. [Zaman Serileri ve Bütünleştirme ile Basitleştirin ve Optimize Edin](/subgraphs/best-practices/timeseries/) -6. [Hızlı Düzeltme Dağıtımı için Aşılama Kullanın](/subgraphs/cookbook/grafting-hotfix/) +6. [Hızlı Düzeltme Dağıtımı için Aşılama Kullanın](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/tr/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/tr/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx similarity index 95% rename from website/src/pages/tr/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx rename to website/src/pages/tr/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx index cf1bfdb9d253..36eb9a1d99bf 100644 --- a/website/src/pages/tr/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ b/website/src/pages/tr/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -178,14 +178,14 @@ Değişmez Varlıkları ve ID olarak Bytes kullanmak hakkında daha fazla bilgiy ## Subgraph Örnek Uygulamalar 1-6 -1. [Subgraph Budama ile Sorgu Hızını İyileştirin](/subgraphs/cookbook/pruning/) +1. [Subgraph Budama ile Sorgu Hızını İyileştirin](/subgraphs/best-practices/pruning/) -2. [@derivedFrom Kullanarak Endeksleme ve Sorgu Yanıt Hızını Artırın](/subgraphs/cookbook/derivedfrom/) +2. [@derivedFrom Kullanarak Endeksleme ve Sorgu Yanıt Hızını Artırın](/subgraphs/best-practices/derivedfrom/) -3. [Değişmez Varlıklar ve Bytes ID'ler Kullanarak Endeksleme ve Sorgu Performansını Artırın](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Değişmez Varlıklar ve Bytes ID'ler Kullanarak Endeksleme ve Sorgu Performansını Artırın](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Endeksleme Hızını `eth_calls`'den Kaçınarak İyileştirin](/subgraphs/cookbook/avoid-eth-calls/) +4. [Endeksleme Hızını `eth_calls`'den Kaçınarak İyileştirin](/subgraphs/best-practices/avoid-eth-calls/) -5. [Zaman Serileri ve Bütünleştirme ile Basitleştirin ve Optimize Edin](/subgraphs/cookbook/timeseries/) +5. [Zaman Serileri ve Bütünleştirme ile Basitleştirin ve Optimize Edin](/subgraphs/best-practices/timeseries/) -6. [Hızlı Düzeltme Dağıtımı için Aşılama Kullanın](/subgraphs/cookbook/grafting-hotfix/) +6. [Hızlı Düzeltme Dağıtımı için Aşılama Kullanın](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/tr/subgraphs/cookbook/pruning.mdx b/website/src/pages/tr/subgraphs/best-practices/pruning.mdx similarity index 90% rename from website/src/pages/tr/subgraphs/cookbook/pruning.mdx rename to website/src/pages/tr/subgraphs/best-practices/pruning.mdx index 6f0eeedb2756..690803e92533 100644 --- a/website/src/pages/tr/subgraphs/cookbook/pruning.mdx +++ b/website/src/pages/tr/subgraphs/best-practices/pruning.mdx @@ -43,14 +43,14 @@ dataSources: ## Subgraph Örnek Uygulamalar 1-6 -1. [Subgraph Budama ile Sorgu Hızını İyileştirin](/subgraphs/cookbook/pruning/) +1. [Subgraph Budama ile Sorgu Hızını İyileştirin](/subgraphs/best-practices/pruning/) -2. [@derivedFrom Kullanarak Endeksleme ve Sorgu Yanıt Hızını Artırın](/subgraphs/cookbook/derivedfrom/) +2. [@derivedFrom Kullanarak Endeksleme ve Sorgu Yanıt Hızını Artırın](/subgraphs/best-practices/derivedfrom/) -3. [Değişmez Varlıklar ve Bytes ID'ler Kullanarak Endeksleme ve Sorgu Performansını Artırın](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Değişmez Varlıklar ve Bytes ID'ler Kullanarak Endeksleme ve Sorgu Performansını Artırın](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Endeksleme Hızını `eth_calls`'den Kaçınarak İyileştirin](/subgraphs/cookbook/avoid-eth-calls/) +4. [Endeksleme Hızını `eth_calls`'den Kaçınarak İyileştirin](/subgraphs/best-practices/avoid-eth-calls/) -5. [Zaman Serileri ve Bütünleştirme ile Basitleştirin ve Optimize Edin](/subgraphs/cookbook/timeseries/) +5. [Zaman Serileri ve Bütünleştirme ile Basitleştirin ve Optimize Edin](/subgraphs/best-practices/timeseries/) -6. [Hızlı Düzeltme Dağıtımı için Aşılama Kullanın](/subgraphs/cookbook/grafting-hotfix/) +6. [Hızlı Düzeltme Dağıtımı için Aşılama Kullanın](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/tr/subgraphs/cookbook/timeseries.mdx b/website/src/pages/tr/subgraphs/best-practices/timeseries.mdx similarity index 96% rename from website/src/pages/tr/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/tr/subgraphs/best-practices/timeseries.mdx index 42b779ceec64..78994cb6f089 100644 --- a/website/src/pages/tr/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/tr/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ Bu modeli benimseyerek, geliştiriciler daha verimli ve ölçeklenebilir subgrap ## Subgraph Örnek Uygulamalar 1-6 -1. [Subgraph Budama ile Sorgu Hızını İyileştirin](/subgraphs/cookbook/pruning/) +1. [Subgraph Budama ile Sorgu Hızını İyileştirin](/subgraphs/best-practices/pruning/) -2. [@derivedFrom Kullanarak Endeksleme ve Sorgu Yanıt Hızını Artırın](/subgraphs/cookbook/derivedfrom/) +2. [@derivedFrom Kullanarak Endeksleme ve Sorgu Yanıt Hızını Artırın](/subgraphs/best-practices/derivedfrom/) -3. [Değişmez Varlıklar ve Bytes ID'ler Kullanarak Endeksleme ve Sorgu Performansını Artırın](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Değişmez Varlıklar ve Bytes ID'ler Kullanarak Endeksleme ve Sorgu Performansını Artırın](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Endeksleme Hızını `eth_calls`'den Kaçınarak İyileştirin](/subgraphs/cookbook/avoid-eth-calls/) +4. [Endeksleme Hızını `eth_calls`'den Kaçınarak İyileştirin](/subgraphs/best-practices/avoid-eth-calls/) -5. [Zaman Serileri ve Bütünleştirme ile Basitleştirin ve Optimize Edin](/subgraphs/cookbook/timeseries/) +5. [Zaman Serileri ve Bütünleştirme ile Basitleştirin ve Optimize Edin](/subgraphs/best-practices/timeseries/) -6. [Hızlı Düzeltme Dağıtımı için Aşılama Kullanın](/subgraphs/cookbook/grafting-hotfix/) +6. [Hızlı Düzeltme Dağıtımı için Aşılama Kullanın](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/tr/subgraphs/cookbook/_meta.js b/website/src/pages/tr/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/tr/subgraphs/cookbook/_meta.js +++ b/website/src/pages/tr/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/tr/subgraphs/cookbook/cosmos.mdx b/website/src/pages/tr/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 507bc7acb87d..000000000000 --- a/website/src/pages/tr/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Cosmos'ta Subgraph'ler Oluşturma ---- - -Bu rehber, [Cosmos](https://cosmos.network/) tabanlı blokzincirleri endeksleyen subgraph'ler oluşturma konusunda bir giriş niteliğindedir. - -## Cosmos subgraph'leri nelerdir? - -The Graph, geliştiricilerin blokzinciri olaylarını işlemesine ve sonuçta ortaya çıkan veriyi açık bir GraphQL API'ı (subgraph olarak bilinir) üzerinden kolayca erişilebilir hale getirmesine olanak tanır. [Graph Düğümü](https://github.com/graphprotocol/graph-node), artık Cosmos olaylarını işleyebiliyor. Bu da Cosmos geliştiricilerinin zincir üzerindeki olayları kolayca endekslemek için subgraph'ler oluşturabileceği anlamına geliyor. - -Cosmos subgraph'lerinde desteklenen dört tür işleyici vardır: - -- **Blok işleyicileri** zincire yeni bir blok eklendiğinde çalışır. -- **Olay işleyicileri** belirli bir olay yayıldığında çalışır. -- **İşlem işleyicileri** bir işlem gerçekleştiğinde çalışır. -- **Mesaj işleyicileri** belirli bir mesaj oluştuğunda çalışır. - -[Cosmos'un resmi dokümantasyonuna](https://docs.cosmos.network/) dayalı olarak: - -> [Olaylar](https://docs.cosmos.network/main/learn/advanced/events), uygulamanın yürütülmesi hakkında bilgi içeren nesnelerdir. Genellikle blok gezginleri ve cüzdanlar gibi hizmet sağlayıcılar tarafından çeşitli mesajların yürütülmesini izlemek ve işlemleri endekslemek için kullanılırlar. -> -> [İşlemler](https://docs.cosmos.network/main/learn/advanced/transactions), uygulamada durum değişikliklerini tetiklemek için son kullanıcılar tarafından oluşturulan nesnelerdir. -> -> [Mesajlar](https://docs.cosmos.network/main/learn/advanced/transactions#messages), ait oldukları modül kapsamındaki durum geçişlerini tetikleyen modüle özel nesnelerdir. - -Tüm verilere bir blok işleyici ile erişilebilmesine rağmen, diğer işleyiciler, subgraph geliştiricilerin verileri çok daha ayrıntılı bir şekilde işlemesine olanak tanır. - -## Cosmos subgraph'i inşa etme - -### Subgraph Gereksinimleri - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli), subgraph'leri oluşturmak ve dağıtmak için bir CLI aracıdır. Cosmos subgraph'leri ile çalışabilmek için `>=0.30.0` sürümü gereklidir. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts), subgraph'e özel türlerden oluşan bir kütüphanedir ve Cosmos subgraph'leri ile çalışabilmek için `>=0.27.0` sürümü gereklidir. - -### Subgraph Ana Bileşenleri - -Bir subgraph'i tanımlama noktasında üç anahtar kısım vardır: - -**subgraph.yaml**: hangi olayıların takip edileceğini ve bunların nasıl işleneceğini tanımlayan subgraph manifestosunu içeren bir YAML dosyası. - -**schema.graphql**: Subgraph'iniz için hangi verilerin saklanacağını ve bu verilerin GraphQL aracılığıyla nasıl sorgulanabileceğini tanımlayan bir GraphQL şemasıdır. - -**AssemblyScript Eşlemeleri:** blokzinciri verilerini şemanızda tanımlanan varlıklara dönüştüren [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) kodu. - -### Subgraph Manifest Tanımı - -Subgraph manifestosu (`subgraph.yaml`), subgraph için veri kaynaklarını, ilgili tetikleyicileri ve bu tetikleyicilere yanıt olarak çalıştırılması gereken fonksiyonları (`handlers`) tanımlar. Aşağıda bir Cosmos subgraph manifestosu örneği bulunmaktadır: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraph'leri, yeni bir veri kaynağı `türü` (`kind`) tanıtır (`cosmos`). -- `network` (ağ), Cosmos ekosistemindeki bir zinciri belirtmelidir. Örnekte, Cosmos Hub ana ağı kullanılmıştır. - -### Şema Tanımı - -Şema tanımı, ortaya çıkan subgraph veritabanının yapısını ve varlıklar arasındaki ilişkileri açıklar. Bu, orijinal veri kaynağından bağımsızdır. Subgraph şema tanımı hakkında daha fazla detay [burada](/developing/creating-a-subgraph/#the-graphql-schema) bulunabilir. - -### AssemblyScript Eşlemeleri - -Olayları işlemek için kullanılan işleyiciler [AssemblyScript](https://www.assemblyscript.org/) ile yazılmıştır. - -Cosmos endeksleme, [AssemblyScript API'ına](/subgraphs/developing/creating/graph-ts/api/) Cosmos'a özgü veri türlerini tanıtır. - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Her işleyici türü, bir eşleme işlevine bağımsız değişken olarak iletilen kendi veri yapısıyla birlikte gelir. - -- Blok işleyiciler `Block` türünü alır. -- Olay işleyiciler `EventData` türünü alır. -- İşlem işleyiciler `TransactionData` türünü alır. -- Mesaj işleyiciler `MessageData` türünü alır. - -`MessageData`'nın bir parçası olarak mesaj işleyici, bir mesajı kapsayan işlemle ilgili en önemli bilgileri içeren bir işlem bağlamı alır. İşlem bağlamı, yalnızca ilgili olay bir işlemle ilişkili olduğunda `EventData` türünde de mevcuttur. Ek olarak, tüm işleyiciler bir bloka (`HeaderOnlyBlock`) referans alır. - -Cosmos entegrasyonun tüm türlerinin listesine [buradan](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts) ulaşabilirsiniz. - -### Mesaj çözme - -Cosmos mesajlarının zincir-spesifik olduğunu ve bir subgraph'e [Protocol Buffers](https://protobuf.dev/) yükü olarak serileştirilmiş biçimde iletildiğini unutmamak önemlidir. Sonuç olarak, mesaj verileri işlenmeden önce bir eşleme fonksiyonunda çözülmelidir. - -Subgraph içinde mesaj verilerinin nasıl çözüleceğine dair bir örneğe [buradan](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts) ulaşabilirsiniz. - -## Bir Cosmos subgraph'i inşa etme ve oluşturma - -Subgraph eşlemelerini yazmaya başlamadan önceki ilk adım, `schema.graphql` dosyasında tanımlanan varlıklar temelinde tür bağlamalarını oluşturmaktır. Bu, eşleme fonksiyonlarının bu türlerden yeni nesneler oluşturmasına ve bunları mağazaya kaydetmesine olanak tanır. Bu işlem, `codegen` CLI komutuyla gerçekleştirilir: - -```bash -$ graph codegen -``` - -Eşlemeler hazır olduğunda, subgraph derlenmelidir. Bu adım, manifestoda veya eşlemelerde herhangi bir hata olup olmadığını gösterir. Bir subgraph, Graph Düğümü'ne dağıtılabilmesi için başarıyla derlenmelidir. Bu işlem, `build` CLI komutuyla gerçekleştirilebilir: - -```bash -$ graph build -``` - -## Bir Cosmos subgraph'ini deploy etme - -Subgraph oluşturulduktan sonra, `graph deploy` CLI komutunu kullanarak subgraph'inizi dağıtabilirsiniz: - -**Subgraph Studio** - -Yeni bir subgraph oluşturmak için Subgraph Studio'yu ziyaret edin. - -```bash -graph deploy subgraph-name -``` - -**Yerel Graph Düğümü (varsayılan yapılandırma temel alınarak):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Bir Cosmos subgraph'ini sorgulama - -Cosmos subgraphleri için GraphQL uç noktası, mevcut API arayüzü ile şema tanımına göre belirlenir. Daha fazla bilgi için [GraphQL API dokümantasyonuna](/subgraphs/querying/graphql-api/) göz atabilirsiniz. - -## Desteklenen Cosmos Blok Zincirleri - -### Cosmos Hub - -#### Cosmos Hub Nedir? - -[Cosmos Hub blokzinciri](https://hub.cosmos.network/), [Cosmos](https://cosmos.network/) ekosistemindeki ilk blokzinciridir. Daha fazla bilgi için [resmi dokümantasyonu] (https://docs.cosmos.network/) ziyaret edebilirsiniz. - -#### Ağlar - -Cosmos Hub ana ağı `cosmoshub-4` olarak geçer. Cosmos Hub mevcut test ağı ise `theta-testnet-001` olarak geçer.
`cosmoshub-3` gibi diğer Cosmos Hub ağları durdurulmuş olduğundan, bu ağlara veri sağlanmamaktadır. - -### Osmosis - -> Graph Düğümü ve Subgraph Studio'daki Osmosis desteği beta aşamasındadır: Osmosis subgraphleri oluşturmayla ilgili sorularınız için The Graph ekibiyle iletişime geçebilirsiniz! - -#### Osmosis Nedir? - -[Osmosis](https://osmosis.zone/), Cosmos SDK üzerinde inşa edilmiş merkeziyetsiz, zincirler arası bir otomatik piyasa yapıcı (AMM) protokolüdür. Kullanıcıların özel likidite havuzları oluşturmasına ve IBC-uyumlu token'ları alıp satmasına olanak tanır. Daha fazla bilgi için [resmi dokümantasyonu](https://docs.osmosis.zone/) inceleyebilirsiniz. - -#### Ağlar - -Osmosis ana ağı `osmosis-1` olarak geçer. Osmosis mevcut test ağı ise `osmo-test-4` olarak geçer. - -## Örnek Subgraph'ler - -Aşağıda bazı örnek subgraph'leri bulabilirsiniz: - -[Blok Filtreleme Örneği](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Ödülleri Örneği](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegasyonları Örneği](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Takasları Örneği](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/tr/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/tr/subgraphs/developing/creating/graph-ts/api.mdx index 57dd5cf5d49c..e90c754f6c34 100644 --- a/website/src/pages/tr/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/tr/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API'si --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Subgraph eşlemeleri yazarken kullanılabilecek yerleşik API'leri öğrenin. Hazır olarak sunulan iki tür API mevcuttur: @@ -35,7 +35,7 @@ Subgraph manifestosundaki `apiVersion`, bir subgraph için Graph Düğümü tara | 0.0.8 | Bir varlığı kaydederken şemadaki alanların varlığını doğrulama mekanizması ekler. | | 0.0.7 | Ethereum türlerine `TransactionReceipt` ve `Log` sınıfları eklendi
Ethereum Event nesnesine `receipt` alanı eklendi | | 0.0.6 | Ethereum Transaction nesnesine `nonce` alanı eklendi
Ethereum Block nesnesine `baseFeePerGas` eklendi | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Ethereum SmartContractCall nesnesine `functionSignature` alanı eklendi | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Ethereum Transaction nesnesine `input` alanı eklendi | diff --git a/website/src/pages/tr/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/tr/subgraphs/developing/creating/install-the-cli.mdx index 6c69a1d90504..5b0633a6c1bf 100644 --- a/website/src/pages/tr/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/tr/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Graph CLI'ı Yükleyin --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Genel Bakış diff --git a/website/src/pages/tr/subgraphs/developing/deploying/_meta.js b/website/src/pages/tr/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/tr/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/tr/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/tr/subgraphs/querying/best-practices.mdx b/website/src/pages/tr/subgraphs/querying/best-practices.mdx index 8f3a056e900e..1f4ba885476f 100644 --- a/website/src/pages/tr/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/tr/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Sending a query to a GraphQL API diff --git a/website/src/pages/tr/subgraphs/querying/managing-api-keys.mdx b/website/src/pages/tr/subgraphs/querying/managing-api-keys.mdx index f8ece448a813..af2cde13b073 100644 --- a/website/src/pages/tr/subgraphs/querying/managing-api-keys.mdx +++ b/website/src/pages/tr/subgraphs/querying/managing-api-keys.mdx @@ -1,5 +1,5 @@ --- -title: Managing your API keys +title: Managing API keys --- ## Genel Bakış diff --git a/website/src/pages/tr/substreams/developing/sinks/sinks.mdx b/website/src/pages/tr/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/tr/substreams/developing/sinks/sinks.mdx rename to website/src/pages/tr/substreams/developing/sinks.mdx diff --git a/website/src/pages/tr/substreams/developing/sinks/_meta.js b/website/src/pages/tr/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/tr/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/tr/substreams/quick-start.mdx b/website/src/pages/tr/substreams/quick-start.mdx index 636e71ae43d6..d7f226438e7b 100644 --- a/website/src/pages/tr/substreams/quick-start.mdx +++ b/website/src/pages/tr/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/uk/resources/_meta-titles.json b/website/src/pages/uk/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/uk/resources/_meta-titles.json +++ b/website/src/pages/uk/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/uk/resources/_meta.js b/website/src/pages/uk/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/uk/resources/_meta.js +++ b/website/src/pages/uk/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/uk/resources/release-notes/_meta.js b/website/src/pages/uk/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/uk/resources/release-notes/_meta.js rename to website/src/pages/uk/resources/migration-guides/_meta.js diff --git a/website/src/pages/uk/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/uk/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/uk/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/uk/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/uk/resources/migration-guides/graphql-validations-migration-guide.mdx b/website/src/pages/uk/resources/migration-guides/graphql-validations-migration-guide.mdx new file mode 100644 index 000000000000..29fed533ef8c --- /dev/null +++ b/website/src/pages/uk/resources/migration-guides/graphql-validations-migration-guide.mdx @@ -0,0 +1,538 @@ +--- +title: GraphQL Validations Migration Guide +--- + +Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). + +Previous versions of `graph-node` did not support all validations and provided more graceful responses - so, in cases of ambiguity, `graph-node` was ignoring invalid GraphQL operations components. + +GraphQL Validations support is the pillar for the upcoming new features and the performance at scale of The Graph Network. + +It will also ensure determinism of query responses, a key requirement on The Graph Network. + +**Enabling the GraphQL Validations will break some existing queries** sent to The Graph API. + +To be compliant with those validations, please follow the migration guide. + +> ⚠️ If you do not migrate your queries before the validations are rolled out, they will return errors and possibly break your frontends/clients. + +## Migration guide + +You can use the CLI migration tool to find any issues in your GraphQL operations and fix them. Alternatively you can update the endpoint of your GraphQL client to use the `https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME` endpoint. Testing your queries against this endpoint will help you find the issues in your queries. + +> Not all subgraphs will need to be migrated, if you are using [GraphQL ESlint](https://the-guild.dev/graphql/eslint/docs) or [GraphQL Code Generator](https://the-guild.dev/graphql/codegen), they already ensure that your queries are valid. + +## Migration CLI tool + +**Most of the GraphQL operations errors can be found in your codebase ahead of time.** + +For this reason, we provide a smooth experience for validating your GraphQL operations during development or in CI. + +[`@graphql-validate/cli`](https://github.com/saihaj/graphql-validate) is a simple CLI tool that helps validate GraphQL operations against a given schema. + +### **Getting started** + +You can run the tool as follows: + +```bash +npx @graphql-validate/cli -s https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME -o *.graphql +``` + +**Notes:** + +- Set or replace $GITHUB_USER, $SUBGRAPH_NAME with the appropriate values. Like: [`artblocks/art-blocks`](https://api.thegraph.com/subgraphs/name/artblocks/art-blocks) +- The preview schema URL (https://api-next.thegraph.com/) provided is heavily rate-limited and will be sunset once all users have migrated to the new version. **Do not use it in production.** +- Operations are identified in files with the following extensions [`.graphql`,](https://www.graphql-tools.com/docs/schema-loading#graphql-file-loader)[`.ts`, `.tsx`, `.js`, `jsx`](https://www.graphql-tools.com/docs/schema-loading#code-file-loader) (`-o` option). + +### CLI output + +The `[@graphql-validate/cli](https://github.com/saihaj/graphql-validate)` CLI tool will output any GraphQL operations errors as follows: + +![Error output from CLI](https://i.imgur.com/x1cBdhq.png) + +For each error, you will find a description, file path and position, and a link to a solution example (see the following section). + +## Run your local queries against the preview schema + +We provide an endpoint `https://api-next.thegraph.com/` that runs a `graph-node` version that has validations turned on. + +You can try out queries by sending them to: + +- `https://api-next.thegraph.com/subgraphs/id/` + +or + +- `https://api-next.thegraph.com/subgraphs/name//` + +To work on queries that have been flagged as having validation errors, you can use your favorite GraphQL query tool, like Altair or [GraphiQL](https://cloud.hasura.io/public/graphiql), and try your query out. Those tools will also mark those errors in their UI, even before you run it. + +## How to solve issues + +Below, you will find all the GraphQL validations errors that could occur on your existing GraphQL operations. + +### GraphQL variables, operations, fragments, or arguments must be unique + +We applied rules for ensuring that an operation includes a unique set of GraphQL variables, operations, fragments, and arguments. + +A GraphQL operation is only valid if it does not contain any ambiguity. + +To achieve that, we need to ensure that some components in your GraphQL operation must be unique. + +Here's an example of a few invalid operations that violates these rules: + +**Duplicate Query name (#UniqueOperationNamesRule)** + +```graphql +# The following operation violated the UniqueOperationName +# rule, since we have a single operation with 2 queries +# with the same name +query myData { + id +} + +query myData { + name +} +``` + +_Solution:_ + +```graphql +query myData { + id +} + +query myData2 { + # rename the second query + name +} +``` + +**Duplicate Fragment name (#UniqueFragmentNamesRule)** + +```graphql +# The following operation violated the UniqueFragmentName +# rule. +query myData { + id + ...MyFields +} + +fragment MyFields { + metadata +} + +fragment MyFields { + name +} +``` + +_Solution:_ + +```graphql +query myData { + id + ...MyFieldsName + ...MyFieldsMetadata +} + +fragment MyFieldsMetadata { # assign a unique name to fragment + metadata +} + +fragment MyFieldsName { # assign a unique name to fragment + name +} +``` + +**Duplicate variable name (#UniqueVariableNamesRule)** + +```graphql +# The following operation violates the UniqueVariables +query myData($id: String, $id: Int) { + id + ...MyFields +} +``` + +_Solution:_ + +```graphql +query myData($id: String) { + # keep the relevant variable (here: `$id: String`) + id + ...MyFields +} +``` + +**Duplicate argument name (#UniqueArgument)** + +```graphql +# The following operation violated the UniqueArguments +query myData($id: ID!) { + userById(id: $id, id: "1") { + id + } +} +``` + +_Solution:_ + +```graphql +query myData($id: ID!) { + userById(id: $id) { + id + } +} +``` + +**Duplicate anonymous query (#LoneAnonymousOperationRule)** + +Also, using two anonymous operations will violate the `LoneAnonymousOperation` rule due to conflict in the response structure: + +```graphql +# This will fail if executed together in +# a single operation with the following two queries: +query { + someField +} + +query { + otherField +} +``` + +_Solution:_ + +```graphql +query { + someField + otherField +} +``` + +Or name the two queries: + +```graphql +query FirstQuery { + someField +} + +query SecondQuery { + otherField +} +``` + +### Overlapping Fields + +A GraphQL selection set is considered valid only if it correctly resolves the eventual result set. + +If a specific selection set, or a field, creates ambiguity either by the selected field or by the arguments used, the GraphQL service will fail to validate the operation. + +Here are a few examples of invalid operations that violate this rule: + +**Conflicting fields aliases (#OverlappingFieldsCanBeMergedRule)** + +```graphql +# Aliasing fields might cause conflicts, either with +# other aliases or other fields that exist on the +# GraphQL schema. +query { + dogs { + name: nickname + name + } +} +``` + +_Solution:_ + +```graphql +query { + dogs { + name: nickname + originalName: name # alias the original `name` field + } +} +``` + +**Conflicting fields with arguments (#OverlappingFieldsCanBeMergedRule)** + +```graphql +# Different arguments might lead to different data, +# so we can't assume the fields will be the same. +query { + dogs { + doesKnowCommand(dogCommand: SIT) + doesKnowCommand(dogCommand: HEEL) + } +} +``` + +_Solution:_ + +```graphql +query { + dogs { + knowsHowToSit: doesKnowCommand(dogCommand: SIT) + knowsHowToHeel: doesKnowCommand(dogCommand: HEEL) + } +} +``` + +Also, in more complex use-cases, you might violate this rule by using two fragments that might cause a conflict in the eventually expected set: + +```graphql +query { + # Eventually, we have two "x" definitions, pointing + # to different fields! + ...A + ...B +} + +fragment A on Type { + x: a +} + +fragment B on Type { + x: b +} +``` + +In addition to that, client-side GraphQL directives like `@skip` and `@include` might lead to ambiguity, for example: + +```graphql +fragment mergeSameFieldsWithSameDirectives on Dog { + name @include(if: true) + name @include(if: false) +} +``` + +[You can read more about the algorithm here.](https://spec.graphql.org/June2018/#sec-Field-Selection-Merging) + +### Unused Variables or Fragments + +A GraphQL operation is also considered valid only if all operation-defined components (variables, fragments) are used. + +Here are a few examples for GraphQL operations that violates these rules: + +**Unused variable** (#NoUnusedVariablesRule) + +```graphql +# Invalid, because $someVar is never used. +query something($someVar: String) { + someData +} +``` + +_Solution:_ + +```graphql +query something { + someData +} +``` + +**Unused Fragment** (#NoUnusedFragmentsRule) + +```graphql +# Invalid, because fragment AllFields is never used. +query something { + someData +} + +fragment AllFields { # unused :( + name + age +} +``` + +_Solution:_ + +```graphql +# Invalid, because fragment AllFields is never used. +query something { + someData +} + +# remove the `AllFields` fragment +``` + +### Invalid or missing Selection-Set (#ScalarLeafsRule) + +Also, a GraphQL field selection is only valid if the following is validated: + +- An object field must-have selection set specified. +- An edge field (scalar, enum) must not have a selection set specified. + +Here are a few examples of violations of these rules with the following Schema: + +```graphql +type Image { + url: String! +} + +type User { + id: ID! + avatar: Image! +} + +type Query { + user: User! +} +``` + +**Invalid Selection-Set** + +```graphql +query { + user { + id { # Invalid, because "id" is of type ID and does not have sub-fields + + } + } +} +``` + +_Solution:_ + +```graphql +query { + user { + id + } +} +``` + +**Missing Selection-Set** + +```graphql +query { + user { + id + image # `image` requires a Selection-Set for sub-fields! + } +} +``` + +_Solution:_ + +```graphql +query { + user { + id + image { + src + } + } +} +``` + +### Incorrect Arguments values (#VariablesInAllowedPositionRule) + +GraphQL operations that pass hard-coded values to arguments must be valid, based on the value defined in the schema. + +Here are a few examples of invalid operations that violate these rules: + +```graphql +query purposes { + # If "name" is defined as "String" in the schema, + # this query will fail during validation. + purpose(name: 1) { + id + } +} + +# This might also happen when an incorrect variable is defined: + +query purposes($name: Int!) { + # If "name" is defined as `String` in the schema, + # this query will fail during validation, because the + # variable used is of type `Int` + purpose(name: $name) { + id + } +} +``` + +### Unknown Type, Variable, Fragment, or Directive (#UnknownX) + +The GraphQL API will raise an error if any unknown type, variable, fragment, or directive is used. + +Those unknown references must be fixed: + +- rename if it was a typo +- otherwise, remove + +### Fragment: invalid spread or definition + +**Invalid Fragment spread (#PossibleFragmentSpreadsRule)** + +A Fragment cannot be spread on a non-applicable type. + +Example, we cannot apply a `Cat` fragment to the `Dog` type: + +```graphql +query { + dog { + ...CatSimple + } +} + +fragment CatSimple on Cat { + # ... +} +``` + +**Invalid Fragment definition (#FragmentsOnCompositeTypesRule)** + +All Fragment must be defined upon (using `on ...`) a composite type, in short: object, interface, or union. + +The following examples are invalid, since defining fragments on scalars is invalid. + +```graphql +fragment fragOnScalar on Int { + # we cannot define a fragment upon a scalar (`Int`) + something +} + +fragment inlineFragOnScalar on Dog { + ... on Boolean { + # `Boolean` is not a subtype of `Dog` + somethingElse + } +} +``` + +### Directives usage + +**Directive cannot be used at this location (#KnownDirectivesRule)** + +Only GraphQL directives (`@...`) supported by The Graph API can be used. + +Here is an example with The GraphQL supported directives: + +```graphql +query { + dog { + name @include(true) + age @skip(true) + } +} +``` + +_Note: `@stream`, `@live`, `@defer` are not supported._ + +**Directive can only be used once at this location (#UniqueDirectivesPerLocationRule)** + +The directives supported by The Graph can only be used once per location. + +The following is invalid (and redundant): + +```graphql +query { + dog { + name @include(true) @include(true) + } +} +``` diff --git a/website/src/pages/uk/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/uk/resources/release-notes/graphql-validations-migration-guide.mdx deleted file mode 100644 index 4d909e8970a8..000000000000 --- a/website/src/pages/uk/resources/release-notes/graphql-validations-migration-guide.mdx +++ /dev/null @@ -1,538 +0,0 @@ ---- -title: GraphQL Validations migration guide ---- - -Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). - -Previous versions of `graph-node` did not support all validations and provided more graceful responses - so, in cases of ambiguity, `graph-node` was ignoring invalid GraphQL operations components. - -GraphQL Validations support is the pillar for the upcoming new features and the performance at scale of The Graph Network. - -It will also ensure determinism of query responses, a key requirement on The Graph Network. - -**Enabling the GraphQL Validations will break some existing queries** sent to The Graph API. - -To be compliant with those validations, please follow the migration guide. - -> ⚠️ If you do not migrate your queries before the validations are rolled out, they will return errors and possibly break your frontends/clients. - -## Migration guide - -You can use the CLI migration tool to find any issues in your GraphQL operations and fix them. Alternatively you can update the endpoint of your GraphQL client to use the `https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME` endpoint. Testing your queries against this endpoint will help you find the issues in your queries. - -> Not all subgraphs will need to be migrated, if you are using [GraphQL ESlint](https://the-guild.dev/graphql/eslint/docs) or [GraphQL Code Generator](https://the-guild.dev/graphql/codegen), they already ensure that your queries are valid. - -## Migration CLI tool - -**Most of the GraphQL operations errors can be found in your codebase ahead of time.** - -For this reason, we provide a smooth experience for validating your GraphQL operations during development or in CI. - -[`@graphql-validate/cli`](https://github.com/saihaj/graphql-validate) is a simple CLI tool that helps validate GraphQL operations against a given schema. - -### **Getting started** - -You can run the tool as follows: - -```bash -npx @graphql-validate/cli -s https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME -o *.graphql -``` - -**Notes:** - -- Set or replace $GITHUB_USER, $SUBGRAPH_NAME with the appropriate values. Like: [`artblocks/art-blocks`](https://api.thegraph.com/subgraphs/name/artblocks/art-blocks) -- The preview schema URL (https://api-next.thegraph.com/) provided is heavily rate-limited and will be sunset once all users have migrated to the new version. **Do not use it in production.** -- Operations are identified in files with the following extensions [`.graphql`,](https://www.graphql-tools.com/docs/schema-loading#graphql-file-loader)[`.ts`, `.tsx`, `.js`, `jsx`](https://www.graphql-tools.com/docs/schema-loading#code-file-loader) (`-o` option). - -### CLI output - -The `[@graphql-validate/cli](https://github.com/saihaj/graphql-validate)` CLI tool will output any GraphQL operations errors as follows: - -![Error output from CLI](https://i.imgur.com/x1cBdhq.png) - -For each error, you will find a description, file path and position, and a link to a solution example (see the following section). - -## Run your local queries against the preview schema - -We provide an endpoint `https://api-next.thegraph.com/` that runs a `graph-node` version that has validations turned on. - -You can try out queries by sending them to: - -- `https://api-next.thegraph.com/subgraphs/id/` - -or - -- `https://api-next.thegraph.com/subgraphs/name//` - -To work on queries that have been flagged as having validation errors, you can use your favorite GraphQL query tool, like Altair or [GraphiQL](https://cloud.hasura.io/public/graphiql), and try your query out. Those tools will also mark those errors in their UI, even before you run it. - -## How to solve issues - -Below, you will find all the GraphQL validations errors that could occur on your existing GraphQL operations. - -### GraphQL variables, operations, fragments, or arguments must be unique - -We applied rules for ensuring that an operation includes a unique set of GraphQL variables, operations, fragments, and arguments. - -A GraphQL operation is only valid if it does not contain any ambiguity. - -To achieve that, we need to ensure that some components in your GraphQL operation must be unique. - -Here's an example of a few invalid operations that violates these rules: - -**Duplicate Query name (#UniqueOperationNamesRule)** - -```graphql -# The following operation violated the UniqueOperationName -# rule, since we have a single operation with 2 queries -# with the same name -query myData { - id -} - -query myData { - name -} -``` - -_Solution:_ - -```graphql -query myData { - id -} - -query myData2 { - # rename the second query - name -} -``` - -**Duplicate Fragment name (#UniqueFragmentNamesRule)** - -```graphql -# The following operation violated the UniqueFragmentName -# rule. -query myData { - id - ...MyFields -} - -fragment MyFields { - metadata -} - -fragment MyFields { - name -} -``` - -_Solution:_ - -```graphql -query myData { - id - ...MyFieldsName - ...MyFieldsMetadata -} - -fragment MyFieldsMetadata { # assign a unique name to fragment - metadata -} - -fragment MyFieldsName { # assign a unique name to fragment - name -} -``` - -**Duplicate variable name (#UniqueVariableNamesRule)** - -```graphql -# The following operation violates the UniqueVariables -query myData($id: String, $id: Int) { - id - ...MyFields -} -``` - -_Solution:_ - -```graphql -query myData($id: String) { - # keep the relevant variable (here: `$id: String`) - id - ...MyFields -} -``` - -**Duplicate argument name (#UniqueArgument)** - -```graphql -# The following operation violated the UniqueArguments -query myData($id: ID!) { - userById(id: $id, id: "1") { - id - } -} -``` - -_Solution:_ - -```graphql -query myData($id: ID!) { - userById(id: $id) { - id - } -} -``` - -**Duplicate anonymous query (#LoneAnonymousOperationRule)** - -Also, using two anonymous operations will violate the `LoneAnonymousOperation` rule due to conflict in the response structure: - -```graphql -# This will fail if executed together in -# a single operation with the following two queries: -query { - someField -} - -query { - otherField -} -``` - -_Solution:_ - -```graphql -query { - someField - otherField -} -``` - -Or name the two queries: - -```graphql -query FirstQuery { - someField -} - -query SecondQuery { - otherField -} -``` - -### Overlapping Fields - -A GraphQL selection set is considered valid only if it correctly resolves the eventual result set. - -If a specific selection set, or a field, creates ambiguity either by the selected field or by the arguments used, the GraphQL service will fail to validate the operation. - -Here are a few examples of invalid operations that violate this rule: - -**Conflicting fields aliases (#OverlappingFieldsCanBeMergedRule)** - -```graphql -# Aliasing fields might cause conflicts, either with -# other aliases or other fields that exist on the -# GraphQL schema. -query { - dogs { - name: nickname - name - } -} -``` - -_Solution:_ - -```graphql -query { - dogs { - name: nickname - originalName: name # alias the original `name` field - } -} -``` - -**Conflicting fields with arguments (#OverlappingFieldsCanBeMergedRule)** - -```graphql -# Different arguments might lead to different data, -# so we can't assume the fields will be the same. -query { - dogs { - doesKnowCommand(dogCommand: SIT) - doesKnowCommand(dogCommand: HEEL) - } -} -``` - -_Solution:_ - -```graphql -query { - dogs { - knowsHowToSit: doesKnowCommand(dogCommand: SIT) - knowsHowToHeel: doesKnowCommand(dogCommand: HEEL) - } -} -``` - -Also, in more complex use-cases, you might violate this rule by using two fragments that might cause a conflict in the eventually expected set: - -```graphql -query { - # Eventually, we have two "x" definitions, pointing - # to different fields! - ...A - ...B -} - -fragment A on Type { - x: a -} - -fragment B on Type { - x: b -} -``` - -In addition to that, client-side GraphQL directives like `@skip` and `@include` might lead to ambiguity, for example: - -```graphql -fragment mergeSameFieldsWithSameDirectives on Dog { - name @include(if: true) - name @include(if: false) -} -``` - -[You can read more about the algorithm here.](https://spec.graphql.org/June2018/#sec-Field-Selection-Merging) - -### Unused Variables or Fragments - -A GraphQL operation is also considered valid only if all operation-defined components (variables, fragments) are used. - -Here are a few examples for GraphQL operations that violates these rules: - -**Unused variable** (#NoUnusedVariablesRule) - -```graphql -# Invalid, because $someVar is never used. -query something($someVar: String) { - someData -} -``` - -_Solution:_ - -```graphql -query something { - someData -} -``` - -**Unused Fragment** (#NoUnusedFragmentsRule) - -```graphql -# Invalid, because fragment AllFields is never used. -query something { - someData -} - -fragment AllFields { # unused :( - name - age -} -``` - -_Solution:_ - -```graphql -# Invalid, because fragment AllFields is never used. -query something { - someData -} - -# remove the `AllFields` fragment -``` - -### Invalid or missing Selection-Set (#ScalarLeafsRule) - -Also, a GraphQL field selection is only valid if the following is validated: - -- An object field must-have selection set specified. -- An edge field (scalar, enum) must not have a selection set specified. - -Here are a few examples of violations of these rules with the following Schema: - -```graphql -type Image { - url: String! -} - -type User { - id: ID! - avatar: Image! -} - -type Query { - user: User! -} -``` - -**Invalid Selection-Set** - -```graphql -query { - user { - id { # Invalid, because "id" is of type ID and does not have sub-fields - - } - } -} -``` - -_Solution:_ - -```graphql -query { - user { - id - } -} -``` - -**Missing Selection-Set** - -```graphql -query { - user { - id - image # `image` requires a Selection-Set for sub-fields! - } -} -``` - -_Solution:_ - -```graphql -query { - user { - id - image { - src - } - } -} -``` - -### Incorrect Arguments values (#VariablesInAllowedPositionRule) - -GraphQL operations that pass hard-coded values to arguments must be valid, based on the value defined in the schema. - -Here are a few examples of invalid operations that violate these rules: - -```graphql -query purposes { - # If "name" is defined as "String" in the schema, - # this query will fail during validation. - purpose(name: 1) { - id - } -} - -# This might also happen when an incorrect variable is defined: - -query purposes($name: Int!) { - # If "name" is defined as `String` in the schema, - # this query will fail during validation, because the - # variable used is of type `Int` - purpose(name: $name) { - id - } -} -``` - -### Unknown Type, Variable, Fragment, or Directive (#UnknownX) - -The GraphQL API will raise an error if any unknown type, variable, fragment, or directive is used. - -Those unknown references must be fixed: - -- rename if it was a typo -- otherwise, remove - -### Fragment: invalid spread or definition - -**Invalid Fragment spread (#PossibleFragmentSpreadsRule)** - -A Fragment cannot be spread on a non-applicable type. - -Example, we cannot apply a `Cat` fragment to the `Dog` type: - -```graphql -query { - dog { - ...CatSimple - } -} - -fragment CatSimple on Cat { - # ... -} -``` - -**Invalid Fragment definition (#FragmentsOnCompositeTypesRule)** - -All Fragment must be defined upon (using `on ...`) a composite type, in short: object, interface, or union. - -The following examples are invalid, since defining fragments on scalars is invalid. - -```graphql -fragment fragOnScalar on Int { - # we cannot define a fragment upon a scalar (`Int`) - something -} - -fragment inlineFragOnScalar on Dog { - ... on Boolean { - # `Boolean` is not a subtype of `Dog` - somethingElse - } -} -``` - -### Directives usage - -**Directive cannot be used at this location (#KnownDirectivesRule)** - -Only GraphQL directives (`@...`) supported by The Graph API can be used. - -Here is an example with The GraphQL supported directives: - -```graphql -query { - dog { - name @include(true) - age @skip(true) - } -} -``` - -_Note: `@stream`, `@live`, `@defer` are not supported._ - -**Directive can only be used once at this location (#UniqueDirectivesPerLocationRule)** - -The directives supported by The Graph can only be used once per location. - -The following is invalid (and redundant): - -```graphql -query { - dog { - name @include(true) @include(true) - } -} -``` diff --git a/website/src/pages/uk/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/uk/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/uk/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/uk/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/uk/sps/sps-faq.mdx b/website/src/pages/uk/sps/sps-faq.mdx index 537f29b09ea6..abc1f3906686 100644 --- a/website/src/pages/uk/sps/sps-faq.mdx +++ b/website/src/pages/uk/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/uk/subgraphs/_meta-titles.json b/website/src/pages/uk/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/uk/subgraphs/_meta-titles.json +++ b/website/src/pages/uk/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/uk/subgraphs/_meta.js b/website/src/pages/uk/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/uk/subgraphs/_meta.js +++ b/website/src/pages/uk/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/uk/subgraphs/best-practices/_meta.js b/website/src/pages/uk/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/uk/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/uk/subgraphs/best-practices/avoid-eth-calls.mdx b/website/src/pages/uk/subgraphs/best-practices/avoid-eth-calls.mdx new file mode 100644 index 000000000000..e40a7b3712e4 --- /dev/null +++ b/website/src/pages/uk/subgraphs/best-practices/avoid-eth-calls.mdx @@ -0,0 +1,117 @@ +--- +title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls +sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' +--- + +## TLDR + +`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. + +## Why Avoiding `eth_calls` Is a Best Practice + +Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. + +### What Does an eth_call Look Like? + +`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: + +```yaml +event Transfer(address indexed from, address indexed to, uint256 value); +``` + +Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, Transfer } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransfer(event: Transfer): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + // Bind the ERC20 contract instance to the given address: + let instance = ERC20.bind(event.address) + + // Retrieve pool information via eth_call + let poolInfo = instance.getPoolInfo(event.params.to) + + transaction.pool = poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is functional, however is not ideal as it slows down our subgraph’s indexing. + +## How to Eliminate `eth_calls` + +Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: + +``` +event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); +``` + +With this update, the subgraph can directly index the required data without external calls: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransferWithPool(event: TransferWithPool): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + transaction.pool = event.params.poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is much more performant as it has eliminated the need for `eth_calls`. + +## How to Optimize `eth_calls` + +If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. + +## Reducing the Runtime Overhead of `eth_calls` + +For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. + +Currently, `eth_calls` can only be declared for event handlers. In the manifest, write + +```yaml +event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) +handler: handleTransferWithPool +calls: + ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) +``` + +The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. + +The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. + +Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. + +## Conclusion + +You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/uk/subgraphs/best-practices/derivedfrom.mdx b/website/src/pages/uk/subgraphs/best-practices/derivedfrom.mdx new file mode 100644 index 000000000000..db3a49928c89 --- /dev/null +++ b/website/src/pages/uk/subgraphs/best-practices/derivedfrom.mdx @@ -0,0 +1,89 @@ +--- +title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom +sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' +--- + +## TLDR + +Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. + +## How to Use the `@derivedFrom` Directive + +You just need to add a `@derivedFrom` directive after your array in your schema. Like this: + +```graphql +comments: [Comment!]! @derivedFrom(field: "post") +``` + +`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. + +### Example Use Case for `@derivedFrom` + +An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. + +Let’s start with our two entities, `Post` and `Comment` + +Without optimization, you could implement it like this with an array: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! +} + +type Comment @entity { + id: Bytes! + content: String! +} +``` + +Arrays like these will effectively store extra Comments data on the Post side of the relationship. + +Here’s what an optimized version looks like using `@derivedFrom`: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! @derivedFrom(field: "post") +} + +type Comment @entity { + id: Bytes! + content: String! + post: Post! +} +``` + +Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. + +This will not only make our subgraph more efficient, but it will also unlock three features: + +1. We can query the `Post` and see all of its comments. + +2. We can do a reverse lookup and query any `Comment` and see which post it comes from. + +3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. + +## Conclusion + +Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. + +For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/uk/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/uk/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/uk/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/uk/subgraphs/best-practices/grafting-hotfix.mdx index e4f11172d76c..d042b1960232 100644 --- a/website/src/pages/uk/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/uk/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/uk/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx b/website/src/pages/uk/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx new file mode 100644 index 000000000000..6ff60ec9ab34 --- /dev/null +++ b/website/src/pages/uk/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -0,0 +1,191 @@ +--- +title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs +sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' +--- + +## TLDR + +Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. + +## Immutable Entities + +To make an entity immutable, we simply add `(immutable: true)` to an entity. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. + +Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. + +### Under the hood + +Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. + +### When not to use Immutable Entities + +If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. + +## Bytes as IDs + +Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. + +### Reasons to Not Use Bytes as IDs + +1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. +2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. +3. Indexing and querying performance improvements are not desired. + +### Concatenating With Bytes as IDs + +It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. + +Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. + +```typescript +export function handleTransfer(event: TransferEvent): void { + let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) + entity.from = event.params.from + entity.to = event.params.to + entity.value = event.params.value + + entity.blockNumber = event.block.number + entity.blockTimestamp = event.block.timestamp + entity.transactionHash = event.transaction.hash + + entity.save() +} +``` + +### Sorting With Bytes as IDs + +Sorting using Bytes as IDs is not optimal as seen in this example query and response. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: id) { + id + from + to + value + } +} +``` + +Query response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x00010000", + "from": "0xabcd...", + "to": "0x1234...", + "value": "256" + }, + { + "id": "0x00020000", + "from": "0xefgh...", + "to": "0x5678...", + "value": "512" + }, + { + "id": "0x01000000", + "from": "0xijkl...", + "to": "0x9abc...", + "value": "1" + } + ] + } +} +``` + +The IDs are returned as hex. + +To improve sorting, we should create another field on the entity that is a BigInt. + +```graphql +type Transfer @entity { + id: Bytes! + from: Bytes! # address + to: Bytes! # address + value: BigInt! # unit256 + tokenId: BigInt! # uint256 +} +``` + +This will allow for sorting to be optimized sequentially. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: tokenId) { + id + tokenId + } +} +``` + +Query Response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x…", + "tokenId": "1" + }, + { + "id": "0x…", + "tokenId": "2" + }, + { + "id": "0x…", + "tokenId": "3" + } + ] + } +} +``` + +## Conclusion + +Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. + +Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/uk/subgraphs/best-practices/pruning.mdx b/website/src/pages/uk/subgraphs/best-practices/pruning.mdx new file mode 100644 index 000000000000..1b51dde8894f --- /dev/null +++ b/website/src/pages/uk/subgraphs/best-practices/pruning.mdx @@ -0,0 +1,56 @@ +--- +title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning +sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' +--- + +## TLDR + +[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. + +## How to Prune a Subgraph With `indexerHints` + +Add a section called `indexerHints` in the manifest. + +`indexerHints` has three `prune` options: + +- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. +- `prune: `: Sets a custom limit on the number of historical blocks to retain. +- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. + +We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: + +```yaml +specVersion: 1.0.0 +schema: + file: ./schema.graphql +indexerHints: + prune: auto +dataSources: + - kind: ethereum/contract + name: Contract + network: mainnet +``` + +## Important Considerations + +- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. + +- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). + +## Conclusion + +Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/uk/subgraphs/best-practices/timeseries.mdx b/website/src/pages/uk/subgraphs/best-practices/timeseries.mdx new file mode 100644 index 000000000000..cacdc44711fe --- /dev/null +++ b/website/src/pages/uk/subgraphs/best-practices/timeseries.mdx @@ -0,0 +1,195 @@ +--- +title: Subgraph Best Practice 5 - Simplify and Optimize with Timeseries and Aggregations +sidebarTitle: 'Subgraph Best Practice 5: Timeseries and Aggregations' +--- + +## TLDR + +Leveraging the new time-series and aggregations feature in subgraphs can significantly enhance both indexing speed and query performance. + +## Overview + +Timeseries and aggregations reduce data processing overhead and accelerate queries by offloading aggregation computations to the database and simplifying mapping code. This approach is particularly effective when handling large volumes of time-based data. + +## Benefits of Timeseries and Aggregations + +1. Improved Indexing Time + +- Less Data to Load: Mappings handle less data since raw data points are stored as immutable timeseries entities. +- Database-Managed Aggregations: Aggregations are automatically computed by the database, reducing the workload on the mappings. + +2. Simplified Mapping Code + +- No Manual Calculations: Developers no longer need to write complex aggregation logic in mappings. +- Reduced Complexity: Simplifies code maintenance and minimizes the potential for errors. + +3. Dramatically Faster Queries + +- Immutable Data: All timeseries data is immutable, enabling efficient storage and retrieval. +- Efficient Data Separation: Aggregates are stored separately from raw timeseries data, allowing queries to process significantly less data—often several orders of magnitude less. + +### Important Considerations + +- Immutable Data: Timeseries data cannot be altered once written, ensuring data integrity and simplifying indexing. +- Automatic ID and Timestamp Management: id and timestamp fields are automatically managed by graph-node, reducing potential errors. +- Efficient Data Storage: By separating raw data from aggregates, storage is optimized, and queries run faster. + +## How to Implement Timeseries and Aggregations + +### Defining Timeseries Entities + +A timeseries entity represents raw data points collected over time. It is defined with the `@entity(timeseries: true)` annotation. Key requirements: + +- Immutable: Timeseries entities are always immutable. +- Mandatory Fields: + - `id`: Must be of type `Int8!` and is auto-incremented. + - `timestamp`: Must be of type `Timestamp!` and is automatically set to the block timestamp. + +Example: + +```graphql +type Data @entity(timeseries: true) { + id: Int8! + timestamp: Timestamp! + price: BigDecimal! +} +``` + +### Defining Aggregation Entities + +An aggregation entity computes aggregated values from a timeseries source. It is defined with the `@aggregation` annotation. Key components: + +- Annotation Arguments: + - `intervals`: Specifies time intervals (e.g., `["hour", "day"]`). + +Example: + +```graphql +type Stats @aggregation(intervals: ["hour", "day"], source: "Data") { + id: Int8! + timestamp: Timestamp! + sum: BigDecimal! @aggregate(fn: "sum", arg: "price") +} +``` + +In this example, Stats aggregates the price field from Data over hourly and daily intervals, computing the sum. + +### Querying Aggregated Data + +Aggregations are exposed via query fields that allow filtering and retrieval based on dimensions and time intervals. + +Example: + +```graphql +{ + tokenStats( + interval: "hour" + where: { token: "0x1234567890abcdef", timestamp_gte: "1704164640000000", timestamp_lt: "1704251040000000" } + ) { + id + timestamp + token { + id + } + totalVolume + priceUSD + count + } +} +``` + +### Using Dimensions in Aggregations + +Dimensions are non-aggregated fields used to group data points. They enable aggregations based on specific criteria, such as a token in a financial application. + +Example: + +### Timeseries Entity + +```graphql +type TokenData @entity(timeseries: true) { + id: Int8! + timestamp: Timestamp! + token: Token! + amount: BigDecimal! + priceUSD: BigDecimal! +} +``` + +### Aggregation Entity with Dimension + +```graphql +type TokenStats @aggregation(intervals: ["hour", "day"], source: "TokenData") { + id: Int8! + timestamp: Timestamp! + token: Token! + totalVolume: BigDecimal! @aggregate(fn: "sum", arg: "amount") + priceUSD: BigDecimal! @aggregate(fn: "last", arg: "priceUSD") + count: Int8! @aggregate(fn: "count", cumulative: true) +} +``` + +- Dimension Field: token groups the data, so aggregates are computed per token. +- Aggregates: + - totalVolume: Sum of amount. + - priceUSD: Last recorded priceUSD. + - count: Cumulative count of records. + +### Aggregation Functions and Expressions + +Supported aggregation functions: + +- sum +- count +- min +- max +- first +- last + +### The arg in @aggregate can be + +- A field name from the timeseries entity. +- An expression using fields and constants. + +### Examples of Aggregation Expressions + +- Sum Token Value: @aggregate(fn: "sum", arg: "priceUSD \_ amount") +- Maximum Positive Amount: @aggregate(fn: "max", arg: "greatest(amount0, amount1, 0)") +- Conditional Sum: @aggregate(fn: "sum", arg: "case when amount0 > amount1 then amount0 else 0 end") + +Supported operators and functions include basic arithmetic (+, -, \_, /), comparison operators, logical operators (and, or, not), and SQL functions like greatest, least, coalesce, etc. + +### Query Parameters + +- interval: Specifies the time interval (e.g., "hour"). +- where: Filters based on dimensions and timestamp ranges. +- timestamp_gte / timestamp_lt: Filters for start and end times (microseconds since epoch). + +### Notes + +- Sorting: Results are automatically sorted by timestamp and id in descending order. +- Current Data: An optional current argument can include the current, partially filled interval. + +### Conclusion + +Implementing timeseries and aggregations in subgraphs is a best practice for projects dealing with time-based data. This approach: + +- Enhances Performance: Speeds up indexing and querying by reducing data processing overhead. +- Simplifies Development: Eliminates the need for manual aggregation logic in mappings. +- Scales Efficiently: Handles large volumes of data without compromising on speed or responsiveness. + +By adopting this pattern, developers can build more efficient and scalable subgraphs, providing faster and more reliable data access to end-users. To learn more about implementing timeseries and aggregations, refer to the [Timeseries and Aggregations Readme](https://github.com/graphprotocol/graph-node/blob/master/docs/aggregations.md) and consider experimenting with this feature in your subgraphs. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/uk/subgraphs/cookbook/_meta.js b/website/src/pages/uk/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/uk/subgraphs/cookbook/_meta.js +++ b/website/src/pages/uk/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/uk/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/uk/subgraphs/cookbook/avoid-eth-calls.mdx deleted file mode 100644 index ae29cdf03a34..000000000000 --- a/website/src/pages/uk/subgraphs/cookbook/avoid-eth-calls.mdx +++ /dev/null @@ -1,117 +0,0 @@ ---- -title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls -sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' ---- - -## TLDR - -`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. - -## Why Avoiding `eth_calls` Is a Best Practice - -Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. - -### What Does an eth_call Look Like? - -`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: - -```yaml -event Transfer(address indexed from, address indexed to, uint256 value); -``` - -Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, Transfer } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransfer(event: Transfer): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - // Bind the ERC20 contract instance to the given address: - let instance = ERC20.bind(event.address) - - // Retrieve pool information via eth_call - let poolInfo = instance.getPoolInfo(event.params.to) - - transaction.pool = poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is functional, however is not ideal as it slows down our subgraph’s indexing. - -## How to Eliminate `eth_calls` - -Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: - -``` -event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); -``` - -With this update, the subgraph can directly index the required data without external calls: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransferWithPool(event: TransferWithPool): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - transaction.pool = event.params.poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is much more performant as it has eliminated the need for `eth_calls`. - -## How to Optimize `eth_calls` - -If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. - -## Reducing the Runtime Overhead of `eth_calls` - -For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. - -Currently, `eth_calls` can only be declared for event handlers. In the manifest, write - -```yaml -event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) -handler: handleTransferWithPool -calls: - ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) -``` - -The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. - -The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. - -Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. - -## Conclusion - -You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/uk/subgraphs/cookbook/cosmos.mdx b/website/src/pages/uk/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 3e335b9d60c2..000000000000 --- a/website/src/pages/uk/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Розробка підграфів на Cosmos ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## Що таке Cosmos підграфи? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -У підграфах на Cosmos підтримується чотири типи обробників: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Хоча до всіх даних можна отримати доступ за допомогою блок-обробника, інші обробники дозволяють розробникам підграфів обробляти дані у значно детальніший спосіб. - -## Розробка підграфів на Cosmos - -### Subgraph Dependencies - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Основні компоненти підграфа - -Визначення підграфа складається з трьох ключових компонентів: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### Визначення маніфесту підграфів - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### Визначення схеми - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript Mappings - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Кожен тип обробника має власну структуру даних, яка передається як аргумент функції маппінгу. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Розшифровка повідомлень - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Створення та побудова підграфа на Cosmos - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Розгортання підграфа на Cosmos - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Запит до Cosmos підграфа - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Блокчейни, що підтримуються Cosmos - -### Cosmos Hub - -#### Що таке Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### Мережі - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### Що таке Osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### Мережі - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## Приклади підграфів - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/uk/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/uk/subgraphs/cookbook/derivedfrom.mdx deleted file mode 100644 index a0942645c999..000000000000 --- a/website/src/pages/uk/subgraphs/cookbook/derivedfrom.mdx +++ /dev/null @@ -1,89 +0,0 @@ ---- -title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom -sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' ---- - -## TLDR - -Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. - -## How to Use the `@derivedFrom` Directive - -You just need to add a `@derivedFrom` directive after your array in your schema. Like this: - -```graphql -comments: [Comment!]! @derivedFrom(field: "post") -``` - -`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. - -### Example Use Case for `@derivedFrom` - -An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. - -Let’s start with our two entities, `Post` and `Comment` - -Without optimization, you could implement it like this with an array: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! -} - -type Comment @entity { - id: Bytes! - content: String! -} -``` - -Arrays like these will effectively store extra Comments data on the Post side of the relationship. - -Here’s what an optimized version looks like using `@derivedFrom`: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! @derivedFrom(field: "post") -} - -type Comment @entity { - id: Bytes! - content: String! - post: Post! -} -``` - -Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. - -This will not only make our subgraph more efficient, but it will also unlock three features: - -1. We can query the `Post` and see all of its comments. - -2. We can do a reverse lookup and query any `Comment` and see which post it comes from. - -3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. - -## Conclusion - -Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. - -For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/uk/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/uk/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx deleted file mode 100644 index 511565bb3dd4..000000000000 --- a/website/src/pages/uk/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ /dev/null @@ -1,191 +0,0 @@ ---- -title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs -sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' ---- - -## TLDR - -Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. - -## Immutable Entities - -To make an entity immutable, we simply add `(immutable: true)` to an entity. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. - -Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. - -### Under the hood - -Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. - -### When not to use Immutable Entities - -If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. - -## Bytes as IDs - -Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. - -### Reasons to Not Use Bytes as IDs - -1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. -2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. -3. Indexing and querying performance improvements are not desired. - -### Concatenating With Bytes as IDs - -It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. - -Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. - -```typescript -export function handleTransfer(event: TransferEvent): void { - let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) - entity.from = event.params.from - entity.to = event.params.to - entity.value = event.params.value - - entity.blockNumber = event.block.number - entity.blockTimestamp = event.block.timestamp - entity.transactionHash = event.transaction.hash - - entity.save() -} -``` - -### Sorting With Bytes as IDs - -Sorting using Bytes as IDs is not optimal as seen in this example query and response. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: id) { - id - from - to - value - } -} -``` - -Query response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x00010000", - "from": "0xabcd...", - "to": "0x1234...", - "value": "256" - }, - { - "id": "0x00020000", - "from": "0xefgh...", - "to": "0x5678...", - "value": "512" - }, - { - "id": "0x01000000", - "from": "0xijkl...", - "to": "0x9abc...", - "value": "1" - } - ] - } -} -``` - -The IDs are returned as hex. - -To improve sorting, we should create another field on the entity that is a BigInt. - -```graphql -type Transfer @entity { - id: Bytes! - from: Bytes! # address - to: Bytes! # address - value: BigInt! # unit256 - tokenId: BigInt! # uint256 -} -``` - -This will allow for sorting to be optimized sequentially. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: tokenId) { - id - tokenId - } -} -``` - -Query Response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x…", - "tokenId": "1" - }, - { - "id": "0x…", - "tokenId": "2" - }, - { - "id": "0x…", - "tokenId": "3" - } - ] - } -} -``` - -## Conclusion - -Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. - -Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/uk/subgraphs/cookbook/pruning.mdx b/website/src/pages/uk/subgraphs/cookbook/pruning.mdx deleted file mode 100644 index e212d5d02bc9..000000000000 --- a/website/src/pages/uk/subgraphs/cookbook/pruning.mdx +++ /dev/null @@ -1,56 +0,0 @@ ---- -title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning -sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' ---- - -## TLDR - -[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. - -## How to Prune a Subgraph With `indexerHints` - -Add a section called `indexerHints` in the manifest. - -`indexerHints` has three `prune` options: - -- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. -- `prune: `: Sets a custom limit on the number of historical blocks to retain. -- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. - -We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: - -```yaml -specVersion: 1.0.0 -schema: - file: ./schema.graphql -indexerHints: - prune: auto -dataSources: - - kind: ethereum/contract - name: Contract - network: mainnet -``` - -## Important Considerations - -- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. - -- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). - -## Conclusion - -Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/uk/subgraphs/cookbook/timeseries.mdx b/website/src/pages/uk/subgraphs/cookbook/timeseries.mdx deleted file mode 100644 index 7c1c41008d29..000000000000 --- a/website/src/pages/uk/subgraphs/cookbook/timeseries.mdx +++ /dev/null @@ -1,195 +0,0 @@ ---- -title: Subgraph Best Practice 5 - Simplify and Optimize with Timeseries and Aggregations -sidebarTitle: 'Subgraph Best Practice 5: Timeseries and Aggregations' ---- - -## TLDR - -Leveraging the new time-series and aggregations feature in subgraphs can significantly enhance both indexing speed and query performance. - -## Overview - -Timeseries and aggregations reduce data processing overhead and accelerate queries by offloading aggregation computations to the database and simplifying mapping code. This approach is particularly effective when handling large volumes of time-based data. - -## Benefits of Timeseries and Aggregations - -1. Improved Indexing Time - -- Less Data to Load: Mappings handle less data since raw data points are stored as immutable timeseries entities. -- Database-Managed Aggregations: Aggregations are automatically computed by the database, reducing the workload on the mappings. - -2. Simplified Mapping Code - -- No Manual Calculations: Developers no longer need to write complex aggregation logic in mappings. -- Reduced Complexity: Simplifies code maintenance and minimizes the potential for errors. - -3. Dramatically Faster Queries - -- Immutable Data: All timeseries data is immutable, enabling efficient storage and retrieval. -- Efficient Data Separation: Aggregates are stored separately from raw timeseries data, allowing queries to process significantly less data—often several orders of magnitude less. - -### Important Considerations - -- Immutable Data: Timeseries data cannot be altered once written, ensuring data integrity and simplifying indexing. -- Automatic ID and Timestamp Management: id and timestamp fields are automatically managed by graph-node, reducing potential errors. -- Efficient Data Storage: By separating raw data from aggregates, storage is optimized, and queries run faster. - -## How to Implement Timeseries and Aggregations - -### Defining Timeseries Entities - -A timeseries entity represents raw data points collected over time. It is defined with the `@entity(timeseries: true)` annotation. Key requirements: - -- Immutable: Timeseries entities are always immutable. -- Mandatory Fields: - - `id`: Must be of type `Int8!` and is auto-incremented. - - `timestamp`: Must be of type `Timestamp!` and is automatically set to the block timestamp. - -Example: - -```graphql -type Data @entity(timeseries: true) { - id: Int8! - timestamp: Timestamp! - price: BigDecimal! -} -``` - -### Defining Aggregation Entities - -An aggregation entity computes aggregated values from a timeseries source. It is defined with the `@aggregation` annotation. Key components: - -- Annotation Arguments: - - `intervals`: Specifies time intervals (e.g., `["hour", "day"]`). - -Example: - -```graphql -type Stats @aggregation(intervals: ["hour", "day"], source: "Data") { - id: Int8! - timestamp: Timestamp! - sum: BigDecimal! @aggregate(fn: "sum", arg: "price") -} -``` - -In this example, Stats aggregates the price field from Data over hourly and daily intervals, computing the sum. - -### Querying Aggregated Data - -Aggregations are exposed via query fields that allow filtering and retrieval based on dimensions and time intervals. - -Example: - -```graphql -{ - tokenStats( - interval: "hour" - where: { token: "0x1234567890abcdef", timestamp_gte: "1704164640000000", timestamp_lt: "1704251040000000" } - ) { - id - timestamp - token { - id - } - totalVolume - priceUSD - count - } -} -``` - -### Using Dimensions in Aggregations - -Dimensions are non-aggregated fields used to group data points. They enable aggregations based on specific criteria, such as a token in a financial application. - -Example: - -### Timeseries Entity - -```graphql -type TokenData @entity(timeseries: true) { - id: Int8! - timestamp: Timestamp! - token: Token! - amount: BigDecimal! - priceUSD: BigDecimal! -} -``` - -### Aggregation Entity with Dimension - -```graphql -type TokenStats @aggregation(intervals: ["hour", "day"], source: "TokenData") { - id: Int8! - timestamp: Timestamp! - token: Token! - totalVolume: BigDecimal! @aggregate(fn: "sum", arg: "amount") - priceUSD: BigDecimal! @aggregate(fn: "last", arg: "priceUSD") - count: Int8! @aggregate(fn: "count", cumulative: true) -} -``` - -- Dimension Field: token groups the data, so aggregates are computed per token. -- Aggregates: - - totalVolume: Sum of amount. - - priceUSD: Last recorded priceUSD. - - count: Cumulative count of records. - -### Aggregation Functions and Expressions - -Supported aggregation functions: - -- sum -- count -- min -- max -- first -- last - -### The arg in @aggregate can be - -- A field name from the timeseries entity. -- An expression using fields and constants. - -### Examples of Aggregation Expressions - -- Sum Token Value: @aggregate(fn: "sum", arg: "priceUSD \_ amount") -- Maximum Positive Amount: @aggregate(fn: "max", arg: "greatest(amount0, amount1, 0)") -- Conditional Sum: @aggregate(fn: "sum", arg: "case when amount0 > amount1 then amount0 else 0 end") - -Supported operators and functions include basic arithmetic (+, -, \_, /), comparison operators, logical operators (and, or, not), and SQL functions like greatest, least, coalesce, etc. - -### Query Parameters - -- interval: Specifies the time interval (e.g., "hour"). -- where: Filters based on dimensions and timestamp ranges. -- timestamp_gte / timestamp_lt: Filters for start and end times (microseconds since epoch). - -### Notes - -- Sorting: Results are automatically sorted by timestamp and id in descending order. -- Current Data: An optional current argument can include the current, partially filled interval. - -### Conclusion - -Implementing timeseries and aggregations in subgraphs is a best practice for projects dealing with time-based data. This approach: - -- Enhances Performance: Speeds up indexing and querying by reducing data processing overhead. -- Simplifies Development: Eliminates the need for manual aggregation logic in mappings. -- Scales Efficiently: Handles large volumes of data without compromising on speed or responsiveness. - -By adopting this pattern, developers can build more efficient and scalable subgraphs, providing faster and more reliable data access to end-users. To learn more about implementing timeseries and aggregations, refer to the [Timeseries and Aggregations Readme](https://github.com/graphprotocol/graph-node/blob/master/docs/aggregations.md) and consider experimenting with this feature in your subgraphs. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/uk/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/uk/subgraphs/developing/creating/graph-ts/api.mdx index b5cec3b091e4..35bb04826c98 100644 --- a/website/src/pages/uk/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/uk/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/uk/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/uk/subgraphs/developing/creating/install-the-cli.mdx index ea09d89ab610..9f03c3a6c84a 100644 --- a/website/src/pages/uk/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/uk/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Install the Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Overview diff --git a/website/src/pages/uk/subgraphs/developing/deploying/_meta.js b/website/src/pages/uk/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/uk/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/uk/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/uk/subgraphs/querying/best-practices.mdx b/website/src/pages/uk/subgraphs/querying/best-practices.mdx index ae0fff305e31..f62d0540130d 100644 --- a/website/src/pages/uk/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/uk/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Відправлення запиту до GraphQL API diff --git a/website/src/pages/ro/substreams/developing/sinks/sinks.mdx b/website/src/pages/uk/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/ro/substreams/developing/sinks/sinks.mdx rename to website/src/pages/uk/substreams/developing/sinks.mdx diff --git a/website/src/pages/uk/substreams/developing/sinks/_meta.js b/website/src/pages/uk/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/uk/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/uk/substreams/quick-start.mdx b/website/src/pages/uk/substreams/quick-start.mdx index 2f8a30261c30..056c7391e15c 100644 --- a/website/src/pages/uk/substreams/quick-start.mdx +++ b/website/src/pages/uk/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/ur/resources/_meta-titles.json b/website/src/pages/ur/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/ur/resources/_meta-titles.json +++ b/website/src/pages/ur/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/ur/resources/_meta.js b/website/src/pages/ur/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/ur/resources/_meta.js +++ b/website/src/pages/ur/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/ur/resources/release-notes/_meta.js b/website/src/pages/ur/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/ur/resources/release-notes/_meta.js rename to website/src/pages/ur/resources/migration-guides/_meta.js diff --git a/website/src/pages/ur/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/ur/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/ur/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/ur/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/ur/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/ur/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 100% rename from website/src/pages/ur/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/ur/resources/migration-guides/graphql-validations-migration-guide.mdx diff --git a/website/src/pages/ur/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/ur/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/ur/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/ur/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/ur/sps/sps-faq.mdx b/website/src/pages/ur/sps/sps-faq.mdx index b070bde91765..e1395adba688 100644 --- a/website/src/pages/ur/sps/sps-faq.mdx +++ b/website/src/pages/ur/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/ur/subgraphs/_meta-titles.json b/website/src/pages/ur/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/ur/subgraphs/_meta-titles.json +++ b/website/src/pages/ur/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/ur/subgraphs/_meta.js b/website/src/pages/ur/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/ur/subgraphs/_meta.js +++ b/website/src/pages/ur/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/ur/subgraphs/best-practices/_meta.js b/website/src/pages/ur/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/ur/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/ur/subgraphs/best-practices/avoid-eth-calls.mdx b/website/src/pages/ur/subgraphs/best-practices/avoid-eth-calls.mdx new file mode 100644 index 000000000000..e40a7b3712e4 --- /dev/null +++ b/website/src/pages/ur/subgraphs/best-practices/avoid-eth-calls.mdx @@ -0,0 +1,117 @@ +--- +title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls +sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' +--- + +## TLDR + +`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. + +## Why Avoiding `eth_calls` Is a Best Practice + +Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. + +### What Does an eth_call Look Like? + +`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: + +```yaml +event Transfer(address indexed from, address indexed to, uint256 value); +``` + +Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, Transfer } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransfer(event: Transfer): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + // Bind the ERC20 contract instance to the given address: + let instance = ERC20.bind(event.address) + + // Retrieve pool information via eth_call + let poolInfo = instance.getPoolInfo(event.params.to) + + transaction.pool = poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is functional, however is not ideal as it slows down our subgraph’s indexing. + +## How to Eliminate `eth_calls` + +Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: + +``` +event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); +``` + +With this update, the subgraph can directly index the required data without external calls: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransferWithPool(event: TransferWithPool): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + transaction.pool = event.params.poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is much more performant as it has eliminated the need for `eth_calls`. + +## How to Optimize `eth_calls` + +If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. + +## Reducing the Runtime Overhead of `eth_calls` + +For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. + +Currently, `eth_calls` can only be declared for event handlers. In the manifest, write + +```yaml +event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) +handler: handleTransferWithPool +calls: + ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) +``` + +The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. + +The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. + +Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. + +## Conclusion + +You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ur/subgraphs/best-practices/derivedfrom.mdx b/website/src/pages/ur/subgraphs/best-practices/derivedfrom.mdx new file mode 100644 index 000000000000..db3a49928c89 --- /dev/null +++ b/website/src/pages/ur/subgraphs/best-practices/derivedfrom.mdx @@ -0,0 +1,89 @@ +--- +title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom +sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' +--- + +## TLDR + +Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. + +## How to Use the `@derivedFrom` Directive + +You just need to add a `@derivedFrom` directive after your array in your schema. Like this: + +```graphql +comments: [Comment!]! @derivedFrom(field: "post") +``` + +`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. + +### Example Use Case for `@derivedFrom` + +An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. + +Let’s start with our two entities, `Post` and `Comment` + +Without optimization, you could implement it like this with an array: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! +} + +type Comment @entity { + id: Bytes! + content: String! +} +``` + +Arrays like these will effectively store extra Comments data on the Post side of the relationship. + +Here’s what an optimized version looks like using `@derivedFrom`: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! @derivedFrom(field: "post") +} + +type Comment @entity { + id: Bytes! + content: String! + post: Post! +} +``` + +Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. + +This will not only make our subgraph more efficient, but it will also unlock three features: + +1. We can query the `Post` and see all of its comments. + +2. We can do a reverse lookup and query any `Comment` and see which post it comes from. + +3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. + +## Conclusion + +Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. + +For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ur/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/ur/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/ur/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/ur/subgraphs/best-practices/grafting-hotfix.mdx index 838f9ab3c6b6..b90ae82e0fa7 100644 --- a/website/src/pages/ur/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/ur/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ur/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx b/website/src/pages/ur/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx new file mode 100644 index 000000000000..6ff60ec9ab34 --- /dev/null +++ b/website/src/pages/ur/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -0,0 +1,191 @@ +--- +title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs +sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' +--- + +## TLDR + +Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. + +## Immutable Entities + +To make an entity immutable, we simply add `(immutable: true)` to an entity. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. + +Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. + +### Under the hood + +Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. + +### When not to use Immutable Entities + +If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. + +## Bytes as IDs + +Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. + +### Reasons to Not Use Bytes as IDs + +1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. +2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. +3. Indexing and querying performance improvements are not desired. + +### Concatenating With Bytes as IDs + +It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. + +Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. + +```typescript +export function handleTransfer(event: TransferEvent): void { + let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) + entity.from = event.params.from + entity.to = event.params.to + entity.value = event.params.value + + entity.blockNumber = event.block.number + entity.blockTimestamp = event.block.timestamp + entity.transactionHash = event.transaction.hash + + entity.save() +} +``` + +### Sorting With Bytes as IDs + +Sorting using Bytes as IDs is not optimal as seen in this example query and response. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: id) { + id + from + to + value + } +} +``` + +Query response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x00010000", + "from": "0xabcd...", + "to": "0x1234...", + "value": "256" + }, + { + "id": "0x00020000", + "from": "0xefgh...", + "to": "0x5678...", + "value": "512" + }, + { + "id": "0x01000000", + "from": "0xijkl...", + "to": "0x9abc...", + "value": "1" + } + ] + } +} +``` + +The IDs are returned as hex. + +To improve sorting, we should create another field on the entity that is a BigInt. + +```graphql +type Transfer @entity { + id: Bytes! + from: Bytes! # address + to: Bytes! # address + value: BigInt! # unit256 + tokenId: BigInt! # uint256 +} +``` + +This will allow for sorting to be optimized sequentially. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: tokenId) { + id + tokenId + } +} +``` + +Query Response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x…", + "tokenId": "1" + }, + { + "id": "0x…", + "tokenId": "2" + }, + { + "id": "0x…", + "tokenId": "3" + } + ] + } +} +``` + +## Conclusion + +Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. + +Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ur/subgraphs/best-practices/pruning.mdx b/website/src/pages/ur/subgraphs/best-practices/pruning.mdx new file mode 100644 index 000000000000..1b51dde8894f --- /dev/null +++ b/website/src/pages/ur/subgraphs/best-practices/pruning.mdx @@ -0,0 +1,56 @@ +--- +title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning +sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' +--- + +## TLDR + +[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. + +## How to Prune a Subgraph With `indexerHints` + +Add a section called `indexerHints` in the manifest. + +`indexerHints` has three `prune` options: + +- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. +- `prune: `: Sets a custom limit on the number of historical blocks to retain. +- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. + +We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: + +```yaml +specVersion: 1.0.0 +schema: + file: ./schema.graphql +indexerHints: + prune: auto +dataSources: + - kind: ethereum/contract + name: Contract + network: mainnet +``` + +## Important Considerations + +- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. + +- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). + +## Conclusion + +Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ur/subgraphs/cookbook/timeseries.mdx b/website/src/pages/ur/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/ur/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/ur/subgraphs/best-practices/timeseries.mdx index 8d34bdadf629..b8a181c76b7a 100644 --- a/website/src/pages/ur/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/ur/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/ur/subgraphs/cookbook/_meta.js b/website/src/pages/ur/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/ur/subgraphs/cookbook/_meta.js +++ b/website/src/pages/ur/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/ur/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/ur/subgraphs/cookbook/avoid-eth-calls.mdx deleted file mode 100644 index ae29cdf03a34..000000000000 --- a/website/src/pages/ur/subgraphs/cookbook/avoid-eth-calls.mdx +++ /dev/null @@ -1,117 +0,0 @@ ---- -title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls -sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' ---- - -## TLDR - -`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. - -## Why Avoiding `eth_calls` Is a Best Practice - -Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. - -### What Does an eth_call Look Like? - -`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: - -```yaml -event Transfer(address indexed from, address indexed to, uint256 value); -``` - -Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, Transfer } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransfer(event: Transfer): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - // Bind the ERC20 contract instance to the given address: - let instance = ERC20.bind(event.address) - - // Retrieve pool information via eth_call - let poolInfo = instance.getPoolInfo(event.params.to) - - transaction.pool = poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is functional, however is not ideal as it slows down our subgraph’s indexing. - -## How to Eliminate `eth_calls` - -Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: - -``` -event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); -``` - -With this update, the subgraph can directly index the required data without external calls: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransferWithPool(event: TransferWithPool): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - transaction.pool = event.params.poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is much more performant as it has eliminated the need for `eth_calls`. - -## How to Optimize `eth_calls` - -If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. - -## Reducing the Runtime Overhead of `eth_calls` - -For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. - -Currently, `eth_calls` can only be declared for event handlers. In the manifest, write - -```yaml -event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) -handler: handleTransferWithPool -calls: - ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) -``` - -The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. - -The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. - -Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. - -## Conclusion - -You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ur/subgraphs/cookbook/cosmos.mdx b/website/src/pages/ur/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index e6cdbe1a2dac..000000000000 --- a/website/src/pages/ur/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: کوزموس پر سب گراف بنانا ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## کوزموس کے سب گراف کیا ہیں ؟ - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -کوزموس سب گراف میں چار قسم کے ہینڈلرز کی حمایت کی جاتی ہے: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -اگرچہ تمام ڈیٹا تک بلاک ہینڈلر کے ذریعے رسائی حاصل کی جا سکتی ہے، دوسرے ہینڈلرز سب گراف ڈویلپرز کو زیادہ دانے دار طریقے سے ڈیٹا پر کارروائی کرنے کے قابل بناتے ہیں. - -## کوزموس سب گراف کی تعمیر - -### سب گراف انحصار - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### سب گراف کے مین اجزاء - -جب سب گراف کی وضاحت کی بات آتی ہے تو تین اہم حصے ہوتے ہیں: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### سب گراف مینی فیسٹ کی تعریف - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### اسکیما کی تعریف - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### اسمبلی اسکرپٹ سب میپنک - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -ہر ہینڈلر کی قسم اس کے اپنے ڈیٹا ڈھانچے کے ساتھ آتی ہے جو میپنگ فنکشن کی دلیل کے طور پر پاس کی جاتی ہے. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### پیغام کی ضابطہ کشائی - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## کوزموس سب گراف بنانا اور تعمیر کرنا - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## کوزموس سب گراف کو تعینات کرنا - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## ایک کوزموس سب گراف کو کیوری کرنا - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## تعاون یافتہ کوزموس بلاکچین - -### کوزموس ہب - -#### کوزموس ہب کیا ہے؟ - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### نیٹ ورکس - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### اوسموسس - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### اوسموسس کیا ہے؟ - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### نیٹ ورکس - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## سب گراف کی مثال - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/ur/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/ur/subgraphs/cookbook/derivedfrom.mdx deleted file mode 100644 index a0942645c999..000000000000 --- a/website/src/pages/ur/subgraphs/cookbook/derivedfrom.mdx +++ /dev/null @@ -1,89 +0,0 @@ ---- -title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom -sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' ---- - -## TLDR - -Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. - -## How to Use the `@derivedFrom` Directive - -You just need to add a `@derivedFrom` directive after your array in your schema. Like this: - -```graphql -comments: [Comment!]! @derivedFrom(field: "post") -``` - -`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. - -### Example Use Case for `@derivedFrom` - -An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. - -Let’s start with our two entities, `Post` and `Comment` - -Without optimization, you could implement it like this with an array: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! -} - -type Comment @entity { - id: Bytes! - content: String! -} -``` - -Arrays like these will effectively store extra Comments data on the Post side of the relationship. - -Here’s what an optimized version looks like using `@derivedFrom`: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! @derivedFrom(field: "post") -} - -type Comment @entity { - id: Bytes! - content: String! - post: Post! -} -``` - -Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. - -This will not only make our subgraph more efficient, but it will also unlock three features: - -1. We can query the `Post` and see all of its comments. - -2. We can do a reverse lookup and query any `Comment` and see which post it comes from. - -3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. - -## Conclusion - -Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. - -For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ur/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/ur/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx deleted file mode 100644 index 511565bb3dd4..000000000000 --- a/website/src/pages/ur/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ /dev/null @@ -1,191 +0,0 @@ ---- -title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs -sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' ---- - -## TLDR - -Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. - -## Immutable Entities - -To make an entity immutable, we simply add `(immutable: true)` to an entity. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. - -Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. - -### Under the hood - -Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. - -### When not to use Immutable Entities - -If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. - -## Bytes as IDs - -Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. - -### Reasons to Not Use Bytes as IDs - -1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. -2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. -3. Indexing and querying performance improvements are not desired. - -### Concatenating With Bytes as IDs - -It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. - -Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. - -```typescript -export function handleTransfer(event: TransferEvent): void { - let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) - entity.from = event.params.from - entity.to = event.params.to - entity.value = event.params.value - - entity.blockNumber = event.block.number - entity.blockTimestamp = event.block.timestamp - entity.transactionHash = event.transaction.hash - - entity.save() -} -``` - -### Sorting With Bytes as IDs - -Sorting using Bytes as IDs is not optimal as seen in this example query and response. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: id) { - id - from - to - value - } -} -``` - -Query response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x00010000", - "from": "0xabcd...", - "to": "0x1234...", - "value": "256" - }, - { - "id": "0x00020000", - "from": "0xefgh...", - "to": "0x5678...", - "value": "512" - }, - { - "id": "0x01000000", - "from": "0xijkl...", - "to": "0x9abc...", - "value": "1" - } - ] - } -} -``` - -The IDs are returned as hex. - -To improve sorting, we should create another field on the entity that is a BigInt. - -```graphql -type Transfer @entity { - id: Bytes! - from: Bytes! # address - to: Bytes! # address - value: BigInt! # unit256 - tokenId: BigInt! # uint256 -} -``` - -This will allow for sorting to be optimized sequentially. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: tokenId) { - id - tokenId - } -} -``` - -Query Response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x…", - "tokenId": "1" - }, - { - "id": "0x…", - "tokenId": "2" - }, - { - "id": "0x…", - "tokenId": "3" - } - ] - } -} -``` - -## Conclusion - -Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. - -Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ur/subgraphs/cookbook/pruning.mdx b/website/src/pages/ur/subgraphs/cookbook/pruning.mdx deleted file mode 100644 index e212d5d02bc9..000000000000 --- a/website/src/pages/ur/subgraphs/cookbook/pruning.mdx +++ /dev/null @@ -1,56 +0,0 @@ ---- -title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning -sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' ---- - -## TLDR - -[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. - -## How to Prune a Subgraph With `indexerHints` - -Add a section called `indexerHints` in the manifest. - -`indexerHints` has three `prune` options: - -- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. -- `prune: `: Sets a custom limit on the number of historical blocks to retain. -- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. - -We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: - -```yaml -specVersion: 1.0.0 -schema: - file: ./schema.graphql -indexerHints: - prune: auto -dataSources: - - kind: ethereum/contract - name: Contract - network: mainnet -``` - -## Important Considerations - -- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. - -- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). - -## Conclusion - -Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/ur/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/ur/subgraphs/developing/creating/graph-ts/api.mdx index 9ad2e9b7cc91..e8e3e92cc489 100644 --- a/website/src/pages/ur/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/ur/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: اسمبلی اسکرپٹ API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/ur/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/ur/subgraphs/developing/creating/install-the-cli.mdx index 70226de74267..14ead227c976 100644 --- a/website/src/pages/ur/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/ur/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: گراف CLI انسٹال کریں --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## جائزہ diff --git a/website/src/pages/ur/subgraphs/developing/deploying/_meta.js b/website/src/pages/ur/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/ur/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/ur/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/ur/subgraphs/querying/best-practices.mdx b/website/src/pages/ur/subgraphs/querying/best-practices.mdx index 7b60a12c440f..3c367fdac0ee 100644 --- a/website/src/pages/ur/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/ur/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### GraphQL API کو ایک کیوری بھیجنا diff --git a/website/src/pages/ur/substreams/developing/sinks/sinks.mdx b/website/src/pages/ur/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/ur/substreams/developing/sinks/sinks.mdx rename to website/src/pages/ur/substreams/developing/sinks.mdx diff --git a/website/src/pages/ur/substreams/developing/sinks/_meta.js b/website/src/pages/ur/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/ur/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/ur/substreams/quick-start.mdx b/website/src/pages/ur/substreams/quick-start.mdx index d251b62c34a5..de7572a6bc59 100644 --- a/website/src/pages/ur/substreams/quick-start.mdx +++ b/website/src/pages/ur/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/vi/resources/_meta-titles.json b/website/src/pages/vi/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/vi/resources/_meta-titles.json +++ b/website/src/pages/vi/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/vi/resources/_meta.js b/website/src/pages/vi/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/vi/resources/_meta.js +++ b/website/src/pages/vi/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/vi/resources/release-notes/_meta.js b/website/src/pages/vi/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/vi/resources/release-notes/_meta.js rename to website/src/pages/vi/resources/migration-guides/_meta.js diff --git a/website/src/pages/vi/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/vi/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/vi/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/vi/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/vi/resources/migration-guides/graphql-validations-migration-guide.mdx b/website/src/pages/vi/resources/migration-guides/graphql-validations-migration-guide.mdx new file mode 100644 index 000000000000..29fed533ef8c --- /dev/null +++ b/website/src/pages/vi/resources/migration-guides/graphql-validations-migration-guide.mdx @@ -0,0 +1,538 @@ +--- +title: GraphQL Validations Migration Guide +--- + +Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). + +Previous versions of `graph-node` did not support all validations and provided more graceful responses - so, in cases of ambiguity, `graph-node` was ignoring invalid GraphQL operations components. + +GraphQL Validations support is the pillar for the upcoming new features and the performance at scale of The Graph Network. + +It will also ensure determinism of query responses, a key requirement on The Graph Network. + +**Enabling the GraphQL Validations will break some existing queries** sent to The Graph API. + +To be compliant with those validations, please follow the migration guide. + +> ⚠️ If you do not migrate your queries before the validations are rolled out, they will return errors and possibly break your frontends/clients. + +## Migration guide + +You can use the CLI migration tool to find any issues in your GraphQL operations and fix them. Alternatively you can update the endpoint of your GraphQL client to use the `https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME` endpoint. Testing your queries against this endpoint will help you find the issues in your queries. + +> Not all subgraphs will need to be migrated, if you are using [GraphQL ESlint](https://the-guild.dev/graphql/eslint/docs) or [GraphQL Code Generator](https://the-guild.dev/graphql/codegen), they already ensure that your queries are valid. + +## Migration CLI tool + +**Most of the GraphQL operations errors can be found in your codebase ahead of time.** + +For this reason, we provide a smooth experience for validating your GraphQL operations during development or in CI. + +[`@graphql-validate/cli`](https://github.com/saihaj/graphql-validate) is a simple CLI tool that helps validate GraphQL operations against a given schema. + +### **Getting started** + +You can run the tool as follows: + +```bash +npx @graphql-validate/cli -s https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME -o *.graphql +``` + +**Notes:** + +- Set or replace $GITHUB_USER, $SUBGRAPH_NAME with the appropriate values. Like: [`artblocks/art-blocks`](https://api.thegraph.com/subgraphs/name/artblocks/art-blocks) +- The preview schema URL (https://api-next.thegraph.com/) provided is heavily rate-limited and will be sunset once all users have migrated to the new version. **Do not use it in production.** +- Operations are identified in files with the following extensions [`.graphql`,](https://www.graphql-tools.com/docs/schema-loading#graphql-file-loader)[`.ts`, `.tsx`, `.js`, `jsx`](https://www.graphql-tools.com/docs/schema-loading#code-file-loader) (`-o` option). + +### CLI output + +The `[@graphql-validate/cli](https://github.com/saihaj/graphql-validate)` CLI tool will output any GraphQL operations errors as follows: + +![Error output from CLI](https://i.imgur.com/x1cBdhq.png) + +For each error, you will find a description, file path and position, and a link to a solution example (see the following section). + +## Run your local queries against the preview schema + +We provide an endpoint `https://api-next.thegraph.com/` that runs a `graph-node` version that has validations turned on. + +You can try out queries by sending them to: + +- `https://api-next.thegraph.com/subgraphs/id/` + +or + +- `https://api-next.thegraph.com/subgraphs/name//` + +To work on queries that have been flagged as having validation errors, you can use your favorite GraphQL query tool, like Altair or [GraphiQL](https://cloud.hasura.io/public/graphiql), and try your query out. Those tools will also mark those errors in their UI, even before you run it. + +## How to solve issues + +Below, you will find all the GraphQL validations errors that could occur on your existing GraphQL operations. + +### GraphQL variables, operations, fragments, or arguments must be unique + +We applied rules for ensuring that an operation includes a unique set of GraphQL variables, operations, fragments, and arguments. + +A GraphQL operation is only valid if it does not contain any ambiguity. + +To achieve that, we need to ensure that some components in your GraphQL operation must be unique. + +Here's an example of a few invalid operations that violates these rules: + +**Duplicate Query name (#UniqueOperationNamesRule)** + +```graphql +# The following operation violated the UniqueOperationName +# rule, since we have a single operation with 2 queries +# with the same name +query myData { + id +} + +query myData { + name +} +``` + +_Solution:_ + +```graphql +query myData { + id +} + +query myData2 { + # rename the second query + name +} +``` + +**Duplicate Fragment name (#UniqueFragmentNamesRule)** + +```graphql +# The following operation violated the UniqueFragmentName +# rule. +query myData { + id + ...MyFields +} + +fragment MyFields { + metadata +} + +fragment MyFields { + name +} +``` + +_Solution:_ + +```graphql +query myData { + id + ...MyFieldsName + ...MyFieldsMetadata +} + +fragment MyFieldsMetadata { # assign a unique name to fragment + metadata +} + +fragment MyFieldsName { # assign a unique name to fragment + name +} +``` + +**Duplicate variable name (#UniqueVariableNamesRule)** + +```graphql +# The following operation violates the UniqueVariables +query myData($id: String, $id: Int) { + id + ...MyFields +} +``` + +_Solution:_ + +```graphql +query myData($id: String) { + # keep the relevant variable (here: `$id: String`) + id + ...MyFields +} +``` + +**Duplicate argument name (#UniqueArgument)** + +```graphql +# The following operation violated the UniqueArguments +query myData($id: ID!) { + userById(id: $id, id: "1") { + id + } +} +``` + +_Solution:_ + +```graphql +query myData($id: ID!) { + userById(id: $id) { + id + } +} +``` + +**Duplicate anonymous query (#LoneAnonymousOperationRule)** + +Also, using two anonymous operations will violate the `LoneAnonymousOperation` rule due to conflict in the response structure: + +```graphql +# This will fail if executed together in +# a single operation with the following two queries: +query { + someField +} + +query { + otherField +} +``` + +_Solution:_ + +```graphql +query { + someField + otherField +} +``` + +Or name the two queries: + +```graphql +query FirstQuery { + someField +} + +query SecondQuery { + otherField +} +``` + +### Overlapping Fields + +A GraphQL selection set is considered valid only if it correctly resolves the eventual result set. + +If a specific selection set, or a field, creates ambiguity either by the selected field or by the arguments used, the GraphQL service will fail to validate the operation. + +Here are a few examples of invalid operations that violate this rule: + +**Conflicting fields aliases (#OverlappingFieldsCanBeMergedRule)** + +```graphql +# Aliasing fields might cause conflicts, either with +# other aliases or other fields that exist on the +# GraphQL schema. +query { + dogs { + name: nickname + name + } +} +``` + +_Solution:_ + +```graphql +query { + dogs { + name: nickname + originalName: name # alias the original `name` field + } +} +``` + +**Conflicting fields with arguments (#OverlappingFieldsCanBeMergedRule)** + +```graphql +# Different arguments might lead to different data, +# so we can't assume the fields will be the same. +query { + dogs { + doesKnowCommand(dogCommand: SIT) + doesKnowCommand(dogCommand: HEEL) + } +} +``` + +_Solution:_ + +```graphql +query { + dogs { + knowsHowToSit: doesKnowCommand(dogCommand: SIT) + knowsHowToHeel: doesKnowCommand(dogCommand: HEEL) + } +} +``` + +Also, in more complex use-cases, you might violate this rule by using two fragments that might cause a conflict in the eventually expected set: + +```graphql +query { + # Eventually, we have two "x" definitions, pointing + # to different fields! + ...A + ...B +} + +fragment A on Type { + x: a +} + +fragment B on Type { + x: b +} +``` + +In addition to that, client-side GraphQL directives like `@skip` and `@include` might lead to ambiguity, for example: + +```graphql +fragment mergeSameFieldsWithSameDirectives on Dog { + name @include(if: true) + name @include(if: false) +} +``` + +[You can read more about the algorithm here.](https://spec.graphql.org/June2018/#sec-Field-Selection-Merging) + +### Unused Variables or Fragments + +A GraphQL operation is also considered valid only if all operation-defined components (variables, fragments) are used. + +Here are a few examples for GraphQL operations that violates these rules: + +**Unused variable** (#NoUnusedVariablesRule) + +```graphql +# Invalid, because $someVar is never used. +query something($someVar: String) { + someData +} +``` + +_Solution:_ + +```graphql +query something { + someData +} +``` + +**Unused Fragment** (#NoUnusedFragmentsRule) + +```graphql +# Invalid, because fragment AllFields is never used. +query something { + someData +} + +fragment AllFields { # unused :( + name + age +} +``` + +_Solution:_ + +```graphql +# Invalid, because fragment AllFields is never used. +query something { + someData +} + +# remove the `AllFields` fragment +``` + +### Invalid or missing Selection-Set (#ScalarLeafsRule) + +Also, a GraphQL field selection is only valid if the following is validated: + +- An object field must-have selection set specified. +- An edge field (scalar, enum) must not have a selection set specified. + +Here are a few examples of violations of these rules with the following Schema: + +```graphql +type Image { + url: String! +} + +type User { + id: ID! + avatar: Image! +} + +type Query { + user: User! +} +``` + +**Invalid Selection-Set** + +```graphql +query { + user { + id { # Invalid, because "id" is of type ID and does not have sub-fields + + } + } +} +``` + +_Solution:_ + +```graphql +query { + user { + id + } +} +``` + +**Missing Selection-Set** + +```graphql +query { + user { + id + image # `image` requires a Selection-Set for sub-fields! + } +} +``` + +_Solution:_ + +```graphql +query { + user { + id + image { + src + } + } +} +``` + +### Incorrect Arguments values (#VariablesInAllowedPositionRule) + +GraphQL operations that pass hard-coded values to arguments must be valid, based on the value defined in the schema. + +Here are a few examples of invalid operations that violate these rules: + +```graphql +query purposes { + # If "name" is defined as "String" in the schema, + # this query will fail during validation. + purpose(name: 1) { + id + } +} + +# This might also happen when an incorrect variable is defined: + +query purposes($name: Int!) { + # If "name" is defined as `String` in the schema, + # this query will fail during validation, because the + # variable used is of type `Int` + purpose(name: $name) { + id + } +} +``` + +### Unknown Type, Variable, Fragment, or Directive (#UnknownX) + +The GraphQL API will raise an error if any unknown type, variable, fragment, or directive is used. + +Those unknown references must be fixed: + +- rename if it was a typo +- otherwise, remove + +### Fragment: invalid spread or definition + +**Invalid Fragment spread (#PossibleFragmentSpreadsRule)** + +A Fragment cannot be spread on a non-applicable type. + +Example, we cannot apply a `Cat` fragment to the `Dog` type: + +```graphql +query { + dog { + ...CatSimple + } +} + +fragment CatSimple on Cat { + # ... +} +``` + +**Invalid Fragment definition (#FragmentsOnCompositeTypesRule)** + +All Fragment must be defined upon (using `on ...`) a composite type, in short: object, interface, or union. + +The following examples are invalid, since defining fragments on scalars is invalid. + +```graphql +fragment fragOnScalar on Int { + # we cannot define a fragment upon a scalar (`Int`) + something +} + +fragment inlineFragOnScalar on Dog { + ... on Boolean { + # `Boolean` is not a subtype of `Dog` + somethingElse + } +} +``` + +### Directives usage + +**Directive cannot be used at this location (#KnownDirectivesRule)** + +Only GraphQL directives (`@...`) supported by The Graph API can be used. + +Here is an example with The GraphQL supported directives: + +```graphql +query { + dog { + name @include(true) + age @skip(true) + } +} +``` + +_Note: `@stream`, `@live`, `@defer` are not supported._ + +**Directive can only be used once at this location (#UniqueDirectivesPerLocationRule)** + +The directives supported by The Graph can only be used once per location. + +The following is invalid (and redundant): + +```graphql +query { + dog { + name @include(true) @include(true) + } +} +``` diff --git a/website/src/pages/vi/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/vi/resources/release-notes/graphql-validations-migration-guide.mdx deleted file mode 100644 index 4d909e8970a8..000000000000 --- a/website/src/pages/vi/resources/release-notes/graphql-validations-migration-guide.mdx +++ /dev/null @@ -1,538 +0,0 @@ ---- -title: GraphQL Validations migration guide ---- - -Soon `graph-node` will support 100% coverage of the [GraphQL Validations specification](https://spec.graphql.org/June2018/#sec-Validation). - -Previous versions of `graph-node` did not support all validations and provided more graceful responses - so, in cases of ambiguity, `graph-node` was ignoring invalid GraphQL operations components. - -GraphQL Validations support is the pillar for the upcoming new features and the performance at scale of The Graph Network. - -It will also ensure determinism of query responses, a key requirement on The Graph Network. - -**Enabling the GraphQL Validations will break some existing queries** sent to The Graph API. - -To be compliant with those validations, please follow the migration guide. - -> ⚠️ If you do not migrate your queries before the validations are rolled out, they will return errors and possibly break your frontends/clients. - -## Migration guide - -You can use the CLI migration tool to find any issues in your GraphQL operations and fix them. Alternatively you can update the endpoint of your GraphQL client to use the `https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME` endpoint. Testing your queries against this endpoint will help you find the issues in your queries. - -> Not all subgraphs will need to be migrated, if you are using [GraphQL ESlint](https://the-guild.dev/graphql/eslint/docs) or [GraphQL Code Generator](https://the-guild.dev/graphql/codegen), they already ensure that your queries are valid. - -## Migration CLI tool - -**Most of the GraphQL operations errors can be found in your codebase ahead of time.** - -For this reason, we provide a smooth experience for validating your GraphQL operations during development or in CI. - -[`@graphql-validate/cli`](https://github.com/saihaj/graphql-validate) is a simple CLI tool that helps validate GraphQL operations against a given schema. - -### **Getting started** - -You can run the tool as follows: - -```bash -npx @graphql-validate/cli -s https://api-next.thegraph.com/subgraphs/name/$GITHUB_USER/$SUBGRAPH_NAME -o *.graphql -``` - -**Notes:** - -- Set or replace $GITHUB_USER, $SUBGRAPH_NAME with the appropriate values. Like: [`artblocks/art-blocks`](https://api.thegraph.com/subgraphs/name/artblocks/art-blocks) -- The preview schema URL (https://api-next.thegraph.com/) provided is heavily rate-limited and will be sunset once all users have migrated to the new version. **Do not use it in production.** -- Operations are identified in files with the following extensions [`.graphql`,](https://www.graphql-tools.com/docs/schema-loading#graphql-file-loader)[`.ts`, `.tsx`, `.js`, `jsx`](https://www.graphql-tools.com/docs/schema-loading#code-file-loader) (`-o` option). - -### CLI output - -The `[@graphql-validate/cli](https://github.com/saihaj/graphql-validate)` CLI tool will output any GraphQL operations errors as follows: - -![Error output from CLI](https://i.imgur.com/x1cBdhq.png) - -For each error, you will find a description, file path and position, and a link to a solution example (see the following section). - -## Run your local queries against the preview schema - -We provide an endpoint `https://api-next.thegraph.com/` that runs a `graph-node` version that has validations turned on. - -You can try out queries by sending them to: - -- `https://api-next.thegraph.com/subgraphs/id/` - -or - -- `https://api-next.thegraph.com/subgraphs/name//` - -To work on queries that have been flagged as having validation errors, you can use your favorite GraphQL query tool, like Altair or [GraphiQL](https://cloud.hasura.io/public/graphiql), and try your query out. Those tools will also mark those errors in their UI, even before you run it. - -## How to solve issues - -Below, you will find all the GraphQL validations errors that could occur on your existing GraphQL operations. - -### GraphQL variables, operations, fragments, or arguments must be unique - -We applied rules for ensuring that an operation includes a unique set of GraphQL variables, operations, fragments, and arguments. - -A GraphQL operation is only valid if it does not contain any ambiguity. - -To achieve that, we need to ensure that some components in your GraphQL operation must be unique. - -Here's an example of a few invalid operations that violates these rules: - -**Duplicate Query name (#UniqueOperationNamesRule)** - -```graphql -# The following operation violated the UniqueOperationName -# rule, since we have a single operation with 2 queries -# with the same name -query myData { - id -} - -query myData { - name -} -``` - -_Solution:_ - -```graphql -query myData { - id -} - -query myData2 { - # rename the second query - name -} -``` - -**Duplicate Fragment name (#UniqueFragmentNamesRule)** - -```graphql -# The following operation violated the UniqueFragmentName -# rule. -query myData { - id - ...MyFields -} - -fragment MyFields { - metadata -} - -fragment MyFields { - name -} -``` - -_Solution:_ - -```graphql -query myData { - id - ...MyFieldsName - ...MyFieldsMetadata -} - -fragment MyFieldsMetadata { # assign a unique name to fragment - metadata -} - -fragment MyFieldsName { # assign a unique name to fragment - name -} -``` - -**Duplicate variable name (#UniqueVariableNamesRule)** - -```graphql -# The following operation violates the UniqueVariables -query myData($id: String, $id: Int) { - id - ...MyFields -} -``` - -_Solution:_ - -```graphql -query myData($id: String) { - # keep the relevant variable (here: `$id: String`) - id - ...MyFields -} -``` - -**Duplicate argument name (#UniqueArgument)** - -```graphql -# The following operation violated the UniqueArguments -query myData($id: ID!) { - userById(id: $id, id: "1") { - id - } -} -``` - -_Solution:_ - -```graphql -query myData($id: ID!) { - userById(id: $id) { - id - } -} -``` - -**Duplicate anonymous query (#LoneAnonymousOperationRule)** - -Also, using two anonymous operations will violate the `LoneAnonymousOperation` rule due to conflict in the response structure: - -```graphql -# This will fail if executed together in -# a single operation with the following two queries: -query { - someField -} - -query { - otherField -} -``` - -_Solution:_ - -```graphql -query { - someField - otherField -} -``` - -Or name the two queries: - -```graphql -query FirstQuery { - someField -} - -query SecondQuery { - otherField -} -``` - -### Overlapping Fields - -A GraphQL selection set is considered valid only if it correctly resolves the eventual result set. - -If a specific selection set, or a field, creates ambiguity either by the selected field or by the arguments used, the GraphQL service will fail to validate the operation. - -Here are a few examples of invalid operations that violate this rule: - -**Conflicting fields aliases (#OverlappingFieldsCanBeMergedRule)** - -```graphql -# Aliasing fields might cause conflicts, either with -# other aliases or other fields that exist on the -# GraphQL schema. -query { - dogs { - name: nickname - name - } -} -``` - -_Solution:_ - -```graphql -query { - dogs { - name: nickname - originalName: name # alias the original `name` field - } -} -``` - -**Conflicting fields with arguments (#OverlappingFieldsCanBeMergedRule)** - -```graphql -# Different arguments might lead to different data, -# so we can't assume the fields will be the same. -query { - dogs { - doesKnowCommand(dogCommand: SIT) - doesKnowCommand(dogCommand: HEEL) - } -} -``` - -_Solution:_ - -```graphql -query { - dogs { - knowsHowToSit: doesKnowCommand(dogCommand: SIT) - knowsHowToHeel: doesKnowCommand(dogCommand: HEEL) - } -} -``` - -Also, in more complex use-cases, you might violate this rule by using two fragments that might cause a conflict in the eventually expected set: - -```graphql -query { - # Eventually, we have two "x" definitions, pointing - # to different fields! - ...A - ...B -} - -fragment A on Type { - x: a -} - -fragment B on Type { - x: b -} -``` - -In addition to that, client-side GraphQL directives like `@skip` and `@include` might lead to ambiguity, for example: - -```graphql -fragment mergeSameFieldsWithSameDirectives on Dog { - name @include(if: true) - name @include(if: false) -} -``` - -[You can read more about the algorithm here.](https://spec.graphql.org/June2018/#sec-Field-Selection-Merging) - -### Unused Variables or Fragments - -A GraphQL operation is also considered valid only if all operation-defined components (variables, fragments) are used. - -Here are a few examples for GraphQL operations that violates these rules: - -**Unused variable** (#NoUnusedVariablesRule) - -```graphql -# Invalid, because $someVar is never used. -query something($someVar: String) { - someData -} -``` - -_Solution:_ - -```graphql -query something { - someData -} -``` - -**Unused Fragment** (#NoUnusedFragmentsRule) - -```graphql -# Invalid, because fragment AllFields is never used. -query something { - someData -} - -fragment AllFields { # unused :( - name - age -} -``` - -_Solution:_ - -```graphql -# Invalid, because fragment AllFields is never used. -query something { - someData -} - -# remove the `AllFields` fragment -``` - -### Invalid or missing Selection-Set (#ScalarLeafsRule) - -Also, a GraphQL field selection is only valid if the following is validated: - -- An object field must-have selection set specified. -- An edge field (scalar, enum) must not have a selection set specified. - -Here are a few examples of violations of these rules with the following Schema: - -```graphql -type Image { - url: String! -} - -type User { - id: ID! - avatar: Image! -} - -type Query { - user: User! -} -``` - -**Invalid Selection-Set** - -```graphql -query { - user { - id { # Invalid, because "id" is of type ID and does not have sub-fields - - } - } -} -``` - -_Solution:_ - -```graphql -query { - user { - id - } -} -``` - -**Missing Selection-Set** - -```graphql -query { - user { - id - image # `image` requires a Selection-Set for sub-fields! - } -} -``` - -_Solution:_ - -```graphql -query { - user { - id - image { - src - } - } -} -``` - -### Incorrect Arguments values (#VariablesInAllowedPositionRule) - -GraphQL operations that pass hard-coded values to arguments must be valid, based on the value defined in the schema. - -Here are a few examples of invalid operations that violate these rules: - -```graphql -query purposes { - # If "name" is defined as "String" in the schema, - # this query will fail during validation. - purpose(name: 1) { - id - } -} - -# This might also happen when an incorrect variable is defined: - -query purposes($name: Int!) { - # If "name" is defined as `String` in the schema, - # this query will fail during validation, because the - # variable used is of type `Int` - purpose(name: $name) { - id - } -} -``` - -### Unknown Type, Variable, Fragment, or Directive (#UnknownX) - -The GraphQL API will raise an error if any unknown type, variable, fragment, or directive is used. - -Those unknown references must be fixed: - -- rename if it was a typo -- otherwise, remove - -### Fragment: invalid spread or definition - -**Invalid Fragment spread (#PossibleFragmentSpreadsRule)** - -A Fragment cannot be spread on a non-applicable type. - -Example, we cannot apply a `Cat` fragment to the `Dog` type: - -```graphql -query { - dog { - ...CatSimple - } -} - -fragment CatSimple on Cat { - # ... -} -``` - -**Invalid Fragment definition (#FragmentsOnCompositeTypesRule)** - -All Fragment must be defined upon (using `on ...`) a composite type, in short: object, interface, or union. - -The following examples are invalid, since defining fragments on scalars is invalid. - -```graphql -fragment fragOnScalar on Int { - # we cannot define a fragment upon a scalar (`Int`) - something -} - -fragment inlineFragOnScalar on Dog { - ... on Boolean { - # `Boolean` is not a subtype of `Dog` - somethingElse - } -} -``` - -### Directives usage - -**Directive cannot be used at this location (#KnownDirectivesRule)** - -Only GraphQL directives (`@...`) supported by The Graph API can be used. - -Here is an example with The GraphQL supported directives: - -```graphql -query { - dog { - name @include(true) - age @skip(true) - } -} -``` - -_Note: `@stream`, `@live`, `@defer` are not supported._ - -**Directive can only be used once at this location (#UniqueDirectivesPerLocationRule)** - -The directives supported by The Graph can only be used once per location. - -The following is invalid (and redundant): - -```graphql -query { - dog { - name @include(true) @include(true) - } -} -``` diff --git a/website/src/pages/vi/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/vi/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/vi/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/vi/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/vi/sps/sps-faq.mdx b/website/src/pages/vi/sps/sps-faq.mdx index 537f29b09ea6..abc1f3906686 100644 --- a/website/src/pages/vi/sps/sps-faq.mdx +++ b/website/src/pages/vi/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/vi/subgraphs/_meta-titles.json b/website/src/pages/vi/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/vi/subgraphs/_meta-titles.json +++ b/website/src/pages/vi/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/vi/subgraphs/_meta.js b/website/src/pages/vi/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/vi/subgraphs/_meta.js +++ b/website/src/pages/vi/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/vi/subgraphs/best-practices/_meta.js b/website/src/pages/vi/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/vi/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/vi/subgraphs/best-practices/avoid-eth-calls.mdx b/website/src/pages/vi/subgraphs/best-practices/avoid-eth-calls.mdx new file mode 100644 index 000000000000..e40a7b3712e4 --- /dev/null +++ b/website/src/pages/vi/subgraphs/best-practices/avoid-eth-calls.mdx @@ -0,0 +1,117 @@ +--- +title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls +sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' +--- + +## TLDR + +`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. + +## Why Avoiding `eth_calls` Is a Best Practice + +Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. + +### What Does an eth_call Look Like? + +`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: + +```yaml +event Transfer(address indexed from, address indexed to, uint256 value); +``` + +Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, Transfer } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransfer(event: Transfer): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + // Bind the ERC20 contract instance to the given address: + let instance = ERC20.bind(event.address) + + // Retrieve pool information via eth_call + let poolInfo = instance.getPoolInfo(event.params.to) + + transaction.pool = poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is functional, however is not ideal as it slows down our subgraph’s indexing. + +## How to Eliminate `eth_calls` + +Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: + +``` +event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); +``` + +With this update, the subgraph can directly index the required data without external calls: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransferWithPool(event: TransferWithPool): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + transaction.pool = event.params.poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is much more performant as it has eliminated the need for `eth_calls`. + +## How to Optimize `eth_calls` + +If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. + +## Reducing the Runtime Overhead of `eth_calls` + +For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. + +Currently, `eth_calls` can only be declared for event handlers. In the manifest, write + +```yaml +event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) +handler: handleTransferWithPool +calls: + ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) +``` + +The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. + +The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. + +Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. + +## Conclusion + +You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/vi/subgraphs/best-practices/derivedfrom.mdx b/website/src/pages/vi/subgraphs/best-practices/derivedfrom.mdx new file mode 100644 index 000000000000..db3a49928c89 --- /dev/null +++ b/website/src/pages/vi/subgraphs/best-practices/derivedfrom.mdx @@ -0,0 +1,89 @@ +--- +title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom +sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' +--- + +## TLDR + +Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. + +## How to Use the `@derivedFrom` Directive + +You just need to add a `@derivedFrom` directive after your array in your schema. Like this: + +```graphql +comments: [Comment!]! @derivedFrom(field: "post") +``` + +`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. + +### Example Use Case for `@derivedFrom` + +An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. + +Let’s start with our two entities, `Post` and `Comment` + +Without optimization, you could implement it like this with an array: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! +} + +type Comment @entity { + id: Bytes! + content: String! +} +``` + +Arrays like these will effectively store extra Comments data on the Post side of the relationship. + +Here’s what an optimized version looks like using `@derivedFrom`: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! @derivedFrom(field: "post") +} + +type Comment @entity { + id: Bytes! + content: String! + post: Post! +} +``` + +Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. + +This will not only make our subgraph more efficient, but it will also unlock three features: + +1. We can query the `Post` and see all of its comments. + +2. We can do a reverse lookup and query any `Comment` and see which post it comes from. + +3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. + +## Conclusion + +Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. + +For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/vi/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/vi/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/vi/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/vi/subgraphs/best-practices/grafting-hotfix.mdx index 3ebeea7bd352..6d941bcf9432 100644 --- a/website/src/pages/vi/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/vi/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/vi/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx b/website/src/pages/vi/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx new file mode 100644 index 000000000000..6ff60ec9ab34 --- /dev/null +++ b/website/src/pages/vi/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -0,0 +1,191 @@ +--- +title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs +sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' +--- + +## TLDR + +Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. + +## Immutable Entities + +To make an entity immutable, we simply add `(immutable: true)` to an entity. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. + +Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. + +### Under the hood + +Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. + +### When not to use Immutable Entities + +If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. + +## Bytes as IDs + +Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. + +### Reasons to Not Use Bytes as IDs + +1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. +2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. +3. Indexing and querying performance improvements are not desired. + +### Concatenating With Bytes as IDs + +It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. + +Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. + +```typescript +export function handleTransfer(event: TransferEvent): void { + let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) + entity.from = event.params.from + entity.to = event.params.to + entity.value = event.params.value + + entity.blockNumber = event.block.number + entity.blockTimestamp = event.block.timestamp + entity.transactionHash = event.transaction.hash + + entity.save() +} +``` + +### Sorting With Bytes as IDs + +Sorting using Bytes as IDs is not optimal as seen in this example query and response. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: id) { + id + from + to + value + } +} +``` + +Query response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x00010000", + "from": "0xabcd...", + "to": "0x1234...", + "value": "256" + }, + { + "id": "0x00020000", + "from": "0xefgh...", + "to": "0x5678...", + "value": "512" + }, + { + "id": "0x01000000", + "from": "0xijkl...", + "to": "0x9abc...", + "value": "1" + } + ] + } +} +``` + +The IDs are returned as hex. + +To improve sorting, we should create another field on the entity that is a BigInt. + +```graphql +type Transfer @entity { + id: Bytes! + from: Bytes! # address + to: Bytes! # address + value: BigInt! # unit256 + tokenId: BigInt! # uint256 +} +``` + +This will allow for sorting to be optimized sequentially. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: tokenId) { + id + tokenId + } +} +``` + +Query Response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x…", + "tokenId": "1" + }, + { + "id": "0x…", + "tokenId": "2" + }, + { + "id": "0x…", + "tokenId": "3" + } + ] + } +} +``` + +## Conclusion + +Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. + +Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/vi/subgraphs/best-practices/pruning.mdx b/website/src/pages/vi/subgraphs/best-practices/pruning.mdx new file mode 100644 index 000000000000..1b51dde8894f --- /dev/null +++ b/website/src/pages/vi/subgraphs/best-practices/pruning.mdx @@ -0,0 +1,56 @@ +--- +title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning +sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' +--- + +## TLDR + +[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. + +## How to Prune a Subgraph With `indexerHints` + +Add a section called `indexerHints` in the manifest. + +`indexerHints` has three `prune` options: + +- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. +- `prune: `: Sets a custom limit on the number of historical blocks to retain. +- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. + +We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: + +```yaml +specVersion: 1.0.0 +schema: + file: ./schema.graphql +indexerHints: + prune: auto +dataSources: + - kind: ethereum/contract + name: Contract + network: mainnet +``` + +## Important Considerations + +- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. + +- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). + +## Conclusion + +Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/vi/subgraphs/cookbook/timeseries.mdx b/website/src/pages/vi/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/vi/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/vi/subgraphs/best-practices/timeseries.mdx index 0b46b363c64f..f1b15a258169 100644 --- a/website/src/pages/vi/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/vi/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/vi/subgraphs/cookbook/_meta.js b/website/src/pages/vi/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/vi/subgraphs/cookbook/_meta.js +++ b/website/src/pages/vi/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/vi/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/vi/subgraphs/cookbook/avoid-eth-calls.mdx deleted file mode 100644 index ae29cdf03a34..000000000000 --- a/website/src/pages/vi/subgraphs/cookbook/avoid-eth-calls.mdx +++ /dev/null @@ -1,117 +0,0 @@ ---- -title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls -sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' ---- - -## TLDR - -`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. - -## Why Avoiding `eth_calls` Is a Best Practice - -Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. - -### What Does an eth_call Look Like? - -`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: - -```yaml -event Transfer(address indexed from, address indexed to, uint256 value); -``` - -Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, Transfer } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransfer(event: Transfer): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - // Bind the ERC20 contract instance to the given address: - let instance = ERC20.bind(event.address) - - // Retrieve pool information via eth_call - let poolInfo = instance.getPoolInfo(event.params.to) - - transaction.pool = poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is functional, however is not ideal as it slows down our subgraph’s indexing. - -## How to Eliminate `eth_calls` - -Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: - -``` -event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); -``` - -With this update, the subgraph can directly index the required data without external calls: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransferWithPool(event: TransferWithPool): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - transaction.pool = event.params.poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is much more performant as it has eliminated the need for `eth_calls`. - -## How to Optimize `eth_calls` - -If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. - -## Reducing the Runtime Overhead of `eth_calls` - -For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. - -Currently, `eth_calls` can only be declared for event handlers. In the manifest, write - -```yaml -event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) -handler: handleTransferWithPool -calls: - ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) -``` - -The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. - -The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. - -Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. - -## Conclusion - -You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/vi/subgraphs/cookbook/cosmos.mdx b/website/src/pages/vi/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 1d68d3cdf7f0..000000000000 --- a/website/src/pages/vi/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: Building Subgraphs on Cosmos ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## What are Cosmos subgraphs? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -There are four types of handlers supported in Cosmos subgraphs: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -Even though all data can be accessed with a block handler, other handlers enable subgraph developers to process data in a much more granular way. - -## Building a Cosmos subgraph - -### Subgraph Dependencies - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### Subgraph Main Components - -There are three key parts when it comes to defining a subgraph: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### Subgraph Manifest Definition - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### Schema Definition - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript Mappings - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Each handler type comes with its own data structure that is passed as an argument to a mapping function. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### Message decoding - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## Creating and building a Cosmos subgraph - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Deploying a Cosmos subgraph - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Querying a Cosmos subgraph - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Supported Cosmos Blockchains - -### Cosmos Hub - -#### What is Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### Các Mạng - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### What is Osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### Các Mạng - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## Example Subgraphs - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/vi/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/vi/subgraphs/cookbook/derivedfrom.mdx deleted file mode 100644 index a0942645c999..000000000000 --- a/website/src/pages/vi/subgraphs/cookbook/derivedfrom.mdx +++ /dev/null @@ -1,89 +0,0 @@ ---- -title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom -sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' ---- - -## TLDR - -Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. - -## How to Use the `@derivedFrom` Directive - -You just need to add a `@derivedFrom` directive after your array in your schema. Like this: - -```graphql -comments: [Comment!]! @derivedFrom(field: "post") -``` - -`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. - -### Example Use Case for `@derivedFrom` - -An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. - -Let’s start with our two entities, `Post` and `Comment` - -Without optimization, you could implement it like this with an array: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! -} - -type Comment @entity { - id: Bytes! - content: String! -} -``` - -Arrays like these will effectively store extra Comments data on the Post side of the relationship. - -Here’s what an optimized version looks like using `@derivedFrom`: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! @derivedFrom(field: "post") -} - -type Comment @entity { - id: Bytes! - content: String! - post: Post! -} -``` - -Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. - -This will not only make our subgraph more efficient, but it will also unlock three features: - -1. We can query the `Post` and see all of its comments. - -2. We can do a reverse lookup and query any `Comment` and see which post it comes from. - -3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. - -## Conclusion - -Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. - -For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/vi/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/vi/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx deleted file mode 100644 index 511565bb3dd4..000000000000 --- a/website/src/pages/vi/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ /dev/null @@ -1,191 +0,0 @@ ---- -title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs -sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' ---- - -## TLDR - -Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. - -## Immutable Entities - -To make an entity immutable, we simply add `(immutable: true)` to an entity. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. - -Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. - -### Under the hood - -Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. - -### When not to use Immutable Entities - -If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. - -## Bytes as IDs - -Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. - -### Reasons to Not Use Bytes as IDs - -1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. -2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. -3. Indexing and querying performance improvements are not desired. - -### Concatenating With Bytes as IDs - -It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. - -Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. - -```typescript -export function handleTransfer(event: TransferEvent): void { - let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) - entity.from = event.params.from - entity.to = event.params.to - entity.value = event.params.value - - entity.blockNumber = event.block.number - entity.blockTimestamp = event.block.timestamp - entity.transactionHash = event.transaction.hash - - entity.save() -} -``` - -### Sorting With Bytes as IDs - -Sorting using Bytes as IDs is not optimal as seen in this example query and response. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: id) { - id - from - to - value - } -} -``` - -Query response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x00010000", - "from": "0xabcd...", - "to": "0x1234...", - "value": "256" - }, - { - "id": "0x00020000", - "from": "0xefgh...", - "to": "0x5678...", - "value": "512" - }, - { - "id": "0x01000000", - "from": "0xijkl...", - "to": "0x9abc...", - "value": "1" - } - ] - } -} -``` - -The IDs are returned as hex. - -To improve sorting, we should create another field on the entity that is a BigInt. - -```graphql -type Transfer @entity { - id: Bytes! - from: Bytes! # address - to: Bytes! # address - value: BigInt! # unit256 - tokenId: BigInt! # uint256 -} -``` - -This will allow for sorting to be optimized sequentially. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: tokenId) { - id - tokenId - } -} -``` - -Query Response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x…", - "tokenId": "1" - }, - { - "id": "0x…", - "tokenId": "2" - }, - { - "id": "0x…", - "tokenId": "3" - } - ] - } -} -``` - -## Conclusion - -Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. - -Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/vi/subgraphs/cookbook/pruning.mdx b/website/src/pages/vi/subgraphs/cookbook/pruning.mdx deleted file mode 100644 index e212d5d02bc9..000000000000 --- a/website/src/pages/vi/subgraphs/cookbook/pruning.mdx +++ /dev/null @@ -1,56 +0,0 @@ ---- -title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning -sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' ---- - -## TLDR - -[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. - -## How to Prune a Subgraph With `indexerHints` - -Add a section called `indexerHints` in the manifest. - -`indexerHints` has three `prune` options: - -- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. -- `prune: `: Sets a custom limit on the number of historical blocks to retain. -- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. - -We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: - -```yaml -specVersion: 1.0.0 -schema: - file: ./schema.graphql -indexerHints: - prune: auto -dataSources: - - kind: ethereum/contract - name: Contract - network: mainnet -``` - -## Important Considerations - -- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. - -- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). - -## Conclusion - -Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/vi/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/vi/subgraphs/developing/creating/graph-ts/api.mdx index 90ecae61db48..7fea4f954429 100644 --- a/website/src/pages/vi/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/vi/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ The `apiVersion` in the subgraph manifest specifies the mapping API version whic | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | Added `TransactionReceipt` and `Log` classes to the Ethereum types
Added `receipt` field to the Ethereum Event object | | 0.0.6 | Added `nonce` field to the Ethereum Transaction object
Added `baseFeePerGas` to the Ethereum Block object | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | Added `functionSignature` field to the Ethereum SmartContractCall object | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | Added `input` field to the Ethereum Transaction object | diff --git a/website/src/pages/vi/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/vi/subgraphs/developing/creating/install-the-cli.mdx index d79f714cf51a..ab11aa3306cb 100644 --- a/website/src/pages/vi/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/vi/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: Cài đặt Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## Tổng quan diff --git a/website/src/pages/vi/subgraphs/developing/deploying/_meta.js b/website/src/pages/vi/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/vi/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/vi/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/vi/subgraphs/querying/best-practices.mdx b/website/src/pages/vi/subgraphs/querying/best-practices.mdx index 3736fa32faeb..ff5f381e2993 100644 --- a/website/src/pages/vi/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/vi/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### Sending a query to a GraphQL API diff --git a/website/src/pages/vi/subgraphs/querying/managing-api-keys.mdx b/website/src/pages/vi/subgraphs/querying/managing-api-keys.mdx index 7798f96071eb..7475b0910885 100644 --- a/website/src/pages/vi/subgraphs/querying/managing-api-keys.mdx +++ b/website/src/pages/vi/subgraphs/querying/managing-api-keys.mdx @@ -1,5 +1,5 @@ --- -title: Managing your API keys +title: Managing API keys --- ## Tổng quan diff --git a/website/src/pages/vi/substreams/developing/sinks/sinks.mdx b/website/src/pages/vi/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/vi/substreams/developing/sinks/sinks.mdx rename to website/src/pages/vi/substreams/developing/sinks.mdx diff --git a/website/src/pages/vi/substreams/developing/sinks/_meta.js b/website/src/pages/vi/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/vi/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/vi/substreams/quick-start.mdx b/website/src/pages/vi/substreams/quick-start.mdx index 54bec3379bc6..bca91aa19452 100644 --- a/website/src/pages/vi/substreams/quick-start.mdx +++ b/website/src/pages/vi/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: diff --git a/website/src/pages/zh/resources/_meta-titles.json b/website/src/pages/zh/resources/_meta-titles.json index 8ac14af7627a..f5971e95a8f6 100644 --- a/website/src/pages/zh/resources/_meta-titles.json +++ b/website/src/pages/zh/resources/_meta-titles.json @@ -1,4 +1,4 @@ { "roles": "Additional Roles", - "release-notes": "Release Notes & Upgrade Guides" + "migration-guides": "Migration Guides" } diff --git a/website/src/pages/zh/resources/_meta.js b/website/src/pages/zh/resources/_meta.js index 3c0862ea1859..66cf79a52b51 100644 --- a/website/src/pages/zh/resources/_meta.js +++ b/website/src/pages/zh/resources/_meta.js @@ -5,5 +5,6 @@ export default { tokenomics: '', benefits: '', roles: titles.roles, - 'release-notes': titles['release-notes'], + 'migration-guides': titles['migration-guides'], + 'subgraph-studio-faq': '', } diff --git a/website/src/pages/zh/resources/release-notes/_meta.js b/website/src/pages/zh/resources/migration-guides/_meta.js similarity index 100% rename from website/src/pages/zh/resources/release-notes/_meta.js rename to website/src/pages/zh/resources/migration-guides/_meta.js diff --git a/website/src/pages/zh/resources/release-notes/assemblyscript-migration-guide.mdx b/website/src/pages/zh/resources/migration-guides/assemblyscript-migration-guide.mdx similarity index 100% rename from website/src/pages/zh/resources/release-notes/assemblyscript-migration-guide.mdx rename to website/src/pages/zh/resources/migration-guides/assemblyscript-migration-guide.mdx diff --git a/website/src/pages/zh/resources/release-notes/graphql-validations-migration-guide.mdx b/website/src/pages/zh/resources/migration-guides/graphql-validations-migration-guide.mdx similarity index 100% rename from website/src/pages/zh/resources/release-notes/graphql-validations-migration-guide.mdx rename to website/src/pages/zh/resources/migration-guides/graphql-validations-migration-guide.mdx diff --git a/website/src/pages/zh/subgraphs/developing/deploying/subgraph-studio-faq.mdx b/website/src/pages/zh/resources/subgraph-studio-faq.mdx similarity index 100% rename from website/src/pages/zh/subgraphs/developing/deploying/subgraph-studio-faq.mdx rename to website/src/pages/zh/resources/subgraph-studio-faq.mdx diff --git a/website/src/pages/zh/sps/sps-faq.mdx b/website/src/pages/zh/sps/sps-faq.mdx index ac9facf7b0c4..aa4938a88621 100644 --- a/website/src/pages/zh/sps/sps-faq.mdx +++ b/website/src/pages/zh/sps/sps-faq.mdx @@ -7,7 +7,7 @@ sidebarTitle: FAQ Substreams is an exceptionally powerful processing engine capable of consuming rich streams of blockchain data. It allows you to refine and shape blockchain data for fast and seamless digestion by end-user applications. -Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/sinks/) their data anywhere. +Specifically, it's a blockchain-agnostic, parallelized, and streaming-first engine that serves as a blockchain data transformation layer. It's powered by [Firehose](https://firehose.streamingfast.io/), and enables developers to write Rust modules, build upon community modules, provide extremely high-performance indexing, and [sink](/substreams/developing/sinks/) their data anywhere. Substreams is developed by [StreamingFast](https://www.streamingfast.io/). Visit the [Substreams Documentation](/substreams/introduction/) to learn more about Substreams. diff --git a/website/src/pages/zh/subgraphs/_meta-titles.json b/website/src/pages/zh/subgraphs/_meta-titles.json index 15d4bb5577b5..0556abfc236c 100644 --- a/website/src/pages/zh/subgraphs/_meta-titles.json +++ b/website/src/pages/zh/subgraphs/_meta-titles.json @@ -1,5 +1,6 @@ { "querying": "Querying", "developing": "Developing", - "cookbook": "Cookbook" + "cookbook": "Cookbook", + "best-practices": "Best Practices" } diff --git a/website/src/pages/zh/subgraphs/_meta.js b/website/src/pages/zh/subgraphs/_meta.js index cdea2804a3da..3b490f214d14 100644 --- a/website/src/pages/zh/subgraphs/_meta.js +++ b/website/src/pages/zh/subgraphs/_meta.js @@ -7,4 +7,5 @@ export default { developing: titles.developing, billing: '', cookbook: titles.cookbook, + 'best-practices': titles['best-practices'], } diff --git a/website/src/pages/zh/subgraphs/best-practices/_meta.js b/website/src/pages/zh/subgraphs/best-practices/_meta.js new file mode 100644 index 000000000000..fab0571f4d0c --- /dev/null +++ b/website/src/pages/zh/subgraphs/best-practices/_meta.js @@ -0,0 +1,8 @@ +export default { + pruning: '', + derivedfrom: '', + 'immutable-entities-bytes-as-ids': '', + 'avoid-eth-calls': '', + timeseries: '', + 'grafting-hotfix': '', +} diff --git a/website/src/pages/zh/subgraphs/best-practices/avoid-eth-calls.mdx b/website/src/pages/zh/subgraphs/best-practices/avoid-eth-calls.mdx new file mode 100644 index 000000000000..e40a7b3712e4 --- /dev/null +++ b/website/src/pages/zh/subgraphs/best-practices/avoid-eth-calls.mdx @@ -0,0 +1,117 @@ +--- +title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls +sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' +--- + +## TLDR + +`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. + +## Why Avoiding `eth_calls` Is a Best Practice + +Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. + +### What Does an eth_call Look Like? + +`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: + +```yaml +event Transfer(address indexed from, address indexed to, uint256 value); +``` + +Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, Transfer } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransfer(event: Transfer): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + // Bind the ERC20 contract instance to the given address: + let instance = ERC20.bind(event.address) + + // Retrieve pool information via eth_call + let poolInfo = instance.getPoolInfo(event.params.to) + + transaction.pool = poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is functional, however is not ideal as it slows down our subgraph’s indexing. + +## How to Eliminate `eth_calls` + +Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: + +``` +event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); +``` + +With this update, the subgraph can directly index the required data without external calls: + +```typescript +import { Address } from '@graphprotocol/graph-ts' +import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' +import { TokenTransaction } from '../generated/schema' + +export function handleTransferWithPool(event: TransferWithPool): void { + let transaction = new TokenTransaction(event.transaction.hash.toHex()) + + transaction.pool = event.params.poolInfo.toHexString() + transaction.from = event.params.from.toHexString() + transaction.to = event.params.to.toHexString() + transaction.value = event.params.value + + transaction.save() +} +``` + +This is much more performant as it has eliminated the need for `eth_calls`. + +## How to Optimize `eth_calls` + +If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. + +## Reducing the Runtime Overhead of `eth_calls` + +For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. + +Currently, `eth_calls` can only be declared for event handlers. In the manifest, write + +```yaml +event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) +handler: handleTransferWithPool +calls: + ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) +``` + +The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. + +The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. + +Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. + +## Conclusion + +You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/zh/subgraphs/best-practices/derivedfrom.mdx b/website/src/pages/zh/subgraphs/best-practices/derivedfrom.mdx new file mode 100644 index 000000000000..db3a49928c89 --- /dev/null +++ b/website/src/pages/zh/subgraphs/best-practices/derivedfrom.mdx @@ -0,0 +1,89 @@ +--- +title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom +sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' +--- + +## TLDR + +Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. + +## How to Use the `@derivedFrom` Directive + +You just need to add a `@derivedFrom` directive after your array in your schema. Like this: + +```graphql +comments: [Comment!]! @derivedFrom(field: "post") +``` + +`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. + +### Example Use Case for `@derivedFrom` + +An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. + +Let’s start with our two entities, `Post` and `Comment` + +Without optimization, you could implement it like this with an array: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! +} + +type Comment @entity { + id: Bytes! + content: String! +} +``` + +Arrays like these will effectively store extra Comments data on the Post side of the relationship. + +Here’s what an optimized version looks like using `@derivedFrom`: + +```graphql +type Post @entity { + id: Bytes! + title: String! + content: String! + comments: [Comment!]! @derivedFrom(field: "post") +} + +type Comment @entity { + id: Bytes! + content: String! + post: Post! +} +``` + +Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. + +This will not only make our subgraph more efficient, but it will also unlock three features: + +1. We can query the `Post` and see all of its comments. + +2. We can do a reverse lookup and query any `Comment` and see which post it comes from. + +3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. + +## Conclusion + +Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. + +For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/zh/subgraphs/cookbook/grafting-hotfix.mdx b/website/src/pages/zh/subgraphs/best-practices/grafting-hotfix.mdx similarity index 95% rename from website/src/pages/zh/subgraphs/cookbook/grafting-hotfix.mdx rename to website/src/pages/zh/subgraphs/best-practices/grafting-hotfix.mdx index 00dcdcd3caca..06f1b9fef399 100644 --- a/website/src/pages/zh/subgraphs/cookbook/grafting-hotfix.mdx +++ b/website/src/pages/zh/subgraphs/best-practices/grafting-hotfix.mdx @@ -174,14 +174,14 @@ By incorporating grafting into your subgraph development workflow, you can enhan ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/zh/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx b/website/src/pages/zh/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx new file mode 100644 index 000000000000..6ff60ec9ab34 --- /dev/null +++ b/website/src/pages/zh/subgraphs/best-practices/immutable-entities-bytes-as-ids.mdx @@ -0,0 +1,191 @@ +--- +title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs +sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' +--- + +## TLDR + +Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. + +## Immutable Entities + +To make an entity immutable, we simply add `(immutable: true)` to an entity. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. + +Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. + +### Under the hood + +Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. + +### When not to use Immutable Entities + +If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. + +## Bytes as IDs + +Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. + +```graphql +type Transfer @entity(immutable: true) { + id: Bytes! + from: Bytes! + to: Bytes! + value: BigInt! +} +``` + +While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. + +### Reasons to Not Use Bytes as IDs + +1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. +2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. +3. Indexing and querying performance improvements are not desired. + +### Concatenating With Bytes as IDs + +It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. + +Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. + +```typescript +export function handleTransfer(event: TransferEvent): void { + let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) + entity.from = event.params.from + entity.to = event.params.to + entity.value = event.params.value + + entity.blockNumber = event.block.number + entity.blockTimestamp = event.block.timestamp + entity.transactionHash = event.transaction.hash + + entity.save() +} +``` + +### Sorting With Bytes as IDs + +Sorting using Bytes as IDs is not optimal as seen in this example query and response. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: id) { + id + from + to + value + } +} +``` + +Query response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x00010000", + "from": "0xabcd...", + "to": "0x1234...", + "value": "256" + }, + { + "id": "0x00020000", + "from": "0xefgh...", + "to": "0x5678...", + "value": "512" + }, + { + "id": "0x01000000", + "from": "0xijkl...", + "to": "0x9abc...", + "value": "1" + } + ] + } +} +``` + +The IDs are returned as hex. + +To improve sorting, we should create another field on the entity that is a BigInt. + +```graphql +type Transfer @entity { + id: Bytes! + from: Bytes! # address + to: Bytes! # address + value: BigInt! # unit256 + tokenId: BigInt! # uint256 +} +``` + +This will allow for sorting to be optimized sequentially. + +Query: + +```graphql +{ + transfers(first: 3, orderBy: tokenId) { + id + tokenId + } +} +``` + +Query Response: + +```json +{ + "data": { + "transfers": [ + { + "id": "0x…", + "tokenId": "1" + }, + { + "id": "0x…", + "tokenId": "2" + }, + { + "id": "0x…", + "tokenId": "3" + } + ] + } +} +``` + +## Conclusion + +Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. + +Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/zh/subgraphs/best-practices/pruning.mdx b/website/src/pages/zh/subgraphs/best-practices/pruning.mdx new file mode 100644 index 000000000000..1b51dde8894f --- /dev/null +++ b/website/src/pages/zh/subgraphs/best-practices/pruning.mdx @@ -0,0 +1,56 @@ +--- +title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning +sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' +--- + +## TLDR + +[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. + +## How to Prune a Subgraph With `indexerHints` + +Add a section called `indexerHints` in the manifest. + +`indexerHints` has three `prune` options: + +- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. +- `prune: `: Sets a custom limit on the number of historical blocks to retain. +- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. + +We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: + +```yaml +specVersion: 1.0.0 +schema: + file: ./schema.graphql +indexerHints: + prune: auto +dataSources: + - kind: ethereum/contract + name: Contract + network: mainnet +``` + +## Important Considerations + +- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. + +- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). + +## Conclusion + +Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. + +## Subgraph Best Practices 1-6 + +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) + +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) + +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) + +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) + +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) + +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/zh/subgraphs/cookbook/timeseries.mdx b/website/src/pages/zh/subgraphs/best-practices/timeseries.mdx similarity index 93% rename from website/src/pages/zh/subgraphs/cookbook/timeseries.mdx rename to website/src/pages/zh/subgraphs/best-practices/timeseries.mdx index a402f407abeb..2197763ae9f0 100644 --- a/website/src/pages/zh/subgraphs/cookbook/timeseries.mdx +++ b/website/src/pages/zh/subgraphs/best-practices/timeseries.mdx @@ -182,14 +182,14 @@ By adopting this pattern, developers can build more efficient and scalable subgr ## Subgraph Best Practices 1-6 -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) +1. [Improve Query Speed with Subgraph Pruning](/subgraphs/best-practices/pruning/) -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) +2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/best-practices/derivedfrom/) -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) +3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/best-practices/immutable-entities-bytes-as-ids/) -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) +4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/best-practices/avoid-eth-calls/) -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) +5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/best-practices/timeseries/) -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) +6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/best-practices/grafting-hotfix/) diff --git a/website/src/pages/zh/subgraphs/cookbook/_meta.js b/website/src/pages/zh/subgraphs/cookbook/_meta.js index 66c172da5ef0..e642f12ef11d 100644 --- a/website/src/pages/zh/subgraphs/cookbook/_meta.js +++ b/website/src/pages/zh/subgraphs/cookbook/_meta.js @@ -1,17 +1,10 @@ export default { 'subgraph-debug-forking': '', near: '', - cosmos: '', arweave: '', grafting: '', 'subgraph-uncrashable': '', 'transfer-to-the-graph': '', - pruning: '', - derivedfrom: '', - 'immutable-entities-bytes-as-ids': '', - 'avoid-eth-calls': '', - timeseries: '', - 'grafting-hotfix': '', enums: '', 'secure-api-keys-nextjs': '', polymarket: '', diff --git a/website/src/pages/zh/subgraphs/cookbook/avoid-eth-calls.mdx b/website/src/pages/zh/subgraphs/cookbook/avoid-eth-calls.mdx deleted file mode 100644 index ae29cdf03a34..000000000000 --- a/website/src/pages/zh/subgraphs/cookbook/avoid-eth-calls.mdx +++ /dev/null @@ -1,117 +0,0 @@ ---- -title: Subgraph Best Practice 4 - Improve Indexing Speed by Avoiding eth_calls -sidebarTitle: 'Subgraph Best Practice 4: Avoiding eth_calls' ---- - -## TLDR - -`eth_calls` are calls that can be made from a subgraph to an Ethereum node. These calls take a significant amount of time to return data, slowing down indexing. If possible, design smart contracts to emit all the data you need so you don’t need to use `eth_calls`. - -## Why Avoiding `eth_calls` Is a Best Practice - -Subgraphs are optimized to index event data emitted from smart contracts. A subgraph can also index the data coming from an `eth_call`, however, this can significantly slow down subgraph indexing as `eth_calls` require making external calls to smart contracts. The responsiveness of these calls relies not on the subgraph but on the connectivity and responsiveness of the Ethereum node being queried. By minimizing or eliminating eth_calls in our subgraphs, we can significantly improve our indexing speed. - -### What Does an eth_call Look Like? - -`eth_calls` are often necessary when the data required for a subgraph is not available through emitted events. For example, consider a scenario where a subgraph needs to identify whether ERC20 tokens are part of a specific pool, but the contract only emits a basic `Transfer` event and does not emit an event that contains the data that we need: - -```yaml -event Transfer(address indexed from, address indexed to, uint256 value); -``` - -Suppose the tokens' pool membership is determined by a state variable named `getPoolInfo`. In this case, we would need to use an `eth_call` to query this data: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, Transfer } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransfer(event: Transfer): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - // Bind the ERC20 contract instance to the given address: - let instance = ERC20.bind(event.address) - - // Retrieve pool information via eth_call - let poolInfo = instance.getPoolInfo(event.params.to) - - transaction.pool = poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is functional, however is not ideal as it slows down our subgraph’s indexing. - -## How to Eliminate `eth_calls` - -Ideally, the smart contract should be updated to emit all necessary data within events. For instance, modifying the smart contract to include pool information in the event could eliminate the need for `eth_calls`: - -``` -event TransferWithPool(address indexed from, address indexed to, uint256 value, bytes32 indexed poolInfo); -``` - -With this update, the subgraph can directly index the required data without external calls: - -```typescript -import { Address } from '@graphprotocol/graph-ts' -import { ERC20, TransferWithPool } from '../generated/ERC20/ERC20' -import { TokenTransaction } from '../generated/schema' - -export function handleTransferWithPool(event: TransferWithPool): void { - let transaction = new TokenTransaction(event.transaction.hash.toHex()) - - transaction.pool = event.params.poolInfo.toHexString() - transaction.from = event.params.from.toHexString() - transaction.to = event.params.to.toHexString() - transaction.value = event.params.value - - transaction.save() -} -``` - -This is much more performant as it has eliminated the need for `eth_calls`. - -## How to Optimize `eth_calls` - -If modifying the smart contract is not possible and `eth_calls` are required, read “[Improve Subgraph Indexing Performance Easily: Reduce eth_calls](https://thegraph.com/blog/improve-subgraph-performance-reduce-eth-calls/)” by Simon Emanuel Schmid to learn various strategies on how to optimize `eth_calls`. - -## Reducing the Runtime Overhead of `eth_calls` - -For the `eth_calls` that can not be eliminated, the runtime overhead they introduce can be minimized by declaring them in the manifest. When `graph-node` processes a block it performs all declared `eth_calls` in parallel before handlers are run. Calls that are not declared are executed sequentially when handlers run. The runtime improvement comes from performing calls in parallel rather than sequentially - that helps reduce the total time spent in calls but does not eliminate it completely. - -Currently, `eth_calls` can only be declared for event handlers. In the manifest, write - -```yaml -event: TransferWithPool(address indexed, address indexed, uint256, bytes32 indexed) -handler: handleTransferWithPool -calls: - ERC20.poolInfo: ERC20[event.address].getPoolInfo(event.params.to) -``` - -The portion highlighted in yellow is the call declaration. The part before the colon is simply a text label that is only used for error messages. The part after the colon has the form `Contract[address].function(params)`. Permissible values for address and params are `event.address` and `event.params.`. - -The handler itself accesses the result of this `eth_call` exactly as in the previous section by binding to the contract and making the call. graph-node caches the results of declared `eth_calls` in memory and the call from the handler will retrieve the result from this in memory cache instead of making an actual RPC call. - -Note: Declared eth_calls can only be made in subgraphs with specVersion >= 1.2.0. - -## Conclusion - -You can significantly improve indexing performance by minimizing or eliminating `eth_calls` in your subgraphs. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/zh/subgraphs/cookbook/cosmos.mdx b/website/src/pages/zh/subgraphs/cookbook/cosmos.mdx deleted file mode 100644 index 3958b67df717..000000000000 --- a/website/src/pages/zh/subgraphs/cookbook/cosmos.mdx +++ /dev/null @@ -1,257 +0,0 @@ ---- -title: 在 Cosmos上构建子图 ---- - -This guide is an introduction on building subgraphs indexing [Cosmos](https://cosmos.network/) based blockchains. - -## Cosmos 子图是什么? - -The Graph allows developers to process blockchain events and make the resulting data easily available via an open GraphQL API, known as a subgraph. [Graph Node](https://github.com/graphprotocol/graph-node) is now able to process Cosmos events, which means Cosmos developers can now build subgraphs to easily index onchain events. - -Cosmos 子图目前支持四种类型的处理程序: - -- **Block handlers** run whenever a new block is appended to the chain. -- **Event handlers** run when a specific event is emitted. -- **Transaction handlers** run when a transaction occurs. -- **Message handlers** run when a specific message occurs. - -Based on the [official Cosmos documentation](https://docs.cosmos.network/): - -> [Events](https://docs.cosmos.network/main/learn/advanced/events) are objects that contain information about the execution of the application. They are mainly used by service providers like block explorers and wallets to track the execution of various messages and index transactions. -> -> [Transactions](https://docs.cosmos.network/main/learn/advanced/transactions) are objects created by end-users to trigger state changes in the application. -> -> [Messages](https://docs.cosmos.network/main/learn/advanced/transactions#messages) are module-specific objects that trigger state transitions within the scope of the module they belong to. - -尽管所有数据都可以通过区块处理程序访问,但其他处理程序使子图开发人员能够以更细粒度的方式处理数据。 - -## 构建 Cosmos 子图 - -### 子图依赖关系 - -[graph-cli](https://github.com/graphprotocol/graph-tooling/tree/main/packages/cli) is a CLI tool to build and deploy subgraphs, version `>=0.30.0` is required in order to work with Cosmos subgraphs. - -[graph-ts](https://github.com/graphprotocol/graph-tooling/tree/main/packages/ts) is a library of subgraph-specific types, version `>=0.27.0` is required in order to work with Cosmos subgraphs. - -### 子图的主要组成部分 - -定义子图有三个关键部分: - -**subgraph.yaml**: a YAML file containing the subgraph manifest, which identifies which events to track and how to process them. - -**schema.graphql**: a GraphQL schema that defines what data is stored for your subgraph, and how to query it via GraphQL. - -**AssemblyScript Mappings**: [AssemblyScript](https://github.com/AssemblyScript/assemblyscript) code that translates from blockchain data to the entities defined in your schema. - -### 子图清单定义 - -The subgraph manifest (`subgraph.yaml`) identifies the data sources for the subgraph, the triggers of interest, and the functions (`handlers`) that should be run in response to those triggers. See below for an example subgraph manifest for a Cosmos subgraph: - -```yaml -specVersion: 0.0.5 -description: Cosmos Subgraph Example -schema: - file: ./schema.graphql # link to the schema file -dataSources: - - kind: cosmos - name: CosmosHub - network: cosmoshub-4 # This will change for each cosmos-based blockchain. In this case, the example uses the Cosmos Hub mainnet. - source: - startBlock: 0 # Required for Cosmos, set this to 0 to start indexing from chain genesis - mapping: - apiVersion: 0.0.7 - language: wasm/assemblyscript - blockHandlers: - - handler: handleNewBlock # the function name in the mapping file - eventHandlers: - - event: rewards # the type of the event that will be handled - handler: handleReward # the function name in the mapping file - transactionHandlers: - - handler: handleTransaction # the function name in the mapping file - messageHandlers: - - message: /cosmos.staking.v1beta1.MsgDelegate # the type of a message - handler: handleMsgDelegate # the function name in the mapping file - file: ./src/mapping.ts # link to the file with the Assemblyscript mappings -``` - -- Cosmos subgraphs introduce a new `kind` of data source (`cosmos`). -- The `network` should correspond to a chain in the Cosmos ecosystem. In the example, the Cosmos Hub mainnet is used. - -### 模式定义 - -Schema definition describes the structure of the resulting subgraph database and the relationships between entities. This is agnostic of the original data source. There are more details on subgraph schema definition [here](/developing/creating-a-subgraph/#the-graphql-schema). - -### AssemblyScript 映射 - -The handlers for processing events are written in [AssemblyScript](https://www.assemblyscript.org/). - -Cosmos indexing introduces Cosmos-specific data types to the [AssemblyScript API](/subgraphs/developing/creating/graph-ts/api/). - -```tsx -class Block { - header: Header - evidence: EvidenceList - resultBeginBlock: ResponseBeginBlock - resultEndBlock: ResponseEndBlock - transactions: Array - validatorUpdates: Array -} - -class EventData { - event: Event - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionData { - tx: TxResult - block: HeaderOnlyBlock -} - -class MessageData { - message: Any - block: HeaderOnlyBlock - tx: TransactionContext -} - -class TransactionContext { - hash: Bytes - index: u32 - code: u32 - gasWanted: i64 - gasUsed: i64 -} - -class HeaderOnlyBlock { - header: Header -} - -class Header { - version: Consensus - chainId: string - height: u64 - time: Timestamp - lastBlockId: BlockID - lastCommitHash: Bytes - dataHash: Bytes - validatorsHash: Bytes - nextValidatorsHash: Bytes - consensusHash: Bytes - appHash: Bytes - lastResultsHash: Bytes - evidenceHash: Bytes - proposerAddress: Bytes - hash: Bytes -} - -class TxResult { - height: u64 - index: u32 - tx: Tx - result: ResponseDeliverTx - hash: Bytes -} - -class Event { - eventType: string - attributes: Array -} - -class Any { - typeUrl: string - value: Bytes -} -``` - -Each handler type comes with its own data structure that is passed as an argument to a mapping function. - -- Block handlers receive the `Block` type. -- Event handlers receive the `EventData` type. -- Transaction handlers receive the `TransactionData` type. -- Message handlers receive the `MessageData` type. - -As a part of `MessageData` the message handler receives a transaction context, which contains the most important information about a transaction that encompasses a message. The transaction context is also available in the `EventData` type, but only when the corresponding event is associated with a transaction. Additionally, all handlers receive a reference to a block (`HeaderOnlyBlock`). - -You can find the full list of types for the Cosmos integration [here](https://github.com/graphprotocol/graph-ts/blob/4c064a8118dff43b110de22c7756e5d47fcbc8df/chain/cosmos.ts). - -### 消息解码 - -It's important to note that Cosmos messages are chain-specific and they are passed to a subgraph in the form of a serialized [Protocol Buffers](https://protobuf.dev/) payload. As a result, the message data needs to be decoded in a mapping function before it can be processed. - -An example of how to decode message data in a subgraph can be found [here](https://github.com/graphprotocol/graph-tooling/blob/main/examples/cosmos-validator-delegations/src/decoding.ts). - -## 创建和构建 Cosmos 子图 - -The first step before starting to write the subgraph mappings is to generate the type bindings based on the entities that have been defined in the subgraph schema file (`schema.graphql`). This will allow the mapping functions to create new objects of those types and save them to the store. This is done by using the `codegen` CLI command: - -```bash -$ graph codegen -``` - -Once the mappings are ready, the subgraph needs to be built. This step will highlight any errors the manifest or the mappings might have. A subgraph needs to build successfully in order to be deployed to the Graph Node. It can be done using the `build` CLI command: - -```bash -$ graph build -``` - -## Deploying a Cosmos subgraph - -Once your subgraph has been created, you can deploy your subgraph by using the `graph deploy` CLI command: - -**Subgraph Studio** - -Visit the Subgraph Studio to create a new subgraph. - -```bash -graph deploy subgraph-name -``` - -**Local Graph Node (based on default configuration):** - -```bash -graph create subgraph-name --node http://localhost:8020 -``` - -```bash -graph deploy subgraph-name --node http://localhost:8020/ --ipfs http://localhost:5001 -``` - -## Querying a Cosmos subgraph - -The GraphQL endpoint for Cosmos subgraphs is determined by the schema definition, with the existing API interface. Please visit the [GraphQL API documentation](/subgraphs/querying/graphql-api/) for more information. - -## Supported Cosmos Blockchains - -### Cosmos Hub - -#### What is Cosmos Hub? - -The [Cosmos Hub blockchain](https://hub.cosmos.network/) is the first blockchain in the [Cosmos](https://cosmos.network/) ecosystem. You can visit the [official documentation](https://docs.cosmos.network/) for more information. - -#### 网络 - -Cosmos Hub mainnet is `cosmoshub-4`. Cosmos Hub current testnet is `theta-testnet-001`.
Other Cosmos Hub networks, i.e. `cosmoshub-3`, are halted, therefore no data is provided for them. - -### Osmosis - -> Osmosis support in Graph Node and on Subgraph Studio is in beta: please contact the graph team with any questions about building Osmosis subgraphs! - -#### What is Osmosis? - -[Osmosis](https://osmosis.zone/) is a decentralized, cross-chain automated market maker (AMM) protocol built on top of the Cosmos SDK. It allows users to create custom liquidity pools and trade IBC-enabled tokens. You can visit the [official documentation](https://docs.osmosis.zone/) for more information. - -#### 网络 - -Osmosis mainnet is `osmosis-1`. Osmosis current testnet is `osmo-test-4`. - -## 示例子图 - -Here are some example subgraphs for reference: - -[Block Filtering Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-block-filtering) - -[Validator Rewards Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-rewards) - -[Validator Delegations Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-validator-delegations) - -[Osmosis Token Swaps Example](https://github.com/graphprotocol/graph-tooling/tree/main/examples/cosmos-osmosis-token-swaps) diff --git a/website/src/pages/zh/subgraphs/cookbook/derivedfrom.mdx b/website/src/pages/zh/subgraphs/cookbook/derivedfrom.mdx deleted file mode 100644 index a0942645c999..000000000000 --- a/website/src/pages/zh/subgraphs/cookbook/derivedfrom.mdx +++ /dev/null @@ -1,89 +0,0 @@ ---- -title: Subgraph Best Practice 2 - Improve Indexing and Query Responsiveness By Using @derivedFrom -sidebarTitle: 'Subgraph Best Practice 2: Arrays with @derivedFrom' ---- - -## TLDR - -Arrays in your schema can really slow down a subgraph's performance as they grow beyond thousands of entries. If possible, the `@derivedFrom` directive should be used when using arrays as it prevents large arrays from forming, simplifies handlers, and reduces the size of individual entities, improving indexing speed and query performance significantly. - -## How to Use the `@derivedFrom` Directive - -You just need to add a `@derivedFrom` directive after your array in your schema. Like this: - -```graphql -comments: [Comment!]! @derivedFrom(field: "post") -``` - -`@derivedFrom` creates efficient one-to-many relationships, enabling an entity to dynamically associate with multiple related entities based on a field in the related entity. This approach removes the need for both sides of the relationship to store duplicate data, making the subgraph more efficient. - -### Example Use Case for `@derivedFrom` - -An example of a dynamically growing array is a blogging platform where a “Post” can have many “Comments”. - -Let’s start with our two entities, `Post` and `Comment` - -Without optimization, you could implement it like this with an array: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! -} - -type Comment @entity { - id: Bytes! - content: String! -} -``` - -Arrays like these will effectively store extra Comments data on the Post side of the relationship. - -Here’s what an optimized version looks like using `@derivedFrom`: - -```graphql -type Post @entity { - id: Bytes! - title: String! - content: String! - comments: [Comment!]! @derivedFrom(field: "post") -} - -type Comment @entity { - id: Bytes! - content: String! - post: Post! -} -``` - -Just by adding the `@derivedFrom` directive, this schema will only store the “Comments” on the “Comments” side of the relationship and not on the “Post” side of the relationship. Arrays are stored across individual rows, which allows them to expand significantly. This can lead to particularly large sizes if their growth is unbounded. - -This will not only make our subgraph more efficient, but it will also unlock three features: - -1. We can query the `Post` and see all of its comments. - -2. We can do a reverse lookup and query any `Comment` and see which post it comes from. - -3. We can use [Derived Field Loaders](/subgraphs/developing/creating/graph-ts/api/#looking-up-derived-entities) to unlock the ability to directly access and manipulate data from virtual relationships in our subgraph mappings. - -## Conclusion - -Use the `@derivedFrom` directive in subgraphs to effectively manage dynamically growing arrays, enhancing indexing efficiency and data retrieval. - -For a more detailed explanation of strategies to avoid large arrays, check out Kevin Jones' blog: [Best Practices in Subgraph Development: Avoiding Large Arrays](https://thegraph.com/blog/improve-subgraph-performance-avoiding-large-arrays/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/zh/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx b/website/src/pages/zh/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx deleted file mode 100644 index 511565bb3dd4..000000000000 --- a/website/src/pages/zh/subgraphs/cookbook/immutable-entities-bytes-as-ids.mdx +++ /dev/null @@ -1,191 +0,0 @@ ---- -title: Subgraph Best Practice 3 - Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs -sidebarTitle: 'Subgraph Best Practice 3: Immutable Entities and Bytes as IDs' ---- - -## TLDR - -Using Immutable Entities and Bytes for IDs in our `schema.graphql` file [significantly improves ](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/) indexing speed and query performance. - -## Immutable Entities - -To make an entity immutable, we simply add `(immutable: true)` to an entity. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -By making the `Transfer` entity immutable, graph-node is able to process the entity more efficiently, improving indexing speeds and query responsiveness. - -Immutable Entities structures will not change in the future. An ideal entity to become an Immutable Entity would be an entity that is directly logging onchain event data, such as a `Transfer` event being logged as a `Transfer` entity. - -### Under the hood - -Mutable entities have a 'block range' indicating their validity. Updating these entities requires the graph node to adjust the block range of previous versions, increasing database workload. Queries also need filtering to find only live entities. Immutable entities are faster because they are all live and since they won't change, no checks or updates are required while writing, and no filtering is required during queries. - -### When not to use Immutable Entities - -If you have a field like `status` that needs to be modified over time, then you should not make the entity immutable. Otherwise, you should use immutable entities whenever possible. - -## Bytes as IDs - -Every entity requires an ID. In the previous example, we can see that the ID is already of the Bytes type. - -```graphql -type Transfer @entity(immutable: true) { - id: Bytes! - from: Bytes! - to: Bytes! - value: BigInt! -} -``` - -While other types for IDs are possible, such as String and Int8, it is recommended to use the Bytes type for all IDs due to character strings taking twice as much space as Byte strings to store binary data, and comparisons of UTF-8 character strings must take the locale into account which is much more expensive than the bytewise comparison used to compare Byte strings. - -### Reasons to Not Use Bytes as IDs - -1. If entity IDs must be human-readable such as auto-incremented numerical IDs or readable strings, Bytes for IDs should not be used. -2. If integrating a subgraph’s data with another data model that does not use Bytes as IDs, Bytes as IDs should not be used. -3. Indexing and querying performance improvements are not desired. - -### Concatenating With Bytes as IDs - -It is a common practice in many subgraphs to use string concatenation to combine two properties of an event into a single ID, such as using `event.transaction.hash.toHex() + "-" + event.logIndex.toString()`. However, as this returns a string, this significantly impedes subgraph indexing and querying performance. - -Instead, we should use the `concatI32()` method to concatenate event properties. This strategy results in a `Bytes` ID that is much more performant. - -```typescript -export function handleTransfer(event: TransferEvent): void { - let entity = new Transfer(event.transaction.hash.concatI32(event.logIndex.toI32())) - entity.from = event.params.from - entity.to = event.params.to - entity.value = event.params.value - - entity.blockNumber = event.block.number - entity.blockTimestamp = event.block.timestamp - entity.transactionHash = event.transaction.hash - - entity.save() -} -``` - -### Sorting With Bytes as IDs - -Sorting using Bytes as IDs is not optimal as seen in this example query and response. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: id) { - id - from - to - value - } -} -``` - -Query response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x00010000", - "from": "0xabcd...", - "to": "0x1234...", - "value": "256" - }, - { - "id": "0x00020000", - "from": "0xefgh...", - "to": "0x5678...", - "value": "512" - }, - { - "id": "0x01000000", - "from": "0xijkl...", - "to": "0x9abc...", - "value": "1" - } - ] - } -} -``` - -The IDs are returned as hex. - -To improve sorting, we should create another field on the entity that is a BigInt. - -```graphql -type Transfer @entity { - id: Bytes! - from: Bytes! # address - to: Bytes! # address - value: BigInt! # unit256 - tokenId: BigInt! # uint256 -} -``` - -This will allow for sorting to be optimized sequentially. - -Query: - -```graphql -{ - transfers(first: 3, orderBy: tokenId) { - id - tokenId - } -} -``` - -Query Response: - -```json -{ - "data": { - "transfers": [ - { - "id": "0x…", - "tokenId": "1" - }, - { - "id": "0x…", - "tokenId": "2" - }, - { - "id": "0x…", - "tokenId": "3" - } - ] - } -} -``` - -## Conclusion - -Using both Immutable Entities and Bytes as IDs has been shown to markedly improve subgraph efficiency. Specifically, tests have highlighted up to a 28% increase in query performance and up to a 48% acceleration in indexing speeds. - -Read more about using Immutable Entities and Bytes as IDs in this blog post by David Lutterkort, a Software Engineer at Edge & Node: [Two Simple Subgraph Performance Improvements](https://thegraph.com/blog/two-simple-subgraph-performance-improvements/). - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/zh/subgraphs/cookbook/pruning.mdx b/website/src/pages/zh/subgraphs/cookbook/pruning.mdx deleted file mode 100644 index e212d5d02bc9..000000000000 --- a/website/src/pages/zh/subgraphs/cookbook/pruning.mdx +++ /dev/null @@ -1,56 +0,0 @@ ---- -title: Subgraph Best Practice 1 - Improve Query Speed with Subgraph Pruning -sidebarTitle: 'Subgraph Best Practice 1: Pruning with indexerHints' ---- - -## TLDR - -[Pruning](/developing/creating-a-subgraph/#prune) removes archival entities from the subgraph’s database up to a given block, and removing unused entities from a subgraph’s database will improve a subgraph’s query performance, often dramatically. Using `indexerHints` is an easy way to prune a subgraph. - -## How to Prune a Subgraph With `indexerHints` - -Add a section called `indexerHints` in the manifest. - -`indexerHints` has three `prune` options: - -- `prune: auto`: Retains the minimum necessary history as set by the Indexer, optimizing query performance. This is the generally recommended setting and is the default for all subgraphs created by `graph-cli` >= 0.66.0. -- `prune: `: Sets a custom limit on the number of historical blocks to retain. -- `prune: never`: No pruning of historical data; retains the entire history and is the default if there is no `indexerHints` section. `prune: never` should be selected if [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired. - -We can add `indexerHints` to our subgraphs by updating our `subgraph.yaml`: - -```yaml -specVersion: 1.0.0 -schema: - file: ./schema.graphql -indexerHints: - prune: auto -dataSources: - - kind: ethereum/contract - name: Contract - network: mainnet -``` - -## Important Considerations - -- If [Time Travel Queries](/subgraphs/querying/graphql-api/#time-travel-queries) are desired as well as pruning, pruning must be performed accurately to retain Time Travel Query functionality. Due to this, it is generally not recommended to use `indexerHints: prune: auto` with Time Travel Queries. Instead, prune using `indexerHints: prune: ` to accurately prune to a block height that preserves the historical data required by Time Travel Queries, or use `prune: never` to maintain all data. - -- It is not possible to [graft](/subgraphs/cookbook/grafting/) at a block height that has been pruned. If grafting is routinely performed and pruning is desired, it is recommended to use `indexerHints: prune: ` that will accurately retain a set number of blocks (e.g., enough for six months). - -## Conclusion - -Pruning using `indexerHints` is a best practice for subgraph development, offering significant query performance improvements. - -## Subgraph Best Practices 1-6 - -1. [Improve Query Speed with Subgraph Pruning](/subgraphs/cookbook/pruning/) - -2. [Improve Indexing and Query Responsiveness by Using @derivedFrom](/subgraphs/cookbook/derivedfrom/) - -3. [Improve Indexing and Query Performance by Using Immutable Entities and Bytes as IDs](/subgraphs/cookbook/immutable-entities-bytes-as-ids/) - -4. [Improve Indexing Speed by Avoiding `eth_calls`](/subgraphs/cookbook/avoid-eth-calls/) - -5. [Simplify and Optimize with Timeseries and Aggregations](/subgraphs/cookbook/timeseries/) - -6. [Use Grafting for Quick Hotfix Deployment](/subgraphs/cookbook/grafting-hotfix/) diff --git a/website/src/pages/zh/subgraphs/developing/creating/graph-ts/api.mdx b/website/src/pages/zh/subgraphs/developing/creating/graph-ts/api.mdx index 5f22909399c6..2a35d4ba56d4 100644 --- a/website/src/pages/zh/subgraphs/developing/creating/graph-ts/api.mdx +++ b/website/src/pages/zh/subgraphs/developing/creating/graph-ts/api.mdx @@ -2,7 +2,7 @@ title: AssemblyScript API --- -> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/). +> Note: If you created a subgraph prior to `graph-cli`/`graph-ts` version `0.22.0`, then you're using an older version of AssemblyScript. It is recommended to review the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/). Learn what built-in APIs can be used when writing subgraph mappings. There are two kinds of APIs available out of the box: @@ -35,7 +35,7 @@ Since language mappings are written in AssemblyScript, it is useful to review th | 0.0.8 | Adds validation for existence of fields in the schema when saving an entity. | | 0.0.7 | 添加了 `TransactionReceipt` 和 `Log` 类到以太坊类型。
已将 `receipt` 字段添加到Ethereum Event对象。 | | 0.0.6 | 向Ethereum Transaction对象添加了 nonce 字段 向 Etherum Block对象添加
baseFeePerGas字段 | -| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/release-notes/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | +| 0.0.5 | AssemblyScript upgraded to version 0.19.10 (this includes breaking changes, please see the [`Migration Guide`](/resources/migration-guides/assemblyscript-migration-guide/))
`ethereum.transaction.gasUsed` renamed to `ethereum.transaction.gasLimit` | | 0.0.4 | 已向 Ethereum SmartContractCall对象添加了 `functionSignature` 字段。 | | 0.0.3 | Added `from` field to the Ethereum Call object
`ethereum.call.address` renamed to `ethereum.call.to` | | 0.0.2 | 已向Ethereum Transaction对象添加了 `input` 字段。 | diff --git a/website/src/pages/zh/subgraphs/developing/creating/install-the-cli.mdx b/website/src/pages/zh/subgraphs/developing/creating/install-the-cli.mdx index 62bb898478c0..521b9a21d1a6 100644 --- a/website/src/pages/zh/subgraphs/developing/creating/install-the-cli.mdx +++ b/website/src/pages/zh/subgraphs/developing/creating/install-the-cli.mdx @@ -2,7 +2,7 @@ title: 安装 Graph CLI --- -> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/subgraphs/developing/deploying/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). +> In order to use your subgraph on The Graph's decentralized network, you will need to [create an API key](/resources/subgraph-studio-faq/#2-how-do-i-create-an-api-key) in [Subgraph Studio](https://thegraph.com/studio/apikeys/). It is recommended that you add signal to your subgraph with at least 3,000 GRT to attract 2-3 Indexers. To learn more about signaling, check out [curating](/resources/roles/curating/). ## 概述 diff --git a/website/src/pages/zh/subgraphs/developing/deploying/_meta.js b/website/src/pages/zh/subgraphs/developing/deploying/_meta.js index c4faacb5e561..cb7ed6c18bcc 100644 --- a/website/src/pages/zh/subgraphs/developing/deploying/_meta.js +++ b/website/src/pages/zh/subgraphs/developing/deploying/_meta.js @@ -1,5 +1,4 @@ export default { 'using-subgraph-studio': '', - 'subgraph-studio-faq': '', 'multiple-networks': '', } diff --git a/website/src/pages/zh/subgraphs/querying/best-practices.mdx b/website/src/pages/zh/subgraphs/querying/best-practices.mdx index 801a461c7414..ead15d8026eb 100644 --- a/website/src/pages/zh/subgraphs/querying/best-practices.mdx +++ b/website/src/pages/zh/subgraphs/querying/best-practices.mdx @@ -61,7 +61,7 @@ query [operationName]([variableName]: [variableType]) { > Note: Failing to follow these rules will result in an error from The Graph API. -For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/release-notes/graphql-validations-migration-guide/). +For a complete list of rules with code examples, check out [GraphQL Validations guide](/resources/migration-guides/graphql-validations-migration-guide/). ### 向 GraphQL API 发送查询 diff --git a/website/src/pages/zh/substreams/developing/sinks/sinks.mdx b/website/src/pages/zh/substreams/developing/sinks.mdx similarity index 100% rename from website/src/pages/zh/substreams/developing/sinks/sinks.mdx rename to website/src/pages/zh/substreams/developing/sinks.mdx diff --git a/website/src/pages/zh/substreams/developing/sinks/_meta.js b/website/src/pages/zh/substreams/developing/sinks/_meta.js deleted file mode 100644 index 6022f9d49b74..000000000000 --- a/website/src/pages/zh/substreams/developing/sinks/_meta.js +++ /dev/null @@ -1,3 +0,0 @@ -export default { - sinks: '', -} diff --git a/website/src/pages/zh/substreams/quick-start.mdx b/website/src/pages/zh/substreams/quick-start.mdx index 275a5c6e7f9f..76f738c2752e 100644 --- a/website/src/pages/zh/substreams/quick-start.mdx +++ b/website/src/pages/zh/substreams/quick-start.mdx @@ -13,7 +13,7 @@ Integrating Substreams can be quick and easy. They are permissionless, and you c ### Use Substreams Packages -There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/sinks/). The registry lets you search for and find any package that meets your needs. +There are many ready-to-use Substreams packages available. You can explore these packages by visiting the [Substreams Registry](https://substreams.dev) and [sinking them](/substreams/developing/sinks/). The registry lets you search for and find any package that meets your needs. Once you find a package that fits your needs, you can choose how you want to consume the data: