diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml new file mode 100644 index 00000000..66ee912f --- /dev/null +++ b/.github/workflows/release.yml @@ -0,0 +1,206 @@ +name: Release +on: + push: + tags: + - 'v*' +jobs: + build: + name: Build on ${{ matrix.vm }} + strategy: + fail-fast: false + matrix: + vm: ["ubuntu-latest", "macos-latest"] + runs-on: ${{ matrix.vm }} + steps: + - name: Setup Go 1.13 + uses: actions/setup-go@v1 + with: + go-version: 1.13 + - name: Extract version metadata + id: meta + run: | + echo "::set-output name=os-arch::$(go env GOOS)_$(go env GOARCH)" + echo "::set-output name=version::${GITHUB_REF##*/}" + - name: Check out project files + uses: actions/checkout@v2 + - name: Build + id: build + run: | + make dist VERSION=${{ steps.meta.outputs.version }} + - name: Upload artifacts + uses: actions/upload-artifact@v1 + with: + name: artifacts-${{ steps.meta.outputs.os-arch }} + path: build + deploy: + name: Deploy ${{ matrix.os-arch }} dist to Bintray + runs-on: ubuntu-latest + needs: + - build + strategy: + matrix: + os-arch: ["linux_amd64", "darwin_amd64"] + steps: + - name: Setup jfrog CLI + uses: jfrog/setup-jfrog-cli@v1 + - name: Download artifacts + uses: actions/download-artifact@v1 + with: + name: artifacts-${{ matrix.os-arch }} + - name: Extract metadata + id: meta + run: | + echo "::set-output name=version::${GITHUB_REF##*/}" + echo "::set-output name=package::istanbul" + echo "::set-output name=upload-path::istanbul-tools" + - name: Prepare ${{ steps.meta.outputs.package }}@${{ steps.meta.outputs.version }} in Bintray + run: | + CHECK_PACKAGE="${{ secrets.BINTRAY_ORGANIZATION }}/${{ secrets.BINTRAY_REPOSITORY }}/${{ steps.meta.outputs.package }}" + CHECK_VERSION="$CHECK_PACKAGE/${{ steps.meta.outputs.version }}" + echo "Checking $CHECK_PACKAGE" + jfrog bt package-show --key ${{ secrets.BINTRAY_API_KEY }} --user ${{ secrets.BINTRAY_USER }} $CHECK_PACKAGE + echo "Checking $CHECK_VERSION" + jfrog bt version-show --key ${{ secrets.BINTRAY_API_KEY }} --user ${{ secrets.BINTRAY_USER }} $CHECK_VERSION && x=0 || x=1 + if [ $x -eq 0 ]; then + echo "$CHECK_VERSION already exists" + else + jfrog bt version-create --key ${{ secrets.BINTRAY_API_KEY }} --user ${{ secrets.BINTRAY_USER }} \ + --vcs-tag ${{ steps.meta.outputs.version }} --released $(date -u +"%Y-%m-%dT%H:%M:%SZ") \ + $CHECK_VERSION + fi + - name: Upload to Bintray + run: | + jfrog bt upload --key ${{ secrets.BINTRAY_API_KEY }} --user ${{ secrets.BINTRAY_USER }} --publish --override \ + "artifacts-${{ matrix.os-arch }}/*.*" \ + ${{ secrets.BINTRAY_ORGANIZATION }}/${{ secrets.BINTRAY_REPOSITORY }}/${{ steps.meta.outputs.package }}/${{ steps.meta.outputs.version }} \ + ${{ steps.meta.outputs.upload-path }}/ + notify: + name: Notify Slack + needs: + - build + - deploy + if: always() + runs-on: ubuntu-latest + steps: + - name: Prepare Slack message + id: status + uses: actions/github-script@0.8.0 + with: + script: | + //////////////////////////////////// + // retrieve workflow run data + //////////////////////////////////// + console.log("get workflow run") + const wf_run = await github.actions.getWorkflowRun({ + owner: context.repo.owner, + repo: context.repo.repo, + run_id: ${{ github.run_id }} + }) + console.log(wf_run.data) + console.log("get jobs for workflow run:", wf_run.data.jobs_url) + const jobs_response = await github.request(wf_run.data.jobs_url) + //////////////////////////////////// + // build slack notification message + //////////////////////////////////// + // some utility functions + var date_diff_func = function(start, end) { + var duration = end - start + // format the duration + var delta = duration / 1000 + var days = Math.floor(delta / 86400) + delta -= days * 86400 + var hours = Math.floor(delta / 3600) % 24 + delta -= hours * 3600 + var minutes = Math.floor(delta / 60) % 60 + delta -= minutes * 60 + var seconds = Math.floor(delta % 60) + var format_func = function(v, text, check) { + if (v <= 0 && check) { + return "" + } else { + return v + text + } + } + return format_func(days, "d", true) + format_func(hours, "h", true) + format_func(minutes, "m", true) + format_func(seconds, "s", false) + } + var status_icon_func = function(s) { + switch (s) { + case "w_success": + return ":white_check_mark:" + case "w_failure": + return ":no_entry:" + case "w_cancelled": + return ":warning:" + case "success": + return "\u2713" + case "failure": + return "\u2717" + default: + return "\u20e0" + } + } + const commit = "${{ github.sha }}".substr(0, 6) + var pr = "" + for (p of wf_run.data.pull_requests) { + pr += ",<"+ p.url + "|#" + p.number + ">" + } + if (pr != "") { + pr = "for " + pr.substr(1) + } + // build the message + var fields = [] + var is_wf_success = true + var is_wf_failure = false + for (j of jobs_response.data.jobs) { + console.log(j.name, ":", j.status, j.conclusion, j.started_at, j.completed_at) + // ignore the current job running this script + if (j.status != "completed") { + continue + } + if (j.conclusion != "success") { + is_wf_success = false + } + if (j.conclusion == "failure") { + is_wf_failure = true + } + fields.push({ + type: "mrkdwn", + text: status_icon_func(j.conclusion) + " <" + j.html_url + "|" + j.name + ">\n \u21b3 completed in " + date_diff_func(new Date(j.started_at), new Date(j.completed_at)) + }) + } + var workflow_status = "w_cancelled" + if (is_wf_success) { + workflow_status = "w_success" + } else if (is_wf_failure) { + workflow_status = "w_failure" + } + var slack_msg = { + blocks: [ + { + type: "section", + text: { + type: "mrkdwn", + text: "\nfrom *${{ github.ref }}@" + commit + "*" + } + }, + { + type: "section", + text: { + type: "mrkdwn", + text: status_icon_func(workflow_status) + " *${{ github.workflow }}* " + pr + "\nWorkflow run <" + wf_run.data.html_url + "|#${{ github.run_number }}> completed in " + date_diff_func(new Date(wf_run.data.created_at), new Date(wf_run.data.updated_at)) + } + }, + { + type: "divider" + }, + { + type: "section", + fields: fields + } + ] + } + return slack_msg + - name: Send to Slack + if: success() + run: | + curl -X POST ${{ secrets.SLACK_WEBHOOK_URL}} -H "Content-type: application/json" --data '${{ steps.status.outputs.result }}' \ No newline at end of file diff --git a/.gitignore b/.gitignore index fcce8d5b..786a3800 100644 --- a/.gitignore +++ b/.gitignore @@ -24,7 +24,7 @@ build/_vendor/pkg # used by the Makefile /build/_workspace/ -/build/bin/ +/build /geth*.zip # travis @@ -32,4 +32,6 @@ profile.tmp profile.cov # vscode -.vscode/ \ No newline at end of file +.vscode/ + +vendor/ \ No newline at end of file diff --git a/Makefile b/Makefile index 96f6ef26..d00ad76d 100644 --- a/Makefile +++ b/Makefile @@ -2,15 +2,28 @@ CURDIR = $(shell pwd) #GOPATH= $(dir $(abspath $(dir $(abspath $(dir ${CURDIR}))))) GOBIN = $(CURDIR)/build/bin GO ?= latest +VERSION ?= undefined +OS ?= $(shell go env GOOS) +ARCH ?= $(shell go env GOARCH) +LDFLAGS = -s -w -X main.Version=$(VERSION) +ifeq (linux,$(OS)) + LDFLAGS+= -linkmode external -extldflags "-static" +endif istanbul: @GOPATH=$(GOPATH) go build -v -o ./build/bin/istanbul ./cmd/istanbul @echo "Done building." @echo "Run \"$(GOBIN)/istanbul\" to launch istanbul." +dist: clean + @GOPATH=$(GOPATH) go build -ldflags='$(LDFLAGS)' -o ./build/bin/istanbul ./cmd/istanbul + @tar cfvz ./build/istanbul-tools_$(VERSION)_$(OS)_$(ARCH).tar.gz -C ./build/bin istanbul + @echo "Distribution file created." + @ls -lh ./build + load-testing: @echo "Run load testing" @CURDIR=$(CURDIR) go test -v github.com/jpmorganchase/istanbul-tools/tests/load/... --timeout 1h clean: - rm -rf build/bin/ + rm -rf build diff --git a/README.md b/README.md index 11ce3b79..6025ff17 100644 --- a/README.md +++ b/README.md @@ -16,16 +16,22 @@ NAME: USAGE: istanbul [global options] command [command options] [arguments...] +VERSION: + v1.0.2 + COMMANDS: extra Istanbul extraData manipulation setup Setup your Istanbul network in seconds - help, h Print this message + reinit Reinitialize a genesis block using previous node info + address Extract validator address + help, h Shows a list of commands or help for one command GLOBAL OPTIONS: - --help, -h show help + --help, -h show help + --version, -v print the version COPYRIGHT: - Copyright 2017 The AMIS Authors + Copyright 2017 The AMIS Authors ``` ### `extra` subcommand @@ -216,6 +222,21 @@ OPTIONS: +### `address` subcommand + +
+Click here to expand + +This command is to extract Validator Address (ID) from node key hex which is the node private key in hex + +E.g.: +``` +$ ./build/bin/istanbul address --nodekeyhex 1be3b50b31734be48452c29d714941ba165ef0cbf3ccea8ca16c45e3d8d45fb0 +0xd8dba507e85f116b1f7e231ca8525fc9008a6966 +``` +
+ + ## Testing
diff --git a/cmd/istanbul/main.go b/cmd/istanbul/main.go index 415e3382..b8a55046 100644 --- a/cmd/istanbul/main.go +++ b/cmd/istanbul/main.go @@ -28,11 +28,15 @@ import ( "github.com/urfave/cli" ) +var ( + Version string // this is externalized via -X flag +) + func main() { app := utils.NewApp() app.Usage = "the istanbul-tools command line interface" - app.Version = "v1.0.1" + app.Version = Version app.Copyright = "Copyright 2017 The AMIS Authors" app.Commands = []cli.Command{ extra.ExtraCommand,