-
Notifications
You must be signed in to change notification settings - Fork 1
MILAB-1505: add non-pure output test block reproducing the CID conflict #1727
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Open
xnacly
wants to merge
4
commits into
main
Choose a base branch
from
MILAB-1505/nonpure-output-test-block
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Changes from 1 commit
Commits
Show all changes
4 commits
Select commit
Hold shift + click to select a range
88f0769
MILAB-1505: add non-pure output test block reproducing the CID conflict
xnacly 8a38857
MILAB-1505: review cleanup - drop copied boilerplate, suppress traili…
xnacly dd5fb34
MILAB-1505: fix formatting (oxfmt) in nonpure-output ui
xnacly cd8300a
MILAB-1505: refresh block structure to the block-facade layout (fixes…
xnacly File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1 @@ | ||
| {"version":1} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1 @@ | ||
| # Changelog |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,6 @@ | ||
| declare const blockSpec: { | ||
| type: "dev-v2"; | ||
| folder: string; | ||
| }; | ||
|
|
||
| export { blockSpec }; |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,8 @@ | ||
| const blockSpec = { | ||
| type: "dev-v2", | ||
| folder: __dirname, | ||
| }; | ||
|
|
||
| module.exports = { | ||
| blockSpec, | ||
| }; |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,40 @@ | ||
| { | ||
| "name": "@milaboratories/milaboratories.test-nonpure-output", | ||
| "version": "1.0.127", | ||
| "private": true, | ||
| "files": [ | ||
| "index.d.ts", | ||
| "index.js" | ||
| ], | ||
| "scripts": { | ||
| "build": "shx rm -rf ./block-pack && block-tools pack", | ||
| "mark-stable": "block-tools mark-stable -r 's3://milab-euce1-prod-pkgs-s3-block-registry/pub/releases/?region=eu-central-1'", | ||
| "prepublishOnly": "block-tools pack && block-tools publish -r 's3://milab-euce1-prod-pkgs-s3-block-registry/pub/releases/?region=eu-central-1'", | ||
| "do-pack": "shx rm -f *.tgz && block-tools pack && pnpm pack && shx mv *.tgz package.tgz" | ||
| }, | ||
| "dependencies": { | ||
| "@milaboratories/milaboratories.test-nonpure-output.model": "workspace:*", | ||
| "@milaboratories/milaboratories.test-nonpure-output.ui": "workspace:*", | ||
| "@milaboratories/milaboratories.test-nonpure-output.workflow": "workspace:*", | ||
| "@platforma-sdk/model": "workspace:*" | ||
| }, | ||
| "devDependencies": { | ||
| "@platforma-sdk/block-tools": "workspace:*", | ||
| "shx": "catalog:" | ||
| }, | ||
| "block": { | ||
| "components": { | ||
| "workflow": "@milaboratories/milaboratories.test-nonpure-output.workflow/dist/tengo/tpl/main.plj.gz", | ||
| "model": "@milaboratories/milaboratories.test-nonpure-output.model/dist/model.json", | ||
| "ui": "@milaboratories/milaboratories.test-nonpure-output.ui/dist" | ||
| }, | ||
| "meta": { | ||
| "title": "Non-pure Output (CID conflict repro)", | ||
| "description": "Test block whose command emits a different value every run, reproducing the recover-mode CID conflict", | ||
| "organization": { | ||
| "name": "MiLaboratories Inc", | ||
| "url": "https://milaboratories.com/" | ||
| } | ||
| } | ||
| } | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,4 @@ | ||
| { | ||
| "extends": ["node_modules/@milaboratories/ts-builder/configs/oxfmt.json"], | ||
| "ignorePatterns": ["dist", "coverage", "CHANGELOG.md"] | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,3 @@ | ||
| { | ||
| "extends": ["node_modules/@milaboratories/ts-builder/dist/configs/oxlint-block-model.json"] | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1 @@ | ||
| # Changelog |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,42 @@ | ||
| { | ||
| "name": "@milaboratories/milaboratories.test-nonpure-output.model", | ||
| "version": "1.0.34", | ||
| "private": true, | ||
| "description": "Block model", | ||
| "type": "module", | ||
| "main": "dist/index.cjs", | ||
| "module": "dist/index.js", | ||
| "types": "dist/index.d.ts", | ||
| "exports": { | ||
| ".": { | ||
| "types": "./dist/index.d.ts", | ||
| "sources": "./src/index.ts", | ||
| "import": "./dist/index.js" | ||
| }, | ||
| "./dist/*": "./dist/*" | ||
| }, | ||
| "scripts": { | ||
| "build": "ts-builder build --target block-model && block-tools build-model", | ||
| "check": "ts-builder check --target block-model", | ||
| "formatter:check": "ts-builder formatter --check", | ||
| "linter:check": "ts-builder linter --check", | ||
| "types:check": "ts-builder type-check --target block-model", | ||
| "fmt": "ts-builder format", | ||
| "watch": "ts-builder build --target block-model --watch" | ||
| }, | ||
| "dependencies": { | ||
| "@platforma-sdk/model": "workspace:*", | ||
| "zod": "catalog:" | ||
| }, | ||
| "devDependencies": { | ||
| "@milaboratories/build-configs": "workspace:*", | ||
| "@milaboratories/ts-builder": "workspace:*", | ||
| "@milaboratories/ts-configs": "workspace:*", | ||
| "@platforma-sdk/block-tools": "workspace:*", | ||
| "vitest": "catalog:" | ||
| }, | ||
| "peerDependencies": { | ||
| "@types/node": "*", | ||
| "typescript": "*" | ||
| } | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,27 @@ | ||
| import type { InferHrefType, InferOutputsType } from "@platforma-sdk/model"; | ||
| import { BlockModel } from "@platforma-sdk/model"; | ||
| import { z } from "zod"; | ||
|
|
||
| // The block takes no inputs: it just runs an impure command. argsValid is always | ||
| // true, so the workflow runs as soon as the block is created. | ||
| export const BlockArgs = z.object({}); | ||
|
|
||
| export type BlockArgs = z.infer<typeof BlockArgs>; | ||
|
|
||
| export const platforma = BlockModel.create("Heavy") | ||
|
|
||
| .withArgs<BlockArgs>({}) | ||
|
|
||
| // The non-deterministic value produced by the workflow command (changes every run). | ||
| .output("nonpureValue", (ctx) => ctx.outputs?.resolve("nonpureValue")?.getDataAsString()) | ||
|
|
||
| .argsValid(() => true) | ||
|
|
||
| .sections((_ctx) => { | ||
| return [{ type: "link", href: "/", label: "Main" }]; | ||
| }) | ||
|
|
||
| .done(2); // ui api version 2 | ||
|
|
||
| export type BlockOutputs = InferOutputsType<typeof platforma>; | ||
| export type Href = InferHrefType<typeof platforma>; |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,4 @@ | ||
| { | ||
| "extends": "@milaboratories/ts-configs/block/model", | ||
| "include": ["src/**/*"] | ||
| } |
42 changes: 42 additions & 0 deletions
42
etc/blocks/nonpure-output/software/random-gen/package.json
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,42 @@ | ||
| { | ||
| "name": "@platforma-open/milaboratories.test-nonpure-output.random-gen", | ||
| "version": "1.0.0", | ||
| "private": true, | ||
| "description": "Impure command: prints a fresh random value on every run", | ||
| "scripts": { | ||
| "build": "shx rm -rf ./dist && pl-pkg build", | ||
| "prepublishOnly": "pl-pkg prepublish", | ||
| "do-pack": "shx rm -f *.tgz && pl-pkg build && pnpm pack && shx mv platforma-open-*.tgz package.tgz" | ||
| }, | ||
| "files": [ | ||
| "./dist/**/*" | ||
| ], | ||
| "dependencies": {}, | ||
| "devDependencies": { | ||
| "@platforma-sdk/package-builder": "workspace:*", | ||
| "@platforma-open/milaboratories.runenv-python-3": "catalog:", | ||
| "shx": "catalog:" | ||
| }, | ||
| "block-software": { | ||
| "entrypoints": { | ||
| "main": { | ||
| "binary": { | ||
| "artifact": { | ||
| "type": "python", | ||
| "registry": "platforma-open", | ||
| "environment": "@platforma-open/milaboratories.runenv-python-3:3.12.10", | ||
| "dependencies": { | ||
| "toolset": "pip", | ||
| "requirements": "requirements.txt" | ||
| }, | ||
| "root": "./src" | ||
| }, | ||
| "cmd": [ | ||
| "python", | ||
| "{pkg}/main.py" | ||
| ] | ||
| } | ||
| } | ||
| } | ||
| } | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,20 @@ | ||
| #!/usr/bin/env python3 | ||
| """Impure helper for the non-pure-output test block. | ||
|
|
||
| Prints a fresh random token on every run, so the same (empty) inputs produce a | ||
| different output each time. That is exactly what makes a block built on it | ||
| non-pure, and what triggers the recover-mode CID conflict in the backend: the | ||
| recovered (predicted) output CID diverges from the recomputed one. | ||
|
|
||
| Stdlib only - cross-platform, no third-party dependencies. | ||
| """ | ||
|
|
||
| import secrets | ||
|
|
||
|
|
||
| def main() -> None: | ||
| print(secrets.token_hex(16)) | ||
|
|
||
|
|
||
| if __name__ == "__main__": | ||
| main() | ||
1 change: 1 addition & 0 deletions
1
etc/blocks/nonpure-output/software/random-gen/src/requirements.txt
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1 @@ | ||
| # No third-party dependencies - main.py uses the Python standard library only. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,3 @@ | ||
| { | ||
| "ignorePatterns": ["dist", "CHANGELOG.md"] | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,3 @@ | ||
| { | ||
| "extends": ["node_modules/@milaboratories/ts-builder/dist/configs/oxlint-block-ui.json"] | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1 @@ | ||
| # Changelog |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,12 @@ | ||
| <!doctype html> | ||
| <html lang="en"> | ||
| <head> | ||
| <meta charset="UTF-8" /> | ||
| <meta http-equiv="Content-Security-Policy" content="script-src 'self' blob:" /> | ||
| <meta name="viewport" content="width=device-width, initial-scale=1.0" /> | ||
| </head> | ||
| <body> | ||
| <div id="app"></div> | ||
| <script type="module" src="/src/main.ts"></script> | ||
| </body> | ||
| </html> |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,34 @@ | ||
| { | ||
| "name": "@milaboratories/milaboratories.test-nonpure-output.ui", | ||
| "version": "1.0.117", | ||
| "private": true, | ||
| "type": "module", | ||
| "scripts": { | ||
| "dev": "ts-builder serve --target block-ui", | ||
| "watch": "ts-builder build --target block-ui --watch", | ||
| "check": "ts-builder check --target block-ui", | ||
| "formatter:check": "ts-builder formatter --check", | ||
| "linter:check": "ts-builder linter --check", | ||
| "types:check": "ts-builder type-check --target block-ui", | ||
| "build": "ts-builder build --target block-ui", | ||
| "fmt": "ts-builder format" | ||
| }, | ||
| "dependencies": { | ||
| "@milaboratories/milaboratories.test-nonpure-output.model": "workspace:*", | ||
| "@platforma-sdk/ui-vue": "workspace:*", | ||
| "vue": "catalog:" | ||
| }, | ||
| "devDependencies": { | ||
| "@faker-js/faker": "catalog:", | ||
| "@milaboratories/build-configs": "workspace:*", | ||
| "@milaboratories/helpers": "workspace:*", | ||
| "@milaboratories/ts-builder": "workspace:*", | ||
| "@milaboratories/ts-configs": "workspace:*", | ||
| "vitest": "catalog:", | ||
| "zod": "catalog:" | ||
| }, | ||
| "peerDependencies": { | ||
| "@types/node": "*", | ||
| "typescript": "*" | ||
| } | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,19 @@ | ||
| <script setup lang="ts"> | ||
| import { PlAlert, PlBlockPage } from "@platforma-sdk/ui-vue"; | ||
| import { useApp } from "./app"; | ||
|
|
||
| const app = useApp(); | ||
| </script> | ||
|
|
||
| <template> | ||
| <PlBlockPage style="max-width: 100%"> | ||
| <PlAlert type="info" monospace> | ||
| Non-pure output (changes on every run): | ||
| {{ app.model.outputs.nonpureValue }} | ||
| </PlAlert> | ||
|
|
||
| <PlAlert v-if="app.error" type="error"> | ||
| {{ app.error }} | ||
| </PlAlert> | ||
|
xnacly marked this conversation as resolved.
Outdated
|
||
| </PlBlockPage> | ||
| </template> | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,39 @@ | ||
| import { platforma } from "@milaboratories/milaboratories.test-nonpure-output.model"; | ||
| import MainPage from "./MainPage.vue"; | ||
| import { defineApp } from "@platforma-sdk/ui-vue"; | ||
| import type { Component } from "vue"; | ||
| import { computed, reactive } from "vue"; | ||
| import type { Equal, Expect } from "@milaboratories/helpers"; | ||
|
|
||
| export const sdkPlugin = defineApp(platforma, (base) => { | ||
| // Additional data | ||
| const data = reactive({ | ||
| counter: 0, | ||
| }); | ||
|
|
||
| function incrementCounter() { | ||
| data.counter++; | ||
| } | ||
|
|
||
| const argsAsJson = computed(() => JSON.stringify(base.snapshot.args)); | ||
|
|
||
| return { | ||
| data, | ||
| incrementCounter, | ||
| argsAsJson, | ||
| routes: { | ||
| "/": () => MainPage, | ||
| }, | ||
| }; | ||
| }); | ||
|
xnacly marked this conversation as resolved.
Outdated
|
||
|
|
||
| type App = ReturnType<typeof sdkPlugin.useApp>; | ||
|
|
||
| type __cases = [ | ||
| Expect<Equal<App["incrementCounter"], () => void>>, | ||
| Expect<Equal<App["data"], { counter: number }>>, | ||
| Expect<Equal<App["argsAsJson"], string>>, | ||
| Expect<Equal<App["getRoute"], (href: "/") => Component | undefined>>, | ||
| ]; | ||
|
xnacly marked this conversation as resolved.
Outdated
|
||
|
|
||
| export const useApp = sdkPlugin.useApp; | ||
|
xnacly marked this conversation as resolved.
|
||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,5 @@ | ||
| import { createApp } from "vue"; | ||
| import { sdkPlugin } from "./app"; | ||
| import { BlockLayout } from "@platforma-sdk/ui-vue"; | ||
|
|
||
| createApp(BlockLayout).use(sdkPlugin).mount("#app"); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,4 @@ | ||
| { | ||
| "extends": "@milaboratories/ts-configs/block/ui", | ||
| "include": ["src/**/*"] | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1 @@ | ||
| # Changelog |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,42 @@ | ||
| ;; This program formats all files inside src directory. Usage: emacs --script ./format.el | ||
|
|
||
| (defun install-go-mode () | ||
| "Installs go-mode" | ||
| (require 'package) | ||
| (add-to-list 'package-archives | ||
| '("melpa-stable" . "https://stable.melpa.org/packages/")) | ||
| (package-initialize) | ||
| (unless package-archive-contents | ||
| (package-refresh-contents)) | ||
|
|
||
| (package-install 'go-mode t) | ||
| (require 'go-mode)) | ||
|
|
||
| ;; spaces -> tabs only at the beginning of lines | ||
| (setq tabify-regexp "^\t* [ \t]+") | ||
|
|
||
| (defun format-file (file) | ||
| "Formats a file according to slightly changed Go rules" | ||
| (message "Format %s" file) | ||
| (save-excursion | ||
| (find-file file) | ||
| (delete-trailing-whitespace) ;; deletes whitespaces | ||
| (go-mode) ;; sets golang rules for indentation | ||
| (tabify (point-min) (point-max)) ;; spaces -> tabs in the whole file | ||
| (indent-region (point-min) (point-max)) ;; indentation in the whole file | ||
| (save-buffer))) ;; save file | ||
|
|
||
| (install-go-mode) | ||
|
|
||
| ;; change syntax of a standard go-mode a bit | ||
| (advice-add | ||
| 'go--in-composite-literal-p | ||
| :filter-return | ||
| (lambda (&rest r) t)) | ||
|
|
||
| ;; find all files in src | ||
| (setq files (directory-files-recursively "src" "\\.tengo\\'")) | ||
|
|
||
| ;; call format on every file. | ||
| (dolist (file files) | ||
| (format-file file)) |
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.