Compare commits

...

1979 Commits
0.1 ... v0.14.0

Author SHA1 Message Date
Ethan Buchman
88f5f21dbb Merge pull request #960 from tendermint/release-v0.14.0
Release v0.14.0
2017-12-12 01:28:35 -05:00
Ethan Buchman
5facfafbd5 Merge branch 'develop' into release-v0.14.0 2017-12-11 23:09:04 -05:00
Ethan Buchman
11761d1769 initial port of cosmos-sdk basecli proxy 2017-12-11 22:23:13 -05:00
Ethan Buchman
2c14488b93 Merge pull request #963 from tendermint/remove-get-deps-from-makefile
Remove get_deps, update_deps and list_deps from Makefile
2017-12-11 21:56:05 -05:00
Ethan Buchman
c127bce73b Merge pull request #962 from tendermint/wait-a-little-longet-on-ci
wait 5 sec for a block on CircleCI
2017-12-11 21:54:57 -05:00
Anton Kaliaev
69205594cc add gopath to path on CircleCI 2017-12-11 16:59:08 -06:00
Anton Kaliaev
d943f66abc remove get_deps, update_deps and list_deps
Rationale: they only lead to broken builds and should not be used by
anyone.
2017-12-11 16:55:40 -06:00
Anton Kaliaev
b2385b46cf wait 5 sec for a block on CircleCI
Fixes:
```
--- FAIL: TestHandshakeReplaySome (12.40s)
        replay_test.go:332: waited too long for tendermint to produce 6 blocks
```
2017-12-11 16:22:27 -06:00
Ethan Buchman
2af32d6665 changelog and version bump 2017-12-11 15:05:56 -05:00
Ethan Buchman
5c58db3bb4 changelog [ci skip] 2017-12-11 14:49:34 -05:00
Ethan Buchman
24a9491203 Merge pull request #955 from tendermint/939-p2p-exponential-backoff-on-reconnect
p2p: exponential backoff on reconnect. closes #939
2017-12-11 14:25:39 -05:00
Ethan Buchman
5511bd8e85 p2p: exponential backoff on reconnect. closes #939 2017-12-11 13:41:09 -05:00
Ethan Buchman
f1ca2b3a3a Merge pull request #698 from tendermint/feat-appveyor
WIP: Run tests on AppVeyor
2017-12-10 20:06:34 -05:00
Ethan Buchman
10fcefe346 appveyor: use make 2017-12-10 20:07:44 -05:00
Ethan Buchman
41bb2c2663 Merge pull request #931 from tendermint/785-wal-improvements
[consensus] remove WAL separator
2017-12-10 19:46:02 -05:00
Ethan Buchman
e7b9cd8ee8 Merge branch 'develop' into 785-wal-improvements 2017-12-10 19:45:52 -05:00
Ethan Buchman
3019b9f320 Merge pull request #948 from tendermint/945-transparent-websocket
bring back transparent websocket (Refs #945)
2017-12-10 19:05:32 -05:00
Ethan Buchman
60872d7d7c Merge pull request #949 from tendermint/docs/trust-metric-usage
Docs/trust metric usage
2017-12-10 19:01:16 -05:00
Ethan Buchman
a37c1143ca adr: update 007 trust metric usage 2017-12-10 19:00:44 -05:00
caffix
4e08ee1833 made clarifications based on odeke-em's PR comments 2017-12-10 15:39:43 -05:00
caffix
7563870d11 added the trust metric usage guide 2017-12-10 15:39:43 -05:00
Zach
12c5a57415 determinisitic linter (#902)
* linter: address gosimple lints

* linter: make deterministic & a rebase fix

* lint/rpc: fix a gosimple lint

* run linter in CI

* fix rebase mistake

* fix makefile

* ugh

* revert Makefile

* add metalinter to CI

* try this

* linter: last little fix

* need glide

* better

* okayy circle, have it your way

* lints: gosimple

* pr comments
2017-12-10 17:44:22 +00:00
Anton Kaliaev
101680d603 update changelog [ci skip] 2017-12-10 11:35:22 -06:00
Anton Kaliaev
d819d5d324 update changelog [ci skip] 2017-12-10 11:34:08 -06:00
Anton Kaliaev
90cdffa067 fixes after my own review (Refs #945) 2017-12-10 11:29:36 -06:00
Ethan Buchman
080640a171 Merge pull request #936 from tendermint/update-dockerfile-to-0.12.1
Update dockerfile to 0.12.1
2017-12-10 12:15:09 -05:00
Anton Kaliaev
950a64f756 bring back transparent websocket (Refs #945) 2017-12-10 01:18:10 -06:00
Anton Kaliaev
b50cef742d Merge pull request #943 from tendermint/feature/update-vagrantfile
Update Vagrantfile to xenial (16.04 LTS)
2017-12-09 17:03:44 -06:00
Anton Kaliaev
4f50935aa2 Merge pull request #946 from ricardohsd/fix-typo
consensus: Fix typo on ticker.go documentation
2017-12-09 17:03:12 -06:00
Ricardo Domingos
59e89e7664 consensus: Fix typo on ticker.go documentation 2017-12-09 13:14:53 +01:00
Ethan Frey
2112299586 Cleanup apt-get ala PR comments 2017-12-08 19:20:53 +01:00
Ethan Frey
c771964a40 Add vagrant_test to Makefile for integration tests 2017-12-08 18:36:58 +01:00
Anton Kaliaev
a199ec2813 update docker readme 2017-12-08 11:35:35 -06:00
Anton Kaliaev
a28b3fff49 update Dockerfile to 0.13.0 2017-12-08 11:34:34 -06:00
Ethan Frey
5bcd95f01f Use apt-get/ppa instead of tarballs for golang/docker
Minor cleanup and comments
2017-12-08 18:10:39 +01:00
Ethan Frey
c84494b36b Update Vagrantfile to xenial (16.04 LTS)
Note default username changed from vagrant to ubuntu in the base image.
2017-12-08 18:10:39 +01:00
Anton Kaliaev
7e3a5b7ce8 Merge pull request #942 from tendermint/bugfix/install-stdlib
From CGO_ENABLED=0 from make install
2017-12-08 11:03:05 -06:00
Ethan Buchman
fbfd11de2c add @melekes as codeowner 2017-12-08 11:48:05 -05:00
Ethan Frey
9657d183f8 Remove CGO_ENABLED=0 from make install
It was writing to stdlib packages net, x/crypto, etc. and failing when it didn't have write access to them (which it often shouldn't)

Fixes issue #941

Explained in golang issue: golang/go#18981 (fixed in develop/1.10)
2017-12-08 17:03:09 +01:00
Ethan Buchman
b98098b1f0 Merge pull request #932 from tendermint/920-default-moniker-to-host-name
default moniker to the host name
2017-12-07 18:34:38 -05:00
Ethan Buchman
1ae14e5a3d Merge pull request #933 from tendermint/880-node-fails-if-one-of-the-seeds-cannot-be-resolved
tolerate unresolvable seeds
2017-12-07 18:27:58 -05:00
Anton Kaliaev
7a92a3b729 update docker readme 2017-12-07 13:49:29 -06:00
Anton Kaliaev
457c688346 update Dockerfile to point to 0.12.1 2017-12-07 13:48:31 -06:00
Anton Kaliaev
c609b18698 tolerate unresolvable seeds (Refs #880) 2017-12-07 13:17:09 -06:00
Anton Kaliaev
5ff0bb2100 default moniker to the host name (Refs #920) 2017-12-07 12:49:29 -06:00
Anton Kaliaev
90944bb1a2 be specific about what type we're encoding
to be consistent with Decode, which returns TimedWALMessage
2017-12-07 11:45:50 -06:00
Anton Kaliaev
07571741c5 [consensus] remove WAL separator (Refs #785)
We don't really need a separator unless we have complex structures
(rows, cells like RDBMS have https://www.sqlite.org/fileformat.html).
2017-12-07 11:36:46 -06:00
Ethan Buchman
14ccc8bc4c Merge pull request #930 from tendermint/468-make-consensus-data-deterministic
make consensus/test_data deterministic
2017-12-06 22:28:03 -05:00
Anton Kaliaev
5cb936fa00 fixes after my own review 2017-12-06 18:28:14 -06:00
Anton Kaliaev
c6f025f40e generate WAL on the fly (Refs #468) 2017-12-06 16:01:08 -06:00
Ethan Buchman
a2b92c0745 Merge pull request #927 from tendermint/release-v0.13.0
Release v0.13.0
2017-12-06 03:57:49 -05:00
Ethan Buchman
6884463ba2 update changelog [ci skip] 2017-12-06 03:38:03 -05:00
Ethan Buchman
167d0e82f9 fixes and version bump 2017-12-06 03:33:03 -05:00
Ethan Buchman
42e77de6a3 changelog; minor stuff; update glide 2017-12-06 02:45:38 -05:00
Ethan Buchman
58b4a8395b Merge pull request #917 from tendermint/trust-metric-cleanup
Trust metric cleanup
2017-12-06 02:11:38 -05:00
Ethan Buchman
d0dc04001e rpc: make time human readable. closes #926 2017-12-06 01:25:11 -05:00
Ethan Buchman
e101aa9fc8 fix for legacy gowire 2017-12-06 01:21:14 -05:00
Ethan Buchman
6a7c399c2d Merge pull request #923 from tendermint/enable-homebrew-installation-from-source
Enable homebrew installation from source
2017-12-05 00:50:52 -05:00
Anton Kaliaev
b3e1341e44 use get rev-parse --short HEAD everywhere instead of GitCommit[:8] 2017-12-04 22:16:19 -06:00
Anton Kaliaev
ebdc7ddf20 add missing get_vendor_deps to "make all" 2017-12-04 19:04:15 -06:00
Anton Kaliaev
f30ce8b210 remove GitDescribe - no such variable defined in version package
- add "-w -s" flags to reduce binary size (they remove debug info)
2017-12-04 18:19:11 -06:00
Anton Kaliaev
76cccfaabd get_vendor_deps does not require all the tools
- remove revision cmd
- rename ensure_tools to tools
2017-12-04 18:19:11 -06:00
Anton Kaliaev
440d76647d rename release to test_release 2017-12-04 17:37:32 -06:00
Anton Kaliaev
2cc2fade06 remove -extldflags "-static"
golang builds static libraries by default.
2017-12-04 17:35:42 -06:00
Anton Kaliaev
e50173c7dc merge 2 rules in .editorconfig 2017-12-04 15:01:28 -06:00
Anton Kaliaev
3318cf9aec do not suppose that GOPATH is added to PATH
```
brew install tendermint --HEAD
==> Installing tendermint from tendermint/tendermint
==> Cloning https://github.com/tendermint/tendermint.git
Cloning into '/Users/antonk/Library/Caches/Homebrew/tendermint--git'...
remote: Counting objects: 437, done.
remote: Compressing objects: 100% (412/412), done.
remote: Total 437 (delta 7), reused 129 (delta 2), pack-reused 0
Receiving objects: 100% (437/437), 3.04 MiB | 1006.00 KiB/s, done.
Resolving deltas: 100% (7/7), done.
==> Checking out branch develop
==> make get_vendor_deps
Last 15 lines from /Users/antonk/Library/Logs/Homebrew/tendermint/01.make:
2017-12-04 14:54:54 -0600

make
get_vendor_deps

go get github.com/mitchellh/gox github.com/tcnksm/ghr github.com/Masterminds/glide github.com/alecthomas/gometalinter
make: gometalinter: No such file or directory
make: *** [ensure_tools] Error 1

If reporting this issue please do so at (not Homebrew/brew or Homebrew/core):
https://github.com/tendermint/homebrew-tendermint/issues
```
2017-12-04 15:00:16 -06:00
Ethan Buchman
b37230f6db Merge pull request #918 from tendermint/abci-update
Abci update
2017-12-03 01:36:59 -05:00
Ethan Buchman
1bf57a90df glide: update grpc version 2017-12-02 23:41:12 -05:00
Ethan Buchman
d2db202a2d mempool: assert -> require in test 2017-12-02 23:41:09 -05:00
Ethan Buchman
08857606dc test: fix test/app/counter_test.sh 2017-12-02 23:39:19 -05:00
Ethan Buchman
72e389041c Merge pull request #914 from tendermint/11-response-info-with-invalid-height-crashes-tm
int64 height (Refs #911)
2017-12-02 23:17:41 -05:00
Anton Kaliaev
d41c0b10c8 change delta's type from int to int64 2017-12-02 11:48:24 -06:00
Ethan Buchman
898ae53672 types: fix for broken customtype int in gogo 2017-12-02 12:00:46 -05:00
Ethan Buchman
9e20cfee0e glide 2017-12-02 01:56:40 -05:00
Ethan Buchman
9af8da7aad update for new abci int types 2017-12-02 01:47:55 -05:00
Ethan Buchman
c9be2b89f9 mempool: return error on cached txs 2017-12-02 01:15:11 -05:00
Ethan Buchman
388f66c9b3 types: drop uint64 from protobuf.go 2017-12-02 01:07:17 -05:00
Anton Kaliaev
cd5a5d332f remove comments for uint64 related to possible underflow [ci skip] 2017-12-01 23:30:08 -06:00
Ethan Buchman
cb9a1dbb4f p2p/trust: lock on Copy() 2017-12-01 23:35:17 -05:00
Ethan Buchman
814541f6d9 p2p/trust: split into multiple files and improve function order 2017-12-01 23:35:12 -05:00
Anton Kaliaev
89cbcceac4 error if app returned negative last block height (Fixes #911) 2017-12-01 21:56:08 -06:00
Anton Kaliaev
10f7858453 use rand.Int63n, remove underflow check, remove unnecessary cast 2017-12-01 19:22:18 -06:00
Anton Kaliaev
922af7c405 int64 height
uint64 is considered dangerous. the details will follow in a blog post.
2017-12-01 19:04:53 -06:00
Ethan Buchman
e9f8e56895 fixes from rebase 2017-12-01 17:25:44 -05:00
Anton Kaliaev
3eb069a50c no need in this hack since we have replay now 2017-12-01 17:17:22 -05:00
Anton Kaliaev
f1fbf995f7 protect ourselves again underflow (Refs #911) 2017-12-01 17:17:22 -05:00
Anton Kaliaev
86af889dfb remove unnecessary casts (Refs #911) 2017-12-01 17:17:22 -05:00
Anton Kaliaev
b3492356e6 uint64 height (Refs #911) 2017-12-01 17:17:22 -05:00
Ethan Buchman
b2489b4318 Merge pull request #912 from bluecollarcoding/fix/docs
docs:clarify py-abci/py-tendermint
2017-12-01 02:57:32 -05:00
Ethan Buchman
a5a7e7ac56 Merge pull request #913 from bluecollarcoding/zramsay-patch-1
codecov: ignore docs files
2017-12-01 02:56:34 -05:00
Ethan Buchman
74cbfc68a1 Merge pull request #835 from tendermint/feature/indexing
Indexing DeliverTx tags
2017-12-01 02:54:30 -05:00
Anton Kaliaev
6423306980 TestIndexAllTags (unit) 2017-11-30 23:02:40 -06:00
Anton Kaliaev
c5b62ce1ee correct abci version 2017-11-30 20:20:35 -06:00
Anton Kaliaev
e538e0e077 config variable to index all tags 2017-11-30 20:02:39 -06:00
Zach
9314e451c8 Update .codecov.yml 2017-11-30 19:01:50 +00:00
Zach Ramsay
3b61e2854a docs: correction, closes #910 2017-11-30 18:27:46 +00:00
Anton Kaliaev
03222d834b update abci dependency 2017-11-30 11:46:28 -06:00
Anton Kaliaev
cb9743e567 dummy app now returns one DeliverTx tag 2017-11-29 20:30:37 -06:00
Anton Kaliaev
66ad366a4f test searching for tx with multiple same tags 2017-11-29 20:04:26 -06:00
Anton Kaliaev
864ad8546e more test cases 2017-11-29 20:04:00 -06:00
Anton Kaliaev
58789c52cd add example for tx_search endpoint 2017-11-29 15:30:12 -06:00
Anton Kaliaev
a762253e24 do not use AddBatch, prefer copying for now 2017-11-29 15:25:12 -06:00
Anton Kaliaev
10d893ee9b update deps 2017-11-29 15:19:45 -06:00
Anton Kaliaev
acbc0717d4 add client methods 2017-11-29 15:19:44 -06:00
Anton Kaliaev
1e19860585 fixes from my own review 2017-11-29 14:24:18 -06:00
Anton Kaliaev
09941b9aa9 fix metalinter warnings 2017-11-29 14:24:18 -06:00
Anton Kaliaev
2a5e8c4a47 add minimal documentation for tx_search RPC method [ci skip] 2017-11-29 14:24:18 -06:00
Anton Kaliaev
686e0eea9f extract indexing goroutine to a separate indexer service 2017-11-29 14:24:18 -06:00
Anton Kaliaev
91f2184003 fixes after bucky's review 2017-11-29 14:24:18 -06:00
Anton Kaliaev
3e577ccf4f add tx_search RPC endpoint 2017-11-29 14:24:18 -06:00
Anton Kaliaev
ea0b205455 searching transaction results 2017-11-29 14:24:18 -06:00
Anton Kaliaev
16cf7a5e0a use a switch when validating tags 2017-11-29 14:23:44 -06:00
Anton Kaliaev
56abea7427 rename tm.events.type to just tm.event 2017-11-29 14:23:44 -06:00
Anton Kaliaev
461a143a2b remove tx.hash tag from config because it's mandatory 2017-11-29 14:23:44 -06:00
Anton Kaliaev
f65e357d2b adapt Tendermint to new abci.Client interface
which was introduced in https://github.com/tendermint/abci/pull/130
2017-11-29 14:23:44 -06:00
Anton Kaliaev
4a31532897 remove unreachable code 2017-11-29 14:23:44 -06:00
Anton Kaliaev
29cd1a1b8f rewrite indexer to be a listener of eventBus 2017-11-29 14:23:44 -06:00
Anton Kaliaev
cd4be1f308 add tx_index config 2017-11-29 14:23:43 -06:00
Anton Kaliaev
acae38ab9e validate tags 2017-11-29 14:23:43 -06:00
Anton Kaliaev
a52cdbfe43 extract tags from DeliverTx/Result
and send them along with predefined
2017-11-29 14:23:43 -06:00
Ethan Buchman
f233cde9a9 Merge pull request #807 from tendermint/45-change-common-start-signature
service#Start, service#Stop signatures were changed
2017-11-29 20:23:07 +00:00
Anton Kaliaev
ceb8ba2e15 comment out gas linter for now 2017-11-29 13:18:34 -06:00
Ethan Buchman
aab54011b3 docs/install: add note about putting GOPATH/bin on PATH 2017-11-29 18:05:51 +00:00
Anton Kaliaev
691e266bef ignore ErrAlreadyStarted when starting addrbook in PEXReactor 2017-11-29 10:53:30 -06:00
Anton Kaliaev
c6b2334fa3 check for error when stopping WSClient 2017-11-29 10:38:58 -06:00
Anton Kaliaev
69b5da766c service#Start, service#Stop signatures were changed
See https://github.com/tendermint/tmlibs/issues/45
2017-11-29 10:38:58 -06:00
Ethan Buchman
a393cf4109 Merge pull request #904 from tendermint/fix-atomic-broadcast-test
test/p2p/atomic_broadcast: wait for node heights before checking app hash
2017-11-28 08:21:15 +00:00
Ethan Buchman
1b120466ee Merge pull request #892 from tendermint/mempool-Stop-method
mempool: implement Mempool.CloseWAL
2017-11-28 06:58:01 +00:00
Ethan Buchman
c8c533cc23 test/p2p/atomic_broadcast: wait for node heights before checking app hash 2017-11-28 05:51:32 +00:00
Ethan Buchman
1e8deacf2e Merge branch 'master' into develop 2017-11-28 04:39:41 +00:00
Emmanuel Odeke
3595b5931a mempool: implement Mempool.CloseWAL
Fixes https://github.com/tendermint/tendermint/issues/890

Add a CloseWAL method to Mempool to close the underlying WAL file
and then discard it so that further writes to it will have no effect.
2017-11-27 21:37:25 -07:00
Ethan Buchman
c7f923c5b0 Merge pull request #903 from tendermint/hotfix-v0.12.1
Upgrade tmlibs dependency to build on Windows
2017-11-28 04:36:52 +00:00
Adrian Brink
25f9eb782b Upgrade tmlibs dependency to build on Windows 2017-11-28 04:04:58 +00:00
Ethan Buchman
2009c3d4f1 Merge pull request #884 from tendermint/wal-benchmark-decode
consensus/WAL: benchmark WALDecode across data sizes
2017-11-28 03:39:55 +00:00
Zach
c3632bc54a Merge pull request #703 from tendermint/fix-linting
add metalinter to CI and include fixes
2017-11-28 00:02:52 +00:00
Ethan Buchman
d9c87a21a6 run metalinter in make test and run_test.sh 2017-11-27 22:39:12 +00:00
Ethan Buchman
2e76b23c9a rpc: fix tests 2017-11-27 22:39:12 +00:00
Ethan Buchman
9529f12c28 more linting 2017-11-27 22:39:12 +00:00
Ethan Buchman
55b81cc1a1 address linting FIXMEs 2017-11-27 22:39:12 +00:00
Zach Ramsay
c4caad7720 lint madness 2017-11-27 22:39:12 +00:00
Zach Ramsay
2563b4fc92 lint fixes 2017-11-27 22:39:12 +00:00
Zach Ramsay
6f3c05545d fix new linting errors 2017-11-27 22:39:12 +00:00
Zach Ramsay
414a8cb0ba pass tests! 2017-11-27 22:39:12 +00:00
Zach Ramsay
c84c7250ba linting: few more fixes 2017-11-27 22:39:12 +00:00
Zach Ramsay
c7b6faf96a bad goimports 2017-11-27 22:39:12 +00:00
Zach Ramsay
fe37afc0d7 do i need this? 2017-11-27 22:39:12 +00:00
Zach Ramsay
478a10aa41 Write doesn't need error checked 2017-11-27 22:39:12 +00:00
Zach Ramsay
d033470817 lil fixes 2017-11-27 22:39:12 +00:00
Zach Ramsay
7ad8a8ab55 Tests almost passing 2017-11-27 22:39:12 +00:00
Zach Ramsay
a15c7f221d linting: moar fixes 2017-11-27 22:39:11 +00:00
Zach Ramsay
d7cb291fb2 errcheck; sort some stuff out 2017-11-27 22:39:11 +00:00
Zach Ramsay
563faa98de address comments, pr #643 2017-11-27 22:39:11 +00:00
Zach Ramsay
9c62ed4595 run linting first for tests 2017-11-27 22:39:11 +00:00
Zach Ramsay
fe694e1fe1 ... 2017-11-27 22:39:11 +00:00
Zach Ramsay
bc2aa79f9a linter: sort through each kind and address small fixes 2017-11-27 22:39:11 +00:00
Zach Ramsay
48aca642e3 linter: address deadcode, implement incremental lint testing 2017-11-27 22:39:11 +00:00
Zach Ramsay
15651a931e linting errors: tackle p2p package 2017-11-27 22:39:11 +00:00
Zach Ramsay
68e7983c70 linting errors: afew more 2017-11-27 22:39:11 +00:00
Zach Ramsay
8f0237610e linting errors: clean it all up 2017-11-27 22:39:11 +00:00
Zach Ramsay
b75d4f73e7 errcheck: PR comment fixes 2017-11-27 22:39:11 +00:00
Zach Ramsay
b3c5933a23 state: return to-be-used function 2017-11-27 22:39:11 +00:00
Zach Ramsay
331857c9e6 linting: apply errcheck part2 2017-11-27 22:39:11 +00:00
Zach Ramsay
57ea4987f7 linting: apply errcheck part1 2017-11-27 22:39:11 +00:00
Zach Ramsay
d95ba866b8 lint: apply deadcode/unused 2017-11-27 22:39:11 +00:00
Zach Ramsay
1721543e5c linting: apply misspell 2017-11-27 22:39:11 +00:00
Zach Ramsay
46ccbcbff6 linting: apply 'gofmt -s -w' throughout 2017-11-27 22:39:11 +00:00
Zach Ramsay
fc33576bac linting: replace megacheck with metalinter 2017-11-27 22:39:11 +00:00
Ethan Buchman
366bc00b70 Merge pull request #895 from tendermint/894-vagrant-instructions
add Vagrant instructions to CONTRIBUTING guides (Refs #894) [ci skip]
2017-11-27 20:54:32 +00:00
Ethan Buchman
d5cd3a111f Merge pull request #899 from tendermint/feature/lite-client
Rename certifier to lite (#784) and add godocs
2017-11-27 17:21:15 +00:00
Ethan Buchman
94e400a5d6 Merge pull request #896 from tendermint/normalize-priority-and-id
normalize priority and id and remove pointers in ChannelDescriptor
2017-11-27 17:05:38 +00:00
Ethan Buchman
7dd249f754 Merge pull request #882 from caffix/develop
fixed race condition reported in issue #881
2017-11-27 16:50:57 +00:00
Adrian Brink
12ae1bb5e5 Address comments 2017-11-27 16:23:56 +01:00
Adrian Brink
248f176c1f Rename light to lite 2017-11-27 16:19:00 +01:00
Adrian Brink
1871a7c3d0 Rename certifier to light (#784) and add godocs
The certifier package is renamed to light. This is more descriptive
especially in the wider blockchain context. Moreover we are building
light-clients using the light package.

This also adds godocs to all exported functions.

Furthermore it introduces some extra error handling. I've added one TODO
where I would like someone else's opinion on how to handle the error.
2017-11-27 16:18:27 +01:00
Petabyte Storage
59b3dcb5cf normalize priority and id and remove pointers in ChannelDescriptor 2017-11-25 22:01:23 -08:00
Anton Kaliaev
fb87590c82 add Vagrant instructions to CONTRIBUTING guides (Refs #894) [ci skip] 2017-11-24 16:42:46 -06:00
Ethan Buchman
38c4de3fc7 Merge pull request #891 from tendermint/fix-vagrantfile
go requires Git (Fixes #879)
2017-11-24 22:07:29 +00:00
Anton Kaliaev
ae67408d13 go requires Git (Fixes #879) 2017-11-23 16:55:57 -06:00
Emmanuel Odeke
42da8cd297 consensus/WAL: benchmark WALDecode across data sizes 2017-11-23 12:43:11 -07:00
caffix
887cb6d0cd added public methods to handle locking within the trust metric 2017-11-22 23:42:38 -05:00
caffix
aeaf2d0b20 Merge branch 'develop' of https://github.com/tendermint/tendermint into develop 2017-11-22 23:11:01 -05:00
Ethan Buchman
932e472986 Merge pull request #885 from AFDudley/patch-1
Update getting-started.rst to fix broken link
2017-11-22 20:29:30 +00:00
Ethan Buchman
e845987503 p2p: disable trustmetric test while being fixed 2017-11-22 20:20:53 +00:00
Ethan Buchman
531b1197a7 Merge pull request #843 from tendermint/refactor-mconnection-with-go-wire-1
WIP: begin parallel refactoring: go-wire Write methods and MConnection
2017-11-22 19:34:22 +00:00
Ethan Buchman
52ad6242f4 Merge pull request #888 from tendermint/rm-dead-file
remove unused file
2017-11-22 18:47:30 +00:00
Zach Ramsay
969b34057b remove unused file 2017-11-22 17:22:53 +00:00
Petabyte Storage
e110f70b5c update glide.yaml versions with go-wire at develop branch 2017-11-22 07:34:10 -08:00
Ethan Buchman
e997db7a23 Merge pull request #859 from tendermint/fix/addrbook
Fix/addrbook
2017-11-21 15:31:48 +00:00
Ethan Buchman
c4b695f78d minor fixes from review 2017-11-21 15:30:19 +00:00
Ethan Buchman
75463b8331 Merge pull request #877 from tendermint/p2p-switch-DialSeeds-undeterministically
p2p: make Switch.DialSeeds use a new PRNG per call
2017-11-21 15:24:29 +00:00
A. F. Dudley
882c25f292 Update getting-started.rst to fix broken link
fixes broken link to introduction.html
2017-11-21 10:11:48 -05:00
caffix
9c8100043e made changes to address suggestions from the PR comments 2017-11-20 19:15:11 -05:00
Emmanuel Odeke
031e10133c p2p: make Switch.DialSeeds use a new PRNG per call
Fixes https://github.com/tendermint/tendermint/issues/875

Ensure that every DialSeeds call uses a new PRNG seeded from
tendermint/tmlibs/common.RandInt which internally uses
crypto/rand to seed its source.
2017-11-20 15:28:42 -07:00
caffix
4087326f45 fixed race condition reported in issue #881 2017-11-20 16:47:05 -05:00
Ethan Buchman
f9bc22ec6a p2p: fix comment on addPeer (thanks @odeke-em) 2017-11-20 21:36:01 +00:00
Ethan Buchman
26cd99c66e p2p: fix non-routable addr in test 2017-11-20 19:56:44 +00:00
Ethan Buchman
9334aad906 Merge pull request #871 from tendermint/fix/docs-860
docs: fix links
2017-11-20 19:47:18 +00:00
Ethan Buchman
c695c53259 Merge pull request #876 from tendermint/p2p-extract-key-lex-check-to-variable-for-clarity
p2p: use bytes.Equal for key comparison
2017-11-20 19:33:58 +00:00
Martin Dyring-Andersen
5c4397ab30 Run tests on AppVeyor 2017-11-20 13:23:28 +01:00
Emmanuel Odeke
5c34d087d9 p2p: use bytes.Equal for key comparison
Updates https://github.com/tendermint/tendermint/issues/850

My security alarms falsely blarred when I skimmed and noticed
keys being compared with `==`, without the proper context
so I mistakenly filed an issue, yet the purpose of that
comparison was to check if the local ephemeral public key
was just the least, sorted lexicographically.

Anyways, let's use the proper bytes.Equal check, to save future labor.
2017-11-18 23:34:27 -07:00
Zach Ramsay
559bd169bd docs: fix links, closes #860 2017-11-17 14:03:43 +00:00
Ethan Buchman
f8c969f5a5 Merge pull request #868 from tendermint/small-things
node: clean makeNodeInfo
2017-11-17 01:22:45 +00:00
Ethan Buchman
c5253c7a31 node: clean makeNodeInfo 2017-11-17 01:22:38 +00:00
Ethan Buchman
53f15fde07 update changelog 2017-11-17 00:04:03 +00:00
Ethan Buchman
814f9cb566 Merge pull request #856 from tendermint/small-things
Small things
2017-11-17 00:03:57 +00:00
Ethan Buchman
af0db599b0 minor fixes 2017-11-16 23:57:00 +00:00
Ethan Buchman
104368bd84 Merge pull request #787 from caffix/develop
Initial Trust Metric Implementation
2017-11-16 23:51:53 +00:00
Ethan Buchman
99461a178e Merge pull request #857 from gguoss/patch-1
Failed to compile comment code
2017-11-16 18:35:18 +00:00
Ethan Buchman
feb3230160 some comments 2017-11-16 04:43:07 +00:00
Ethan Buchman
be1a16a601 p2p/pex: simplify ensurePeers 2017-11-16 04:30:38 +00:00
Ethan Buchman
8e044b0e6d p2p/addrbook: some comments 2017-11-16 04:30:23 +00:00
Ethan Buchman
40e93a5f9e p2p/addrbook: fix addToOldBucket 2017-11-16 04:08:46 +00:00
Ethan Buchman
435eb6e2b3 p2p/addrbook: add non-terminating test 2017-11-16 04:04:54 +00:00
Ethan Buchman
8c88cc017a p2p/addrbook: addAddress returns error. more defensive PickAddress 2017-11-16 03:59:54 +00:00
Ethan Buchman
ed95cc160a p2p/addrbook: simplify PickAddress 2017-11-16 02:31:47 +00:00
Ethan Buchman
2f067a3f65 p2p/addrbook: addrNew/Old -> bucketsNew/Old 2017-11-16 02:28:11 +00:00
Ethan Buchman
498a82784d p2p/addrbook: comments 2017-11-16 02:25:00 +00:00
Guanghua Guo
b5708825a7 Failed to compile comment code 2017-11-16 09:45:58 +08:00
caffix
a724ffab25 added changes based on PR comments to the proposal 2017-11-15 17:59:48 -05:00
Ethan Buchman
de34ef91d7 Merge pull request #854 from tendermint/add-go-version-to-readme
add Go version badge to README [ci skip]
2017-11-15 20:49:36 +00:00
Anton Kaliaev
248a9383a0 add Go version badge to README [ci skip] 2017-11-15 10:22:02 -06:00
Ethan Buchman
78b4ad291c Merge pull request #853 from tendermint/p2p-netPipe-own-file
p2p: netPipe for <Go1.10 in own file with own build tag
2017-11-15 16:09:48 +00:00
Emmanuel Odeke
3f9dff9aac p2p: netPipe for <Go1.10 in own file with own build tag
Follow up of 283544c7f3
putting <Go1.10 implementation of netPipe in its own
file and protect it with its separate build tag.
2017-11-14 22:23:48 -07:00
Ethan Buchman
443854222c Merge pull request #852 from tendermint/net-conn-SetDeadline-wraps
p2p: use fake net.Pipe since only >=Go1.10 implements SetDeadline
2017-11-15 05:09:39 +00:00
Emmanuel Odeke
283544c7f3 p2p: use fake net.Pipe since only >=Go1.10 implements SetDeadline
Fixes https://github.com/tendermint/tendermint/issues/851

Go1.9 and below's net.Pipe did not implement the SetDeadline
method so after commit
e2dd8ca946
this problem was exposed since now we check for errors.

To counter this problem, implement a simple composition for
net.Conn that always returns nil on SetDeadline instead of
tripping out.

Added build tags so that anyone using go1.10 when it is released
will be able to automatically use net.Pipe's net.Conns
2017-11-14 22:03:23 -07:00
Ethan Buchman
49faa79bdc Merge pull request #848 from tendermint/p2p-catch-conn.SetDeadline-errors
p2p: peer should respect errors from SetDeadline
2017-11-15 03:34:58 +00:00
Ethan Buchman
7670049a31 Merge pull request #845 from tendermint/fix/826-wait-for-rpc
rpc: wait for rpc servers to be available in tests
2017-11-15 03:29:05 +00:00
Ethan Buchman
0cd642bca7 Merge pull request #849 from tendermint/846-fix-TestFullRound1-race
fix TestFullRound1 race (Refs #846)
2017-11-15 03:27:59 +00:00
Anton Kaliaev
fe3c92ecce unescape $NODE_FLAGS (see comment) 2017-11-14 20:56:39 -06:00
Ethan Buchman
a969e24177 crank context timeouts 2017-11-15 01:42:15 +00:00
Emmanuel Odeke
7b0fa6c889 p2p: peer should respect errors from SetDeadline
Noticed while auditing the code that we aren't respecting
(*net.Conn) SetDeadline errors which return after
a connection has been killed and is simultaneously
being used.

For example given program, without SetDeadline error checks
```go
package main

import (
  "log"
  "net"
  "time"
)

func main() {
  conn, err := net.Dial("tcp", "tendermint.com:443")
  if err != nil {
    log.Fatal(err)
  }
  go func() {
    <-time.After(400 * time.Millisecond)
    conn.Close()
  }()
  for i := 0; i < 5; i++ {
    if err := conn.SetDeadline(time.Now().Add(time.Duration(10 * time.Second))); err != nil {
      log.Fatalf("set deadline #%d, err: %v", i, err)
    }
    log.Printf("Successfully set deadline #%d", i)
    <-time.After(150 * time.Millisecond)
  }
}
```

erraneously gives
```shell
2017/11/14 17:46:28 Successfully set deadline #0
2017/11/14 17:46:29 Successfully set deadline #1
2017/11/14 17:46:29 Successfully set deadline #2
2017/11/14 17:46:29 Successfully set deadline #3
2017/11/14 17:46:29 Successfully set deadline #4
```

However, if we properly fix it to respect that error with
```diff
--- wild.go 2017-11-14 17:44:38.000000000 -0700
+++ main.go 2017-11-14 17:45:40.000000000 -0700
@@ -16,7 +16,9 @@
    conn.Close()
  }()
  for i := 0; i < 5; i++ {
-   conn.SetDeadline(time.Now().Add(time.Duration(10 * time.Second)))
+   if err := conn.SetDeadline(time.Now().Add(time.Duration(10 *
time.Second))); err != nil {
+     log.Fatalf("set deadline #%d, err: %v", i, err)
+   }
    log.Printf("Successfully set deadline #%d", i)
    <-time.After(150 * time.Millisecond)
  }
```

properly catches any problems and gives
```shell
$ go run main.go
2017/11/14 17:43:44 Successfully set deadline #0
2017/11/14 17:43:45 Successfully set deadline #1
2017/11/14 17:43:45 Successfully set deadline #2
2017/11/14 17:43:45 set deadline #3, err: set tcp 10.182.253.51:57395:
use of closed network connection
exit status 1
```
2017-11-14 18:01:51 -07:00
Anton Kaliaev
fa60d8120e fix TestFullRound1 race (Refs #846)
```
==================
WARNING: DATA RACE
Write at 0x00c42d7605f0 by goroutine 844:
  github.com/tendermint/tendermint/consensus.(*ConsensusState).updateToState()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/state.go:465 +0x59e
I[11-14|22:37:28.781] Added to prevote                             vote="Vote{0:646753DCE124 1/02/1(Prevote) E9B19636DCDB {/CAD5FA805E8C.../}}" prevotes="VoteSet{H:1 R:2 T:1 +2/3:<nil> BA{2:X_} map[]}"
  github.com/tendermint/tendermint/consensus.(*ConsensusState).finalizeCommit()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/state.go:1229 +0x16a9
  github.com/tendermint/tendermint/consensus.(*ConsensusState).tryFinalizeCommit()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/state.go:1135 +0x721
  github.com/tendermint/tendermint/consensus.(*ConsensusState).enterCommit.func1()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/state.go:1087 +0x153
  github.com/tendermint/tendermint/consensus.(*ConsensusState).enterCommit()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/state.go:1114 +0xa34
  github.com/tendermint/tendermint/consensus.(*ConsensusState).addVote()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/state.go:1423 +0xdd6
  github.com/tendermint/tendermint/consensus.(*ConsensusState).tryAddVote()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/state.go:1317 +0x77
  github.com/tendermint/tendermint/consensus.(*ConsensusState).handleMsg()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/state.go:565 +0x7a9
  github.com/tendermint/tendermint/consensus.(*ConsensusState).receiveRoutine()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/state.go:523 +0x6d2

Previous read at 0x00c42d7605f0 by goroutine 654:
  github.com/tendermint/tendermint/consensus.validatePrevote()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/common_test.go:149 +0x57
  github.com/tendermint/tendermint/consensus.TestFullRound1()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/state_test.go:256 +0x3c5
  testing.tRunner()
      /usr/local/go/src/testing/testing.go:746 +0x16c

Goroutine 844 (running) created at:
  github.com/tendermint/tendermint/consensus.(*ConsensusState).startRoutines()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/state.go:258 +0x8c
  github.com/tendermint/tendermint/consensus.startTestRound()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/common_test.go:118 +0x63
  github.com/tendermint/tendermint/consensus.TestFullRound1()
      /home/vagrant/go/src/github.com/tendermint/tendermint/consensus/state_test.go:247 +0x1fb
  testing.tRunner()
      /usr/local/go/src/testing/testing.go:746 +0x16c

Goroutine 654 (running) created at:
  testing.(*T).Run()
      /usr/local/go/src/testing/testing.go:789 +0x568
  testing.runTests.func1()
      /usr/local/go/src/testing/testing.go:1004 +0xa7
  testing.tRunner()
      /usr/local/go/src/testing/testing.go:746 +0x16c
  testing.runTests()
      /usr/local/go/src/testing/testing.go:1002 +0x521
  testing.(*M).Run()
      /usr/local/go/src/testing/testing.go:921 +0x206
  main.main()
      github.com/tendermint/tendermint/consensus/_test/_testmain.go:106 +0x1d3
==================
```
2017-11-14 17:41:30 -06:00
caffix
8b7649b90c enhancements made in response to PR full review comments 2017-11-14 18:26:06 -05:00
caffix
687834c99e added initial trust metric test routines 2017-11-14 18:26:06 -05:00
caffix
54c25ccbf5 integrated trust metric store as per PR comments 2017-11-14 18:26:06 -05:00
caffix
e160a6198c added initial trust metric design doc and code 2017-11-14 18:26:06 -05:00
Ethan Buchman
e69d36d54f some more robust sleeps 2017-11-14 22:31:23 +00:00
Ethan Buchman
844c43e044 use stdlib context 2017-11-14 22:30:00 +00:00
Ethan Buchman
194712fd3b rpc: wait for rpc servers to be available in tests 2017-11-14 21:51:49 +00:00
Ethan Buchman
30f675aafa Merge pull request #839 from tendermint/bugfix/pubsub-failures
Fix nondeterministic tests failures related to pubsub
2017-11-14 18:13:47 +00:00
Ethan Buchman
695266e907 Merge pull request #844 from tendermint/bunch-up-p2p.AddrBook-wg-calls
p2p: comment on the wg.Add before go saveRoutine()
2017-11-14 17:18:27 +00:00
Ethan Buchman
3db44dacae Merge pull request #840 from tendermint/fix/tests
Fix/tests
2017-11-14 15:48:17 +00:00
Emmanuel Odeke
62c1bc0a20 p2p: comment on the wg.Add before go saveRoutine()
Just noticed while auditing the code in p2p/addrbook.go,
wg.Add(1) but no subsequent defer.
@jaekwon and I had a discussion offline and we agreed to
comment about why the code was that way and why
we shouldn't move the wg.Add(1) into .saveRoutine() because
if go a.saveRoutine() isn't started before anyone invokes
a.Wait(), then we'd have raced a.saveRoutine().
2017-11-13 18:14:58 -07:00
Petabyte Storage
3863885c71 WIP: begin parallel refactoring with go-wire Write methods and MConnection 2017-11-12 22:11:15 -08:00
Ethan Buchman
238e2b72ee Merge pull request #834 from tendermint/829-enable-logs-by-default
Enable logs by default
2017-11-12 07:06:14 +00:00
Ethan Buchman
a65ab3b0e0 Merge pull request #838 from tendermint/docker
docker update || 0.12.0
2017-11-12 06:51:01 +00:00
Ethan Buchman
aba8a8f4fc consensus: crank timeout in timeoutWaitGroup 2017-11-12 06:41:15 +00:00
Ethan Buchman
0448c2b437 consensus: fix LastCommit log 2017-11-12 06:40:27 +00:00
Ethan Buchman
0ada0cf525 certifiers: test uses WaitForHeight 2017-11-12 00:43:16 +00:00
Anton Kaliaev
7fa12662c4 check whatever we can read from the channel
```
panic: interface conversion: interface {} is nil, not types.TMEventData

goroutine 7690 [running]:
github.com/tendermint/tendermint/consensus.waitForAndValidateBlock.func1(0xc427727620, 0x3)
        /go/src/github.com/tendermint/tendermint/consensus/reactor_test.go:292 +0x62b
created by github.com/tendermint/tendermint/consensus.timeoutWaitGroup
        /go/src/github.com/tendermint/tendermint/consensus/reactor_test.go:349 +0xa4
exit status 2
FAIL    github.com/tendermint/tendermint/consensus      38.614s

```
2017-11-10 18:16:31 -05:00
Anton Kaliaev
bc9c4e8dee update readme [ci skip] 2017-11-10 15:38:32 -05:00
Anton Kaliaev
8004af2519 update docker readme 2017-11-10 15:17:13 -05:00
Anton Kaliaev
21e87ebc11 update Go version to 1.9.2 2017-11-10 15:10:52 -05:00
Anton Kaliaev
70d8afa6e9 update Dockerfile 2017-11-10 15:09:38 -05:00
Ethan Buchman
847f865438 Merge pull request #836 from tendermint/fix/tests
consensus: make mempool_test deterministic
2017-11-10 05:08:54 +00:00
Ethan Buchman
2cda777900 consensus: make mempool_test deterministic 2017-11-09 23:54:02 +00:00
Anton Kaliaev
432a7276e2 [test_integrations] enable logs from peers by default (Refs #829) 2017-11-09 15:19:49 -05:00
Anton Kaliaev
533f7c45eb fix bash linter warnings for atomic_broadcast integration test 2017-11-09 14:58:16 -05:00
Anton Kaliaev
a1cdc2b68a set logger for peer's MConnection 2017-11-09 14:57:40 -05:00
Ethan Buchman
9c4d533695 Merge pull request #833 from tendermint/fix/consensus-tests
consensus: fix for initializing block parts during catchup
2017-11-09 19:04:21 +00:00
Anton Kaliaev
ad03491ee6 remove duplicated key 2017-11-09 13:37:29 -05:00
Ethan Buchman
4b9dfc8990 consensus: fix for initializing block parts during catchup 2017-11-09 18:14:41 +00:00
Ethan Buchman
a46f64cd1e Merge pull request #824 from tendermint/bugfix/node_test
rewrite node test to use new pubsub
2017-11-09 01:35:35 +00:00
Anton Kaliaev
b1e7163689 rewrite node test to use new pubsub 2017-11-08 13:12:48 -05:00
Ethan Buchman
c931279960 p2p: some fixes re @odeke-em issues #813,#816,#817 2017-11-08 17:54:29 +00:00
Ethan Buchman
12b25fdf6e blockchain: add comment in AddPeer. closes #666 2017-11-08 02:42:27 +00:00
Ethan Buchman
c0e2649ed6 Merge pull request #788 from tendermint/feature/548-indexing-tags
new pubsub package
2017-11-08 01:02:48 +00:00
Ethan Buchman
593c127257 rpc/lib/types: RPCResponse.Result is not a pointer 2017-11-08 01:00:15 +00:00
Ethan Buchman
9f6a09277e Merge pull request #812 from tendermint/808-make-connected-switches
MakeConnectedSwitches: connect first switch to others
2017-11-08 00:54:23 +00:00
Ethan Buchman
dd47884661 Merge pull request #820 from tendermint/790-use-tickers-instead-of-time-Sleep
prefer tickers to time.Sleep
2017-11-08 00:53:42 +00:00
Anton Kaliaev
a01c226dc4 wsConnection: call onDisconnect 2017-11-07 19:22:01 -05:00
Ethan Buchman
47f5e37205 copy RoundState for event 2017-11-07 23:57:23 +00:00
Petabyte Storage
51c9211cf4 add test for MConnection TrySend and Send 2017-11-07 23:35:25 +00:00
Anton Kaliaev
7869e541f6 change MakeConnectedSwitches to not connect to itself
and a test for it
2017-11-07 18:33:00 -05:00
Anton Kaliaev
e0daca5693 fixes from Bucky's review 2017-11-07 18:20:24 -05:00
Ethan Buchman
e8e512f1fa Merge pull request #815 from tendermint/p2p-readme-tests
P2P: readme and tests
2017-11-07 23:01:15 +00:00
Ethan Buchman
37ce171061 p2p/connetion: remove panics, test error cases 2017-11-07 23:00:52 +00:00
Ethan Buchman
e01986e2b3 p2p: update readme, some minor things 2017-11-07 23:00:49 +00:00
Ethan Buchman
433416fef8 Merge pull request #818 from tendermint/fix/810-stuck-trailing-node
consensus: ensure prs.ProposalBlockParts is initialized. fixes #810
2017-11-07 21:52:08 +00:00
Anton Kaliaev
2d4ad02356 prefer tickers to time.Sleep (Refs #790) 2017-11-07 15:38:25 -05:00
Ethan Buchman
3b81d3fea4 consensus: ensure prs.ProposalBlockParts is initialized. fixes #810 2017-11-07 17:14:40 +00:00
Anton Kaliaev
e785697a64 connect first switch to others (Refs #808) 2017-11-06 23:43:40 -05:00
Anton Kaliaev
4ffe9304ba unsubscribe from all subscriptions on WS disconnect 2017-11-02 14:00:18 -05:00
Anton Kaliaev
b1eec3a5d3 remove test_data/empty_block and test_data/small_blockN 2017-11-02 13:20:14 -05:00
Anton Kaliaev
fcdd30b2d3 fixes from Bucky's review 2 2017-11-02 13:20:05 -05:00
Ethan Buchman
ec87c740a7 Merge pull request #794 from tendermint/243-restart-app-via-os
Kill Tendermint when App dies
2017-10-31 16:27:23 -04:00
Ethan Buchman
6b737d2c1b Merge pull request #745 from tendermint/test-rpc-server-handlers
rpc/lib/server: add handlers tests for params inclusion
2017-10-31 15:42:24 -04:00
Ethan Buchman
f7f4ba5e90 rpc/lib/server: minor changes to test 2017-10-31 15:41:25 -04:00
Ethan Buchman
5466720d75 minor changes from @odeke-em PR #725 2017-10-31 15:32:07 -04:00
Ethan Buchman
7c3cf316f1 rpc/wsevents: small cleanup 2017-10-31 15:16:08 -04:00
Ethan Buchman
d71aed309f some minor changes 2017-10-30 22:52:03 -04:00
Ethan Buchman
d6beb60bf7 Merge pull request #799 from petabytestorage/fix-typo-switch-comment
fix comment typos
2017-10-30 18:01:32 -04:00
Anton Kaliaev
61d76a273f fixes from Bucky's and Emmanuel's reviews 2017-10-30 11:12:01 -05:00
Anton Kaliaev
6d18e2f447 do not send whole round state via eventHub
Fixes

```
WARNING: DATA RACE
Write at 0x00c4200715b8 by goroutine 24:
  github.com/tendermint/tendermint/consensus.(*ConsensusState).enterPrevote.func1()
      /go/src/github.com/tendermint/tendermint/consensus/state.go:359 +0x3f
  github.com/tendermint/tendermint/consensus.(*ConsensusState).enterPrevote()
      /go/src/github.com/tendermint/tendermint/consensus/state.go:897 +0x8de
  github.com/tendermint/tendermint/consensus.(*ConsensusState).addProposalBlockPart()
      /go/src/github.com/tendermint/tendermint/consensus/state.go:1303 +0x701
  github.com/tendermint/tendermint/consensus.(*ConsensusState).handleMsg()
      /go/src/github.com/tendermint/tendermint/consensus/state.go:560 +0x88c
  github.com/tendermint/tendermint/consensus.(*ConsensusState).receiveRoutine()
      /go/src/github.com/tendermint/tendermint/consensus/state.go:525 +0x6d2

Previous read at 0x00c4200715b8 by goroutine 19:
  github.com/tendermint/tendermint/consensus.makeRoundStepMessages()
      /go/src/github.com/tendermint/tendermint/consensus/reactor.go:415 +0x192
  github.com/tendermint/tendermint/consensus.(*ConsensusReactor).broadcastNewRoundStep()
      /go/src/github.com/tendermint/tendermint/consensus/reactor.go:377 +0x3c
  github.com/tendermint/tendermint/consensus.(*ConsensusReactor).broadcastNewRoundStepsAndVotes.func1()
      /go/src/github.com/tendermint/tendermint/consensus/reactor.go:350 +0x275
```
2017-10-30 00:32:23 -05:00
Anton Kaliaev
1c1c68df8d fixes from my own review 2017-10-30 00:32:23 -05:00
Anton Kaliaev
f6539737de new pubsub package
comment out failing consensus tests for now

rewrite rpc httpclient to use new pubsub package

import pubsub as tmpubsub, query as tmquery

make event IDs constants
EventKey -> EventTypeKey

rename EventsPubsub to PubSub

mempool does not use pubsub

rename eventsSub to pubsub

new subscribe API

fix channel size issues and consensus tests bugs

refactor rpc client

add missing discardFromChan method

add mutex

rename pubsub to eventBus

remove IsRunning from WSRPCConnection interface (not needed)

add a comment in broadcastNewRoundStepsAndVotes

rename registerEventCallbacks to broadcastNewRoundStepsAndVotes

See https://dave.cheney.net/2014/03/19/channel-axioms

stop eventBuses after reactor tests

remove unnecessary Unsubscribe

return subscribe helper function

move discardFromChan to where it is used

subscribe now returns an err

this gives us ability to refuse to subscribe if pubsub is at its max
capacity.

use context for control overflow

cache queries

handle err when subscribing in replay_test

rename testClientID to testSubscriber

extract var

set channel buffer capacity to 1 in replay_file

fix byzantine_test

unsubscribe from single event, not all events

refactor httpclient to return events to appropriate channels

return failing testReplayCrashBeforeWriteVote test

fix TestValidatorSetChanges

refactor code a bit

fix testReplayCrashBeforeWriteVote

add comment

fix TestValidatorSetChanges

fixes from Bucky's review

update comment [ci skip]

test TxEventBuffer

update changelog

fix TestValidatorSetChanges (2nd attempt)

only do wg.Done when no errors

benchmark event bus

create pubsub server inside NewEventBus

only expose config params (later if needed)

set buffer capacity to 0 so we are not testing cache

new tx event format: key = "Tx" plus a tag {"tx.hash": XYZ}

This should allow to subscribe to all transactions! or a specific one
using a query: "tm.events.type = Tx and tx.hash = '013ABF99434...'"

use TimeoutCommit instead of afterPublishEventNewBlockTimeout

TimeoutCommit is the time a node waits after committing a block, before
it goes into the next height. So it will finish everything from the last
block, but then wait a bit. The idea is this gives it time to hear more
votes from other validators, to strengthen the commit it includes in the
next block. But it also gives it time to hear about new transactions.

waitForBlockWithUpdatedVals

rewrite WAL crash tests

Task:
test that we can recover from any WAL crash.

Solution:
the old tests were relying on event hub being run in the same thread (we
were injecting the private validator's last signature).

when considering a rewrite, we considered two possible solutions: write
a "fuzzy" testing system where WAL is crashing upon receiving a new
message, or inject failures and trigger them in tests using something
like https://github.com/coreos/gofail.

remove sleep

no cs.Lock around wal.Save

test different cases (empty block, non-empty block, ...)

comments

add comments

test 4 cases: empty block, non-empty block, non-empty block with smaller part size, many blocks

fixes as per Bucky's last review

reset subscriptions on UnsubscribeAll

use a simple counter to track message for which we panicked

also, set a smaller part size for all test cases
2017-10-30 00:32:22 -05:00
Petabyte Storage
fe9ff62297 fix comment typos 2017-10-28 22:01:45 -07:00
Ethan Buchman
7c85f15a6c Merge pull request #798 from petabytestorage/fix-test-uncommon-names
fix test using uncommon names
2017-10-28 23:47:31 -04:00
Petabyte Storage
6b366b2443 fix test using uncommon names 2017-10-28 20:29:11 -07:00
Emmanuel Odeke
a8b77359df rpc/lib/server: separate out Notifications test
Addressing feedback from @ebuchman
2017-10-28 15:24:40 -07:00
Emmanuel Odeke
e7fab7d4bf rpc/lib/server: update with @melekes and @ebuchman feedback 2017-10-28 15:11:21 -07:00
Emmanuel Odeke
59556ab030 rpc/lib/server: add handlers tests
Follow up of PR https://github.com/tendermint/tendermint/pull/724
For https://github.com/tendermint/tendermint/issues/708

Reported initially in #708, this bug was reconfirmed
by the fuzzer.

This fix ensures that:
* if the user doesn't pass in `"id"` that we send them back
a message in an error telling them to send `"id"`. Previously
we let the handler return a 200 with nothing.
* passing in nil `params` doesn't crash
* not passing in `params` doesn't crash
* passing in non-JSON parseable data to `params` doesn't crash
2017-10-28 15:11:21 -07:00
Ethan Buchman
128e2a1d9e Merge branch 'master' into develop 2017-10-28 00:09:03 -04:00
Ethan Buchman
e236302256 Merge pull request #793 from tendermint/release-v0.12.0
Release v0.12.0
2017-10-28 00:06:53 -04:00
Ethan Buchman
dfe28c8855 test: update for abci-cli consolidation. shell formatting 2017-10-27 23:09:50 -04:00
Ethan Buchman
4b616344fa update glide, again 2017-10-27 22:36:03 -04:00
Ethan Buchman
1ecd580061 Merge pull request #773 from tendermint/docs-staging
docs improvements
2017-10-27 16:18:56 -04:00
Ethan Buchman
21dcb4f290 update glide 2017-10-27 13:55:56 -04:00
Ethan Buchman
b2b35d7dc1 update changelog 2017-10-27 11:54:20 -04:00
Ethan Buchman
a1501dcde8 version bump 2017-10-27 11:54:20 -04:00
Ethan Buchman
3319ad03b8 Merge pull request #791 from tendermint/740-no-wal-after-fast-sync
dont catchupReplay on wal if we fast synced
2017-10-27 11:49:54 -04:00
Ethan Buchman
fe1c60b5cf consensus: kill process on app error 2017-10-27 10:55:20 -04:00
Ethan Buchman
591dd9e662 dont catchupReplay on wal if we fast synced 2017-10-27 10:46:19 -04:00
Ethan Buchman
bb6c15b00a CHANGELOG [ci skip] 2017-10-26 09:42:46 -04:00
Ethan Buchman
6af28ead87 Merge pull request #672 from tendermint/573-wal-issues
Add checksum and length to CS WAL record
2017-10-26 00:31:38 -04:00
Ethan Buchman
fcf459158d CHANGELOG [ci skip] 2017-10-26 00:29:58 -04:00
Ethan Buchman
e76ef2a8a1 types: unexpose valset.To/FromBytes 2017-10-26 00:27:02 -04:00
Ethan Buchman
3c92bea519 glide: more external deps locked to versions 2017-10-26 00:07:43 -04:00
Ethan Buchman
12c703c1c3 Merge branch 'develop' into 573-wal-issues 2017-10-25 23:56:08 -04:00
Ethan Buchman
376f47e030 Merge pull request #775 from tendermint/rpc-client-jitter
rpc/lib/client: add jitter for exponential backoff of WSClient
2017-10-25 22:53:50 -04:00
Petabyte Storage
ceedd4d968 remove unnecessary plus [ci skip] 2017-10-25 22:28:20 -04:00
Ethan Buchman
c595636999 glide 2017-10-25 22:23:55 -04:00
Emmanuel Odeke
6e5cd10399 rpc/lib/client: jitter test updates and only to-be run on releases
* Updated code with feedback from @melekes, @ebuchman and @silasdavis.
* Added Makefile clause `release` to only run the test on seeing tag
`release` during releases i.e
```shell
make release
```
which will run the comprehensive and long integration-ish tests.
2017-10-25 19:20:55 -07:00
Ethan Buchman
57a684d5ac fixes from review 2017-10-25 21:54:56 -04:00
Ethan Buchman
5534eb4707 Merge pull request #776 from tendermint/feature/merge-light-client
Merge light client
2017-10-25 16:12:39 -04:00
Ethan Buchman
b2d5546cf8 Merge pull request #777 from silasdavis/fix-blocking-ws-client
Fix WSClient deadlock in the readRoutine after Stop() is called
2017-10-25 11:00:30 -04:00
Ethan Frey
f653ba63bf Separated out certifiers.Commit from rpc structs 2017-10-25 16:43:18 +02:00
Ethan Frey
0396b6d521 Rename checkpoint.go 2017-10-25 16:13:04 +02:00
Ethan Frey
94b36bb65e Move VerifyCommitAny into the types package 2017-10-25 16:13:04 +02:00
Ethan Frey
b4fd6e876e Copy certifiers from light-client 2017-10-25 16:13:04 +02:00
Ethan Buchman
775e100d2c Merge pull request #783 from tendermint/782-tendermint-invalid-command-panics
fix panic: failed to determine gopath: exec: "go"
2017-10-25 08:50:16 -04:00
Silas Davis
4cb02d0bf2 Exploit the fact the BaseService's closed Quit channel will keep emitting quit signals to close both readRoutine and writeRoutine 2017-10-25 10:19:18 +01:00
Anton Kaliaev
ae538337ba fix panic: failed to determine gopath: exec: "go" (Refs #782)
```
-bash-4.2$ tendermint show_validators
panic: failed to determine gopath: exec: "go": executable file not found in $PATH

goroutine 1 [running]:
github.com/tendermint/tendermint/vendor/github.com/tendermint/tmlibs/common.gopath(0xc4200632c0, 0x18)
	/var/lib/jenkins/workspace/03.Build.Package/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/tmlibs/common/os.go:26 +0x1b5
github.com/tendermint/tendermint/vendor/github.com/tendermint/tmlibs/common.init()
	/var/lib/jenkins/workspace/03.Build.Package/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/tmlibs/common/os.go:17 +0x13c
github.com/tendermint/tendermint/vendor/github.com/tendermint/go-wire.init()
	/var/lib/jenkins/workspace/03.Build.Package/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-wire/wire.go:165 +0x50
github.com/tendermint/tendermint/vendor/github.com/tendermint/go-wire/data.init()
	/var/lib/jenkins/workspace/03.Build.Package/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-wire/data/wrapper.go:89 +0x50
github.com/tendermint/tendermint/vendor/github.com/tendermint/tmlibs/cli.init()
	/var/lib/jenkins/workspace/03.Build.Package/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/tmlibs/cli/setup.go:190 +0x76
main.init()
	/var/lib/jenkins/workspace/03.Build.Package/go/src/github.com/tendermint/tendermint/cmd/tendermint/main.go:42 +0x49```

An error message instead would be nice.
```

Now GoPath() is a function instead of a variable.
2017-10-25 11:19:53 +04:00
Ethan Buchman
62a7beec21 Merge pull request #780 from ericdmann/769-error-msg-while-testnet-sync
Change log level to Info when proposal block hashing fails
2017-10-24 23:27:20 -04:00
Eric Mann
45e18a1832 Change log level to Info when proposal block hashing fails due to partially complete block 2017-10-24 14:13:35 -07:00
Silas Davis
f6adddb4a8 Replace ResultsCh with ResponsesCh 2017-10-24 17:45:13 +01:00
Ethan Buchman
38fc351532 Merge pull request #765 from tendermint/762-blockchain-reactor-timeout
blockchain reactor timeout
2017-10-24 09:13:26 -04:00
Silas Davis
01be6fa309 Fix WSClient blocking in the readRoutine after Stop() as it tries to write to ResultsCh 2017-10-24 13:31:24 +01:00
Anton Kaliaev
e06bbaf303 refactor TestNoBlockMessageResponse to eliminate a race condition 2017-10-24 15:32:01 +04:00
Anton Kaliaev
bb7b152af5 write docs for cutWALUntil and wal2json binaries 2017-10-24 13:25:47 +04:00
Emmanuel Odeke
5504920ba3 rpc/lib/client: add jitter for exponential backoff of WSClient
Fixes https://github.com/tendermint/tendermint/issues/751.

Adds jitter to our exponential backoff to mitigate a self DDOS
vector. The jitter is a randomly picked percentage of a second
whose purpose is to ensure that each exponential backoff retry
occurs within (1<<attempts) == 2**attempts, but with the delay
each client will have a random buffer time before it tries to
reconnect instead of all at once reconnections that might even
bring back the previous conditions that might have caused the
dial to the WSServer to have failed e.g
* Network outage
* File descriptor exhaustion
* False positives from firewalls
etc
2017-10-24 02:00:20 -07:00
Anton Kaliaev
c74a359c46 fixes per Bucky's review 2017-10-24 12:14:21 +04:00
Zach Ramsay
ee9dc6ce59 docs: fixup abci guide 2017-10-23 20:56:49 -04:00
Zach Ramsay
62e8ec34d1 fix comment, #723 2017-10-23 19:51:09 -04:00
Matt Bell
6a5254c475 Added local blockchain sync benchmark script 2017-10-23 19:46:57 -04:00
Ethan Buchman
2802a06a08 blockchain/store: comment about panics 2017-10-23 19:46:14 -04:00
Zach
8ac430813d Merge pull request #772 from tendermint/docs/flow
moar docs updates
2017-10-23 19:14:06 -04:00
Zach Ramsay
3e61b8c17a docs: comb through step by step 2017-10-23 19:11:51 -04:00
Zach Ramsay
9e277d1596 docs: smaller logo (200px) 2017-10-23 17:34:27 -04:00
Zach
4c9d5244a5 Merge pull request #759 from tendermint/improve-docs
docs: update abci example details
2017-10-23 17:29:34 -04:00
Ethan Buchman
87cc277b38 Merge pull request #721 from tendermint/564-add-app-options-to-genesis-resp
Add app_options to GenesisDoc
2017-10-23 16:03:45 -04:00
Anton Kaliaev
3115c23762 binary format for WAL 2017-10-23 22:27:24 +04:00
Anton Kaliaev
31030c6514 make crc32c a global var
change echo format in build.sh script
2017-10-23 22:09:42 +04:00
Anton Kaliaev
7b8ffc9981 add checksum and msg size to TimedWALMessage
updated test_data/build.sh script
2017-10-23 22:09:17 +04:00
Ethan Buchman
a75bccfbc4 Merge branch 'develop' into 564-add-app-options-to-genesis-resp 2017-10-23 11:30:00 -04:00
Ethan Buchman
f97229f05a Merge pull request #748 from tendermint/params-test
types: ConsensusParams test + document the ranges/limits
2017-10-23 11:18:00 -04:00
Ethan Buchman
ac2ef9e0ea Merge pull request #750 from tendermint/feature/cleanup
Cleanup of code and code docs
2017-10-23 11:14:15 -04:00
Ethan Buchman
c2803b80e8 update changelog; fixes from rebase 2017-10-23 11:13:12 -04:00
Ethan Buchman
7a6876bc62 Merge pull request #768 from tendermint/feature/merkleeyes-to-iavl
Feature/merkleeyes to iavl
2017-10-23 11:07:21 -04:00
Adrian Brink
819f81f702 Change NOTE to CONTRACT 2017-10-23 11:04:45 -04:00
Adrian Brink
036d3b59a3 Address reviews 2017-10-23 11:04:45 -04:00
Adrian Brink
782a836db0 Cleanup of code and code docs
This cleans up some of the code in the state package
2017-10-23 11:04:45 -04:00
Ethan Buchman
bd46b78785 Merge pull request #755 from tendermint/753-notified-mempool-txs-but-mempool-empty
WIP: only notify when there are some txs (Refs #753)
2017-10-23 10:31:38 -04:00
Anton Kaliaev
f908dd0e55 only notify when there are some txs (Refs #753) 2017-10-23 10:31:00 -04:00
Ethan Buchman
0bbf38141a blockchain/pool: some comments and small changes 2017-10-23 10:13:46 -04:00
Ethan Buchman
f188366e26 update glide 2017-10-23 10:04:00 -04:00
Ethan Buchman
fd60621a8e update cswal test 2017-10-23 10:03:54 -04:00
Ethan Buchman
60b7f2c61b Merge pull request #767 from silasdavis/do-not-swallow
Make RPCError an actual error and don't swallow its companion data
2017-10-23 01:51:40 -04:00
Silas Davis
3e3d53daef Make RPCError an actual error and don't swallow its companion data 2017-10-22 15:14:21 +01:00
Anton Kaliaev
d64a48e0ee set logger on blockchain pool 2017-10-20 23:56:21 +04:00
Anton Kaliaev
0a7b2ab52c fix invalid memory address or nil pointer dereference error (Refs #762)
https://github.com/tendermint/tendermint/issues/762#issuecomment-338276055
```
E[10-19|04:52:38.969] Stopping peer for error                      module=p2p peer="Peer{MConn{178.62.46.14:46656} B14916FAF38A out}" err="Error: runtime error: invalid memory address or nil pointer dereference\nStack: goroutine 529485 [running]:\nruntime/debug.Stack(0xc4355cfb38, 0xb463e0, 0x11b1c30)\n\t/usr/local/go/src/runtime/debug/stack.go:24 +0xa7\ngithub.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/p2p.(*MConnection)._recover(0xc439a28870)\n\t/home/ubuntu/go/src/github.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/p2p/connection.go:206 +0x6e\npanic(0xb463e0, 0x11b1c30)\n\t/usr/local/go/src/runtime/panic.go:491 +0x283\ngithub.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/blockchain.(*bpPeer).decrPending(0x0, 0x381)\n\t/home/ubuntu/go/src/github.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/blockchain/pool.go:376 +0x22\ngithub.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/blockchain.(*BlockPool).AddBlock(0xc4200e4000, 0xc4266d1f00, 0x40, 0xc432ac9640, 0x381)\n\t/home/ubuntu/go/src/github.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/blockchain/pool.go:215 +0x139\ngithub.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/blockchain.(*BlockchainReactor).Receive(0xc42050a780, 0xc420257740, 0x1171be0, 0xc42ff302d0, 0xc4384b2000, 0x381, 0x1000)\n\t/home/ubuntu/go/src/github.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/blockchain/reactor.go:160 +0x712\ngithub.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/p2p.createMConnection.func1(0x11e5040, 0xc4384b2000, 0x381, 0x1000)\n\t/home/ubuntu/go/src/github.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/p2p/peer.go:334 +0xbd\ngithub.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/p2p.(*MConnection).recvRoutine(0xc439a28870)\n\t/home/ubuntu/go/src/github.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/p2p/connection.go:475 +0x4a3\ncreated by github.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/p2p.(*MConnection).OnStart\n\t/home/ubuntu/go/src/github.com/cosmos/gaia/vendor/github.com/tendermint/tendermint/p2p/connection.go:170 +0x187\n"
```
2017-10-20 21:56:10 +04:00
Zach Ramsay
8a69f1087b docs: typo 2017-10-20 07:56:26 -04:00
Emmanuel Odeke
f24f03906f types: ConsensusParams: add feedback from @ebuchman and @melekes 2017-10-20 00:11:30 -06:00
Ethan Buchman
fa56e8c0ce Merge pull request #676 from tendermint/state-unexpose-genesisDoc-chainID
all, state: unexpose GenesisDoc, ChainID fields make them accessor methods
2017-10-18 20:10:02 -04:00
Zach Ramsay
fc406d1657 docs: update abci example details [ci skip] 2017-10-18 16:33:37 -04:00
Zach
9dcefd0e1e Merge pull request #754 from tendermint/improve-docs
add tm-migrator to docs
2017-10-18 13:04:12 -04:00
Zach
a2dc53d43d Merge pull request #757 from tendermint/756-specification-validators
correct an error in validator's specification [ci skip] (Refs #756)
2017-10-18 13:02:13 -04:00
Anton Kaliaev
b9c4fab96e correct an error in validator's specification [ci skip] (Refs #756) 2017-10-18 19:23:30 +04:00
Zach Ramsay
fa07dbd7ec docs: add info about tm-migrate 2017-10-18 08:47:58 -04:00
Zach Ramsay
9b382d7a11 docs: remove mention of type byte 2017-10-18 08:00:01 -04:00
Anton Kaliaev
75b78bfb72 panic on marshal/unmarshal failures for genesisDoc 2017-10-17 13:33:57 +04:00
Ethan Buchman
b234f7aba2 Merge pull request #741 from tendermint/client-compile-time-assertions
rpc/client: use compile time assertions instead of methods
2017-10-17 03:41:24 -04:00
Emmanuel Odeke
bff069f83c types: ConsensusParams test + document the ranges/limits
Fixes https://github.com/tendermint/tendermint/issues/747
Updates https://github.com/tendermint/tendermint/issues/693

* Document the unmentioned limits for ConsensusParams.Validate()
* Make the limit for ConsensusParams.BlockSizeParams.MaxBytes
clear at 100MiB
2017-10-16 16:57:44 -06:00
Anton Kaliaev
616b07ff6b make AppOptions an interface{} 2017-10-16 10:58:52 +04:00
Anton Kaliaev
b26f812399 update changelog 2017-10-16 10:58:52 +04:00
Anton Kaliaev
321061125f add app_options to GenesisDoc (Refs #564) 2017-10-16 10:58:52 +04:00
Anton Kaliaev
6469e2ccca save genesis doc in DB to prevent user errors
https://github.com/tendermint/tendermint/pull/676#discussion_r144411458
2017-10-16 10:51:58 +04:00
Anton Kaliaev
c4646bf87f make state#Params not a pointer
also remove the comment
2017-10-16 10:34:02 +04:00
Anton Kaliaev
716364182d [state] expose ChainID and Params
```
jaekwon
Yeah we should definitely expose ChainID.
ConsensusParams is small enough, we can just write it.
```
https://github.com/tendermint/tendermint/pull/676#discussion_r144123203
2017-10-16 10:34:02 +04:00
Anton Kaliaev
1971e149fb ChainID() and Params() do not return errors
- remove state#GenesisDoc() method
2017-10-16 10:34:02 +04:00
Emmanuel Odeke
7939d62ef0 all, state: unexpose GenesisDoc, ChainID fields make them accessor methods
Fixes #671

Unexpose GenesisDoc and ChainID fields to avoid them being
serialized to the DB on every block write/state.Save()

A GenesisDoc can now be alternatively written to the state's
database, by serializing its JSON as a value of key "genesis-doc".

There are now accessors and a setter for these attributes:
- state.GenesisDoc() (*types.GenesisDoc, error)
- state.ChainID() (string, error)
- state.SetGenesisDoc(*types.GenesisDoc)

This is a breaking change since it changes how the state's
serialization and requires that if loading the GenesisDoc entirely
from the database, you'll need to set its value in the database
as the GenesisDoc's JSON marshaled bytes.
2017-10-16 10:34:01 +04:00
Zach
4c1f1e4e57 Merge pull request #746 from srmo/701-add-dev-docs-in-java
701 add dev docs in java
2017-10-15 11:02:36 -04:00
Zach
09170f76fe Merge pull request #743 from tendermint/zramsay-patch-1
Update getting-started.rst
2017-10-15 11:01:19 -04:00
srmo
9e1edf8685 [docs] add Java examples for each section 2017-10-15 13:45:43 +02:00
srmo
e7fe299504 [docs] replace all GO snippets with collapsible blocks 2017-10-15 12:21:06 +02:00
srmo
b90edffe28 [docs] add first java block for deliverTx 2017-10-15 12:00:08 +02:00
srmo
f361092ed9 [docs] provide means to have collapsible code blocks without adding a new theme 2017-10-15 11:59:37 +02:00
Ethan Buchman
a1e0f0ba95 docs/ecosystem: add py-tendermint to abci-servers 2017-10-14 00:59:34 -04:00
Emmanuel Odeke
5f218a43fd rpc/client: use compile time assertions instead of methods 2017-10-13 14:30:54 -06:00
Zach
7fe470fc76 Update getting-started.rst 2017-10-13 14:50:54 -04:00
Ethan Buchman
d490c25807 Merge pull request #720 from tendermint/types-heartbeat-test
types/heartbeat: test all Heartbeat functions
2017-10-13 09:22:59 -04:00
Ethan Buchman
340f33b475 Merge pull request #734 from tendermint/482-support-historical-abci-queries
support historical abci queries
2017-10-13 09:14:32 -04:00
Anton Kaliaev
7518c4a9be [rpc] update comment [ci skip] 2017-10-13 15:03:21 +04:00
Anton Kaliaev
db413aadfd fixes from @cloudhead review 2017-10-13 15:03:21 +04:00
Anton Kaliaev
5433e5771e support historical abci queries (Refs #482) 2017-10-13 15:03:20 +04:00
Zach Ramsay
e2e50bc0fc rpc: use /iavl repo in test (#713) 2017-10-11 10:35:22 -04:00
Ethan Buchman
27245ce6f6 Merge branch 'master' into develop 2017-10-10 19:12:40 -04:00
Ethan Buchman
d4634dc683 Merge pull request #729 from tendermint/release/0.11.1
Release/0.11.1
2017-10-10 18:50:15 -04:00
Ethan Buchman
8c08fc671c fix version 2017-10-10 18:49:08 -04:00
Ethan Buchman
a2d40580d7 Merge pull request #732 from sbellem/docs-install-typo-fix
[docs: typo fix] add missing "have"
2017-10-10 11:22:39 -04:00
Ethan Buchman
0011af7adf Merge pull request #727 from sbellem/docs-typo-fix
[docs:typo fix] remove misplaced "the"
2017-10-10 11:20:34 -04:00
Sylvain Bellemare
1764106606 [docs: typo fix] add missing "have" 2017-10-10 17:15:35 +02:00
Ethan Buchman
3356544706 update changelog 2017-10-10 11:10:48 -04:00
Ethan Buchman
335e012b6a Merge branch 'develop' into release/0.11.1 2017-10-10 11:08:14 -04:00
Ethan Buchman
a458da8f92 Merge pull request #724 from tendermint/708-leaving-out-params-crashes-tm-rpc
Leaving out params crashes tm rpc
2017-10-10 10:53:21 -04:00
Ethan Buchman
9fb45c5b5a remove a stale comment 2017-10-10 10:52:26 -04:00
Anton Kaliaev
aae4e94998 make RPCRequest params not a pointer
https://github.com/tendermint/tendermint/pull/724#issuecomment-335362927
2017-10-10 13:50:06 +04:00
Anton Kaliaev
d935a4f0a8 recover from panic in WS JSON RPC readRoutine
https://github.com/tendermint/tendermint/pull/724#issuecomment-335316484
2017-10-10 13:48:56 +04:00
Anton Kaliaev
5c331d8276 log a notification to help debug user issues 2017-10-10 13:01:25 +04:00
Anton Kaliaev
13b9de6778 return missing package declaration 2017-10-10 12:48:36 +04:00
Anton Kaliaev
dc0e8de9b0 extract some of the consensus types into ./types
so they can be used in rpc/core/types/responses.go.

```
So, it seems like we could use the actual structs here, but we don't want to have to import consensus to get them, as then clients are importing too much crap. So probably we should move some types from consensus into consensus/types so we can import.

Will these raw messages be identical to:

type ResultDumpConsensusState struct {
  RoundState cstypes.RoundState
  PeerRoundStates map[string]cstypes.PeerRoundState
}
```
https://github.com/tendermint/tendermint/pull/724#discussion_r143598193
2017-10-10 12:39:21 +04:00
Anton Kaliaev
90a2335267 bump version to 0.11.1 2017-10-10 01:18:33 +04:00
Anton Kaliaev
99c4e48038 return missing package declaration 2017-10-10 01:14:42 +04:00
Anton Kaliaev
4bd4d59af5 update changelog [ci skip] 2017-10-10 01:14:00 +04:00
Sylvain Bellemare
8219abc552 [docs:typo fix] remove misplaced "the" 2017-10-09 20:06:43 +02:00
Anton Kaliaev
d6a87d3c43 [rpc] DumpConsensusState: output state as json rather than string
Before:

```
{
  "jsonrpc": "2.0",
  "id": "",
  "result": {
    "round_state": "RoundState{\n  H:10 R:0 S:RoundStepNewHeight\n  StartTime:     2017-10-09 13:07:24.841134374 +0400 +04\n  CommitTime:    2017-10-09 13:07:23.841134374 +0400 +04\n  Validators:    ValidatorSet{\n      Proposer: Validator{EF243CC0E9B88D0161D24D733BDE9003518CEA27 {PubKeyEd25519{2E0B9301334FCDAB193D514022F81BA09BBEC028685C96602BE9DD0BD4F9E202}} VP:10 A:0}\n      Validators:\n        Validator{EF243CC0E9B88D0161D24D733BDE9003518CEA27 {PubKeyEd25519{2E0B9301334FCDAB193D514022F81BA09BBEC028685C96602BE9DD0BD4F9E202}} VP:10 A:0}\n    }\n  Proposal:      \u003cnil\u003e\n  ProposalBlock: nil-PartSet nil-Block\n  LockedRound:   0\n  LockedBlock:   nil-PartSet nil-Block\n  Votes:         HeightVoteSet{H:10 R:0~0\n      VoteSet{H:10 R:0 T:1 +2/3:\u003cnil\u003e BA{1:_} map[]}\n      VoteSet{H:10 R:0 T:2 +2/3:\u003cnil\u003e BA{1:_} map[]}\n    }\n  LastCommit: VoteSet{H:9 R:0 T:2 +2/3:947F67A7B85439AF2CD5DFED376C51AC7BD67AEE:1:365E9983E466 BA{1:X} map[]}\n  LastValidators:    ValidatorSet{\n      Proposer: Validator{EF243CC0E9B88D0161D24D733BDE9003518CEA27 {PubKeyEd25519{2E0B9301334FCDAB193D514022F81BA09BBEC028685C96602BE9DD0BD4F9E202}} VP:10 A:0}\n      Validators:\n        Validator{EF243CC0E9B88D0161D24D733BDE9003518CEA27 {PubKeyEd25519{2E0B9301334FCDAB193D514022F81BA09BBEC028685C96602BE9DD0BD4F9E202}} VP:10 A:0}\n    }\n}",
    "peer_round_states": []
  }
}
```

After:

```
{
  "jsonrpc": "2.0",
  "id": "",
  "result": {
    "round_state": {
      "Height": 1691,
      "Round": 0,
      "Step": 1,
      "StartTime": "2017-10-09T14:08:09.129491764+04:00",
      "CommitTime": "2017-10-09T14:08:08.129491764+04:00",
      "Validators": {
        "validators": [
          {
            "address": "EF243CC0E9B88D0161D24D733BDE9003518CEA27",
            "pub_key": {
              "type": "ed25519",
              "data": "2E0B9301334FCDAB193D514022F81BA09BBEC028685C96602BE9DD0BD4F9E202"
            },
            "voting_power": 10,
            "accum": 0
          }
        ],
        "proposer": {
          "address": "EF243CC0E9B88D0161D24D733BDE9003518CEA27",
          "pub_key": {
            "type": "ed25519",
            "data": "2E0B9301334FCDAB193D514022F81BA09BBEC028685C96602BE9DD0BD4F9E202"
          },
          "voting_power": 10,
          "accum": 0
        }
      },
      "Proposal": null,
      "ProposalBlock": null,
      "ProposalBlockParts": null,
      "LockedRound": 0,
      "LockedBlock": null,
      "LockedBlockParts": null,
      "Votes": {},
      "CommitRound": -1,
      "LastCommit": {},
      "LastValidators": {
        "validators": [
          {
            "address": "EF243CC0E9B88D0161D24D733BDE9003518CEA27",
            "pub_key": {
              "type": "ed25519",
              "data": "2E0B9301334FCDAB193D514022F81BA09BBEC028685C96602BE9DD0BD4F9E202"
            },
            "voting_power": 10,
            "accum": 0
          }
        ],
        "proposer": {
          "address": "EF243CC0E9B88D0161D24D733BDE9003518CEA27",
          "pub_key": {
            "type": "ed25519",
            "data": "2E0B9301334FCDAB193D514022F81BA09BBEC028685C96602BE9DD0BD4F9E202"
          },
          "voting_power": 10,
          "accum": 0
        }
      }
    },
    "peer_round_states": {
      "75EC8F15D244A421202F9725CD4DE509EE50303670310CF7530EF25E2B7C524B": {
        "Height": 1691,
        "Round": 0,
        "Step": 1,
        "StartTime": "2017-10-09T14:08:08.563251997+04:00",
        "Proposal": false,
        "ProposalBlockPartsHeader": {
          "total": 0,
          "hash": ""
        },
        "ProposalBlockParts": null,
        "ProposalPOLRound": -1,
        "ProposalPOL": null,
        "Prevotes": null,
        "Precommits": null,
        "LastCommitRound": 0,
        "LastCommit": null,
        "CatchupCommitRound": -1,
        "CatchupCommit": null
      }
    }
  }
}
```
2017-10-09 14:09:26 +04:00
Anton Kaliaev
a3adac3787 [rpc] do not try to parse params if they were not provided (Refs #708) 2017-10-09 13:30:52 +04:00
Emmanuel Odeke
6fc82f3824 types/heartbeat: test all Heartbeat functions
Updates https://github.com/tendermint/tendermint/issues/693

* Adjusted Heartbeat.Copy to return nil on
trying to copy a nil value instead of panicking.
* Also documented that WriteSignBytes panics
if the Heartbeat is nil.
2017-10-05 21:24:36 -06:00
Ethan Buchman
bcca27ee20 Merge pull request #718 from tendermint/restore-rpc-lib-readme
restore rpc/lib readme as doc.go (Refs #710) [ci skip]
2017-10-05 22:08:17 -04:00
Anton Kaliaev
3702cb7e7c restore rpc/lib readme as doc.go (Refs #710) [ci skip]
I don't want to lose any documentation. Correct me if I am wrong, but we
don't have this docs anywhere else.
2017-10-05 11:44:02 +04:00
Ethan Buchman
49653d3e31 CODEOWNERS file 2017-10-04 23:44:55 -04:00
Ethan Buchman
ddb8430341 Merge pull request #716 from tendermint/unstable
Unstable
2017-10-04 23:43:36 -04:00
Ethan Buchman
91a3cb0f21 makefile: remove megacheck 2017-10-04 23:20:22 -04:00
Ethan Buchman
765c325441 Merge pull request #714 from tendermint/feature/no-block-response
Feature/no block response
2017-10-04 22:27:06 -04:00
Ethan Buchman
659768783f blockchain: fixing reactor tests 2017-10-04 22:26:00 -04:00
Ethan Buchman
e756906a0e Merge pull request #711 from tendermint/imports
get rid of anonymous imports
2017-10-04 22:16:07 -04:00
Zach Ramsay
136b6a7673 rpc/lib: remove dead files, closes #710 2017-10-04 17:45:15 -04:00
Emmanuel Odeke
068f01368f blockchain/reactor: respondWithNoResponseMessage for missing height
Fixes #514
Replaces #540

If a peer requests a block with a height that we don't have
respond with a bcNoBlockResponseMessage.
However, according to the Tendermint spec, if all nodes are honest
this condition shouldn't occur, so this is a possible hint of an
dishonest node.
2017-10-04 17:27:10 -04:00
Zach Ramsay
f23d47e5d2 upnp: keep a link 2017-10-04 17:19:49 -04:00
Ethan Buchman
09aed7ee89 Merge pull request #707 from tendermint/619-how-to-read-logs
How To Read Logs guide
2017-10-04 16:55:20 -04:00
Zach Ramsay
d56b44f3a5 all: no more anonymous imports 2017-10-04 16:40:45 -04:00
Anton Kaliaev
9e4c25761c relative links [ci skip] 2017-10-04 23:33:31 +04:00
Anton Kaliaev
54f2cc9709 [docs] add how to read logs guide [ci skip] 2017-10-04 18:35:22 +04:00
Ethan Buchman
31a7e2b3b4 Merge pull request #704 from tendermint/no-empty-docs
document no empty blocks
2017-10-03 23:56:05 -04:00
Zach Ramsay
00ab3daa0c document no empty blocks, closes #605 [ci skip] 2017-10-03 23:55:45 -04:00
Ethan Buchman
bbf0228aa7 Merge pull request #700 from tendermint/695-improve-app-dev-docs
Improve app dev docs
2017-10-03 23:40:21 -04:00
Ethan Buchman
6550199751 [docs] minor fixes from review [ci skip] 2017-10-03 23:39:46 -04:00
Anton Kaliaev
10f361fcd0 [docs] use persistent_dummy only when needed [ci skip] 2017-10-04 00:04:45 +04:00
Anton Kaliaev
4a0ae17401 [docs] include examples from the persistent_dummy app [ci skip] 2017-10-04 00:04:32 +04:00
Anton Kaliaev
8537070575 [docs] restructure sentence [ci skip] 2017-10-04 00:04:22 +04:00
Ethan Buchman
9cbcd4b5e3 Merge pull request #692 from tendermint/unstable
add the unstable changes
2017-10-03 12:47:16 -04:00
Ethan Buchman
4fa4e617b7 docs/ecosystem: add stratumn 2017-10-03 12:47:01 -04:00
Zach Ramsay
2e598a7caf one more fix 2017-10-03 11:26:32 -04:00
Zach Ramsay
031eb23dc8 docs: fix build warnings 2017-10-03 11:23:08 -04:00
Zach
edd718c580 Update ecosystem.rst 2017-10-03 11:14:24 -04:00
Zach
392a041c2b Merge pull request #699 from tendermint/update-getting-started-docs
remove unnecessary args in abci_query call in getting-started [ci skip]
2017-10-03 10:41:36 -04:00
Anton Kaliaev
8727bfc265 remove unnecessary args in abci_query call in getting-started [ci skip]
Since 0.10.0, RPC does not require all args (default values will be used).
2017-10-03 16:21:48 +04:00
Ethan Buchman
84e39203bb readme points to ecosystem doc; add lotion, clean up 2017-10-02 23:46:35 -04:00
Ethan Buchman
97e9802255 fix out of range error in VoteSet.addVote 2017-10-02 23:34:06 -04:00
Ethan Buchman
8c6bd44929 log stack trace on consensus failure 2017-10-02 23:34:06 -04:00
Ethan Buchman
ed5511dc08 glide: update for autofile fix 2017-10-02 23:34:02 -04:00
Ethan Buchman
aa57e89e21 changelog: add genesis amount->power 2017-10-02 14:28:04 -04:00
Zach Ramsay
c2f6ff759b typo 2017-10-02 13:02:45 -04:00
Anton Kaliaev
45ff7cdd0c rewrite ws client to expose a callback instead of a channel
callback gives more power to the publisher. plus it is optional
comparing to a channel, which will block the whole client if you won't
read from it.
2017-10-02 13:00:20 -04:00
Alexandre Thibault
ce36a0111a rpc: subscribe on reconnection (#689)
* rpc: subscribe on reconnection

* rpc: fix unit tests
2017-10-02 13:00:20 -04:00
Martin Dyring-Andersen
b61f5482d4 Fix broken reference to ABCI 2017-10-02 13:00:20 -04:00
Anton Kaliaev
40b5defe18 release script [ci skip] 2017-10-02 13:00:20 -04:00
Tino Rusch
e40d1b36f7 docs: added passchain to the ecosystem.rst in the applications section; 2017-10-02 13:00:20 -04:00
Zach Ramsay
60a2867af2 docs/ecosystem: add ABCI implementations 2017-10-02 12:59:32 -04:00
Adrian Brink
bfdad916a2 Update ecosystem.rst 2017-10-02 12:59:32 -04:00
Tino Rusch
498ff803db [README] added passchain to application list;
This adds passchain to the 'applications' part of the toplevel README.md file.
Passchain is a distributed password sharing system built on top of tendermint.
2017-10-02 12:59:32 -04:00
Anton Kaliaev
c8789492dc update docker readme [ci skip] 2017-10-02 12:59:32 -04:00
Anton Kaliaev
1723836014 update Dockerfile [ci skip] 2017-10-02 12:59:32 -04:00
Anton Kaliaev
2d6bc8d7d7 bump up Golang version to 1.9.0 2017-10-02 12:59:32 -04:00
Ethan Buchman
7448c4adde Merge pull request #690 from etherealmachine/patch-1
Fix typo in using-tendermint.rst
2017-10-01 11:03:16 -04:00
James Pettit
a221736eee Fix typo in using-tendermint.rst
configutation -> configuration
2017-09-29 23:18:45 -07:00
Alexandre Thibault
382bead548 rpc: fix client websocket timeout (#687) 2017-09-29 13:32:30 +04:00
Anton Kaliaev
f9479b34cb sleep time should be greater than readTimeout (5 sec)
otherwise, we're not testing ping/pongs.
see https://github.com/tendermint/tendermint/pull/687#issuecomment-332494735
2017-09-27 15:44:19 +04:00
Emmanuel Odeke
925696ca65 Merge branch 'p2p-prune-unused-IPRangeCount-funcs' into develop 2017-09-22 21:09:41 -06:00
Ethan Buchman
7682ad9a60 Merge pull request #675 from tendermint/release-v0.11.0
Release v0.11.0
2017-09-22 13:48:52 -04:00
Ethan Buchman
3e92d295e4 glide for tmlibs 0.3.1 2017-09-22 13:25:10 -04:00
Ethan Buchman
661d336dd5 glide 2017-09-22 12:29:53 -04:00
Ethan Buchman
d1a00c684e types: comments 2017-09-22 12:00:37 -04:00
Ethan Buchman
db034e079a version bump 2017-09-22 11:44:57 -04:00
Ethan Buchman
7d983a548b changelog 2017-09-22 11:44:25 -04:00
Ethan Buchman
8311f5c611 abci.Info takes a struct; less merkleeyes 2017-09-22 11:42:40 -04:00
Ethan Buchman
628791e5a5 Merge pull request #665 from tendermint/no-internet
p2p: allow listener with no external connection
2017-09-22 10:16:50 -04:00
Ethan Buchman
df857266b6 update glide 2017-09-22 10:14:05 -04:00
Ethan Buchman
ddb3d8945d p2p: allow listener with no external connection 2017-09-22 10:13:23 -04:00
Ethan Buchman
7f5908b622 Merge pull request #637 from tendermint/feature/hsm
PrivValidator Interface
2017-09-22 00:28:40 -04:00
Ethan Buchman
24f7b9387a more tests 2017-09-22 00:05:39 -04:00
Ethan Buchman
756818f940 fixes from review 2017-09-21 21:44:36 -04:00
Ethan Buchman
2131f8d330 some fixes from review 2017-09-21 17:21:20 -04:00
Ethan Buchman
8ae2ffda89 put funcs back in order to simplify review 2017-09-21 16:59:25 -04:00
Ethan Buchman
75b97a5a65 PrivValidatorFS is like old PrivValidator, for now 2017-09-21 16:46:31 -04:00
Ethan Buchman
7b99039c34 make signBytesHRS a method on LastSignedInfo 2017-09-21 15:54:33 -04:00
Ethan Buchman
3ca7b10ad4 types: more . -> cmn 2017-09-21 15:54:33 -04:00
Ethan Buchman
779c2a22d0 node: NewNode takes DBProvider and GenDocProvider 2017-09-21 15:54:33 -04:00
Ethan Buchman
147a18b34a fix some comments 2017-09-21 15:52:25 -04:00
Ethan Buchman
4382c8d28b fix tests 2017-09-21 15:52:25 -04:00
Ethan Buchman
944ebccfe9 more PrivValidator interface 2017-09-21 15:51:20 -04:00
Ethan Buchman
fd1b0b997a PrivValidator interface 2017-09-21 15:51:20 -04:00
Ethan Buchman
abe912c610 FuncSignerAndApp allows custom signer and abci app 2017-09-21 15:50:43 -04:00
Ethan Buchman
66fcdf7c7a minor fixes 2017-09-21 15:50:43 -04:00
Adrian Brink
4e13a19339 Add ability to construct new instance of Tendermint core from scratch 2017-09-21 15:50:43 -04:00
Adrian Brink
7dd3c007c7 Refactor priv_validator
Users can now just pass an object that implements the Signer interface.
2017-09-21 15:50:43 -04:00
Duncan Jones
0d392a0442 Allow Signer to be generated with priv key
Prior to this change, a custom Signer would have no knowledge of the private
key stored in the configuration file. This changes introduces a generator
function, which creates a Signer based on the private key. This provides an
opportunity for customer Signers to adjust behaviour based on the key
contents. (E.g. imagine key contents are a key label, rather than the key
itself).
2017-09-21 15:50:43 -04:00
Duncan Jones
7e4a704bd1 Remove reliance on default Signer
This change allows the default privValidator to use a custom Signer
implementation with no reliance on the default Signer implementation.
2017-09-21 15:50:43 -04:00
Adrian Brink
bf5e956087 Change capitalisation 2017-09-21 15:50:43 -04:00
Adrian Brink
2ccc3326ec Remove redundant file 2017-09-21 15:50:43 -04:00
Adrian Brink
83f7d5c95a Setup custom tendermint node
By exporting all of the commands, we allow users to setup their own
tendermint node cli. This enables users to provide a different
pivValidator without the need to fork tendermint.
2017-09-21 15:50:43 -04:00
Adrian Brink
2c129447fd Example that showcases how to build your own tendermint node
This example shows how a user of the tendermint library can build their
own node and supply it with its own commands. It includes two todos in
order to make it easier for library users to use tendermint.
2017-09-21 15:50:43 -04:00
Ethan Buchman
b50339e8e7 p2p: sw.AddPeer -> sw.addPeer 2017-09-21 15:47:41 -04:00
Ethan Buchman
8ff5b365dd Merge pull request #650 from tendermint/consensus_params
Consensus params
2017-09-21 15:46:57 -04:00
Ethan Buchman
1f0985689d ConsensusParams ptr in GenesisDoc for json 2017-09-21 15:22:58 -04:00
Ethan Buchman
3089bbf2b8 Amount -> Power. Closes #166 2017-09-21 14:59:27 -04:00
Ethan Buchman
5feeb65cf0 dont use pointers for ConsensusParams 2017-09-21 14:59:24 -04:00
Ethan Buchman
715e74186c fixes from review 2017-09-21 14:51:29 -04:00
Ethan Buchman
3a03fe5a15 updated to match adr 005 2017-09-21 14:51:29 -04:00
Ethan Buchman
d343560108 adr: add 005 consensus params 2017-09-21 14:51:29 -04:00
Ethan Buchman
2b6db268cf genesis json tests and mv ConsensusParams to types 2017-09-21 14:51:29 -04:00
Ethan Buchman
14abdd57f3 genDoc.ValidateAndComplete 2017-09-21 14:51:29 -04:00
Ethan Buchman
1f3e4d2d9a move PartSetSize out of the config, into ConsensusParams 2017-09-21 14:51:29 -04:00
Ethan Buchman
29bfcb0a31 minor comments/changes 2017-09-21 14:51:29 -04:00
Ethan Buchman
301845943c Merge pull request #663 from tendermint/readme-update
update readme and other files
2017-09-21 12:36:11 -04:00
Ethan Buchman
b0017c5460 update CHANGELOG [ci skip] 2017-09-21 12:34:37 -04:00
Zach
0b61d22652 Merge pull request #664 from tendermint/windows-path
use filepath for windows compatibility
2017-09-21 07:34:20 -04:00
Zach Ramsay
70b95135e6 consensus: use filepath for windows compatibility, closes #595 2017-09-18 17:49:43 -04:00
Zach Ramsay
a3d925ac1d pr fixes 2017-09-18 16:52:00 -04:00
Zach Ramsay
cf9a03f698 docs: organize install a bit better 2017-09-18 16:42:24 -04:00
Ethan Buchman
7f8240dfde Merge pull request #521 from tendermint/json-rpc-patch
updated json response to match spec by @davebryson
2017-09-18 16:37:34 -04:00
Anton Kaliaev
f8b152972f return method not found error
if somebody tries to access WS method in non-ws context
2017-09-18 16:36:03 -04:00
Anton Kaliaev
95875c55fc ID must be present in both request and response
from the spec:
This member is REQUIRED.
It MUST be the same as the value of the id member in the Request Object.
If there was an error in detecting the id in the Request object (e.g. Parse error/Invalid Request), it MUST be Null.
2017-09-18 16:36:03 -04:00
Anton Kaliaev
7fadde0b37 check for request ID after receiving it 2017-09-18 16:36:03 -04:00
Anton Kaliaev
e36c79f713 capitalize RpcError 2017-09-18 16:36:03 -04:00
Anton Kaliaev
2252071866 update changelog 2017-09-18 16:36:03 -04:00
Anton Kaliaev
b700ed8e31 remove check for non-empty message as it should always be present 2017-09-18 16:36:03 -04:00
Anton Kaliaev
e1fd587ddd we now omit error if empty 2017-09-18 16:36:03 -04:00
Anton Kaliaev
f74de4cb86 include optional data field in error object
```
data
A Primitive or Structured value that contains additional information about the error.
This may be omitted.
The value of this member is defined by the Server (e.g. detailed error information, nested errors etc.).
```
2017-09-18 16:36:02 -04:00
Anton Kaliaev
6c1572c9b8 fix invalid memory address or nil pointer dereference 2017-09-18 16:36:02 -04:00
Dave Bryson
60a1f49a5c updated json response to match spec by @davebryson 2017-09-18 16:35:50 -04:00
Zach Ramsay
740167202f readme & al., update links to docs 2017-09-18 16:23:22 -04:00
Ethan Buchman
e0017c8a97 Merge pull request #654 from tendermint/docs-add-tools
consolidate docs from tools repo
2017-09-18 13:55:37 -04:00
Ethan Buchman
4a78c1bb28 Merge pull request #661 from tendermint/docs-add-ecosystem
docs: add ecosystem from website
2017-09-18 13:55:09 -04:00
Zach Ramsay
1d3f723ccc docs: remove last section from ecosystem 2017-09-18 13:41:12 -04:00
Zach Ramsay
77408b7bde docs: using ABCI-CLI 2017-09-18 13:31:18 -04:00
Ethan Buchman
0cd1bd6d8b Merge pull request #658 from tendermint/organize-docs
docs: organize the directory
2017-09-18 13:08:38 -04:00
Zach Ramsay
881d2ce31e docs: pull from tools' master branch 2017-09-18 12:14:23 -04:00
Zach Ramsay
ad79ead93d docs: add and re-format the ecosystem from website 2017-09-18 11:57:35 -04:00
Zach Ramsay
17a748c796 docs: rename file 2017-09-18 09:39:23 -04:00
Zach Ramsay
583599b19f docs: add software.json from website (ecosystem) 2017-09-18 09:38:22 -04:00
Zach Ramsay
044fe56b43 update changelog 2017-09-16 15:24:30 -04:00
Zach Ramsay
b46da19b74 docs: organize the directory, #656 2017-09-16 15:19:22 -04:00
Zach Ramsay
d635783d07 docs: finish pull from tools 2017-09-16 15:11:10 -04:00
Zach Ramsay
f79e13af38 docs: pull from tools on build 2017-09-16 15:11:10 -04:00
Zach Ramsay
34e6474ad9 docs: organize tm-bench/monitor description 2017-09-16 15:11:10 -04:00
Zach Ramsay
5c96e0c812 docs: add original tm-bench/monitor files 2017-09-16 15:11:10 -04:00
Zach Ramsay
921a2b41f0 docs: add kubes docs to mintnet doc, from tools 2017-09-16 15:11:10 -04:00
Zach Ramsay
a8cec967ac docs: harmonize headers for tools docs 2017-09-16 15:11:10 -04:00
Zach Ramsay
044c500cc0 docs: move images in from tools repo 2017-09-16 15:11:10 -04:00
Zach Ramsay
a917ec9ea2 docs: update index.rst 2017-09-16 15:11:10 -04:00
Zach Ramsay
d4ccc88676 docs: convert from md to rst 2017-09-16 15:11:10 -04:00
Zach Ramsay
12c85c4e60 docs: add original README's from tools repo 2017-09-16 15:11:10 -04:00
Ethan Buchman
90c0267bc1 types: privVal.Sign returns an error 2017-09-16 01:07:04 -04:00
Ethan Buchman
8963bf08aa Merge pull request #657 from tendermint/fix/adr
docs: update and clean up adr
2017-09-15 19:32:58 -04:00
Ethan Buchman
ede4f818fd docs: update and clean up adr 2017-09-15 19:31:37 -04:00
Ethan Buchman
126f63c0a2 Merge pull request #653 from tendermint/improvement/peer_interface
peer interface
2017-09-15 18:43:53 -04:00
Ethan Buchman
aea8629272 peer interface 2017-09-15 18:40:59 -04:00
Emmanuel Odeke
5138bcb1c7 p2p: delete unused and untested *IPRangeCount functions
Fixes #602

Delete unused and untested functions:
- AddToIPRangeCounts
- CheckIPRangeCounts
2017-09-15 14:03:01 -06:00
Ethan Buchman
cc50dc076a Merge pull request #638 from tendermint/feature/state_tests
Upgrade state_test.go
2017-09-12 14:37:59 -04:00
Ethan Buchman
bf576f0097 state: minor comment fixes 2017-09-12 14:37:32 -04:00
Zach
377747b061 Merge pull request #651 from tendermint/doc/testnet
Started expanding "automated deployments" in documentation
2017-09-12 12:41:42 -04:00
Adrian Brink
870a98ccc3 Last fixes 2017-09-12 17:12:19 +02:00
Adrian Brink
8eda3efa28 Cleanup lines to fit within 72 characters 2017-09-12 17:08:30 +02:00
Zach Ramsay
e2c3cc9685 docs: give index a Tools section 2017-09-12 10:57:34 -04:00
Adrian Brink
2a6e71a753 Reformat tests to extract common setup 2017-09-12 16:57:10 +02:00
GaryTomato
340d273f83 Started expanding "automated deployments" 2017-09-11 11:34:36 -04:00
Ethan Buchman
54c63726b0 p2p: minor comment fixes 2017-09-06 16:40:21 -04:00
Ethan Buchman
cb80ab2965 Merge remote-tracking branch 'orijtech/p2p-full-test-PeerSet' into develop 2017-09-06 16:40:07 -04:00
Emmanuel Odeke
c48e772115 p2p: fully test PeerSet, more docs, parallelize PeerSet tests
* Full test PeerSet and check its concurrent guarantees
* Improve the doc for PeerSet.Has and remove unnecessary
defer for a path that sets a variable, make it fast anyways.
* Parallelize PeerSet tests with t.Parallel()
* Document functions in peer_set.go more.
2017-09-06 02:47:31 -06:00
Ethan Buchman
aa78fc14b5 cmd: dont wait for genesis. closes #562 2017-09-06 01:57:21 -04:00
Ethan Buchman
399fb9aa70 consensus: remove support for replay by #HEIGHT. closes #567 2017-09-06 01:53:41 -04:00
Ethan Buchman
ec3c91ac14 Merge pull request #618 from tendermint/historical_validators
Historical validators
2017-09-06 01:46:31 -04:00
Ethan Buchman
fae0603413 more fixes from review 2017-09-06 01:25:57 -04:00
Ethan Buchman
9af837c24d Merge pull request #644 from tendermint/release-v0.10.4
Release v0.10.4
2017-09-05 17:44:48 -04:00
Ethan Buchman
cc2b418f7f p2p: test fix 2017-09-05 17:10:11 -04:00
Ethan Buchman
6ddc30ffc7 Merge branch 'master' into release-v0.10.4 2017-09-05 16:49:57 -04:00
Ethan Buchman
aa7d63f2ff bump version to 0.10.4 2017-09-05 16:46:56 -04:00
Ethan Buchman
50f2ef548c Merge pull request #642 from tendermint/zramsay-patch-1
Delete roadmap.md
2017-09-05 16:26:04 -04:00
Ethan Buchman
b9637f7185 Update changelog and add roadmap 2017-09-05 16:25:02 -04:00
Ethan Buchman
88138c38cf mempool: reactor test 2017-09-05 16:25:02 -04:00
Ethan Buchman
5ad0da1750 Merge pull request #640 from tendermint/read-the-docs
Implement read the docs
2017-09-05 15:37:24 -04:00
Ethan Buchman
9deb647303 fixes from review 2017-09-04 18:29:51 -04:00
Ethan Buchman
b856c45b9c Merge pull request #634 from tendermint/config-p2p
p2p: put maxMsgPacketPayloadSize, recvRate, sendRate in config
2017-09-04 14:16:16 -04:00
Ethan Buchman
f0f1ebe013 rpc: Block and Commit take pointers; return latest on nil 2017-09-03 16:07:37 -04:00
Ethan Buchman
34beff117a state: comments; use wire.BinaryBytes 2017-09-03 16:07:37 -04:00
Ethan Buchman
e2e8746044 rpc: historical validators 2017-09-03 16:07:37 -04:00
Ethan Buchman
78446fd99c state: persist validators 2017-09-03 16:07:37 -04:00
Ethan Buchman
daa258ea6d p2p: put maxMsgPacketPayloadSize, recvRate, sendRate in config
Updates #628
2017-09-01 21:44:15 -04:00
Zach Ramsay
54c85ef8b9 try image 2017-09-01 21:14:26 -04:00
Zach Ramsay
de512c5923 fix 2017-09-01 21:05:12 -04:00
Zach Ramsay
8fd133ff19 docs: pretty-fy 2017-09-01 20:59:27 -04:00
Zach Ramsay
f5ba931115 docs: logo, add readme, fixes 2017-09-01 20:08:22 -04:00
Zach
3370e40fe1 Delete roadmap.md
file is out of date & provides no useful information
2017-09-01 19:38:11 -04:00
Zach Ramsay
e509e8f354 docs: clean a bunch of stuff up 2017-08-31 15:30:17 -04:00
Zach Ramsay
aaef2f7c84 docs: link fixes 2017-08-30 22:26:26 -04:00
Zach Ramsay
369aa5854f docs: fix image links 2017-08-30 22:11:21 -04:00
Zach Ramsay
9d12e485e5 docs: rst-ify the intro 2017-08-30 21:43:39 -04:00
Zach Ramsay
dc54fc707e docs: port website's intro for rtd 2017-08-30 21:34:51 -04:00
Zach Ramsay
212a5ebc2e docs: use maxdepth 2 for spec 2017-08-30 21:17:07 -04:00
Zach Ramsay
2d2e769e96 rtd: build fixes 2017-08-30 21:01:05 -04:00
Zach Ramsay
bba35c1486 docs: rpc docs to be slate, see #526, #629 2017-08-30 20:51:48 -04:00
Zach Ramsay
0a902ebf61 docs: organize the specification 2017-08-30 20:47:37 -04:00
Zach Ramsay
70c0f4b936 docs: convert markdown to rst 2017-08-30 17:54:25 -04:00
Zach Ramsay
e19fa59b63 docs: consolidate ADRs 2017-08-30 17:43:39 -04:00
Ethan Buchman
30d351b0c1 Merge pull request #623 from tendermint/fix/no-config-on-version
cmd: don't load config for version command. closes #620
2017-08-30 16:42:58 -04:00
Zach Ramsay
818314c5db docs: add sphinx Makefile & requirements 2017-08-30 16:37:51 -04:00
Zach Ramsay
700e4bb29d docs: test 2017-08-30 15:26:32 -04:00
Zach Ramsay
8ad4a1341f docs: add conf.py 2017-08-30 15:16:39 -04:00
Ethan Buchman
d87acc2d1b cmd: don't load config for version command. closes #620 2017-08-28 15:01:51 -04:00
Ethan Buchman
f2349b1092 Merge pull request #526 from tendermint/feature/rpc-docs
RPC docs
2017-08-25 18:10:21 -04:00
Ethan Buchman
7824b66f5b Merge pull request #548 from tendermint/indexing-proposal
Indexing proposal
2017-08-25 18:02:18 -04:00
Ethan Buchman
83048fb2fe Merge pull request #604 from tendermint/bugfix/ws-io-timeout
Biff up RPC WSClient
2017-08-25 17:59:34 -04:00
Ethan Buchman
9dde1a0bd4 rpc: comments 2017-08-25 17:57:09 -04:00
Ethan Buchman
bc9092d7db Merge pull request #609 from orijtech/parseConfig-doc-update
cmd/tendermint/commands: update ParseConfig doc
2017-08-21 13:55:45 -04:00
Ethan Buchman
56b959b9f9 Merge pull request #611 from tendermint/dont_panic
Dont panic
2017-08-21 13:54:58 -04:00
Zach Ramsay
b3796e0aaa rpc: typo fixes 2017-08-16 15:18:55 -04:00
Anton Kaliaev
d24083b257 generate md for Slate 2017-08-16 15:17:08 -04:00
Anton Kaliaev
83ec9f773a wrote docs for rpc methods [ci skip]
for all of them except unsafe
2017-08-16 15:17:08 -04:00
Ethan Buchman
9ceccbe9a4 consensus: recover panics in receive routine 2017-08-16 01:01:09 -04:00
Ethan Buchman
35a4912449 dont panic on getVoteBitArray 2017-08-16 00:43:55 -04:00
Ethan Buchman
01e008cedd Merge pull request #607 from tendermint/zramsay-patch-1
fix link from slack to rocket
2017-08-15 12:40:07 -04:00
Emmanuel Odeke
d8af26e75a cmd/tendermint/commands: update ParseConfig doc 2017-08-12 16:29:11 -06:00
Zach
03ddb109ec fix link from slack to rocket 2017-08-11 10:30:04 -04:00
Anton Kaliaev
2fd8496bc1 correct handling of pings and pongs
server:
- always has read & write timeouts
- ping handler never blocks the reader (see A)
- sends regular pings to check up on a client

A:
at some point server write buffer can become full, so in order not to
block reads from a client (see
https://github.com/gorilla/websocket/issues/97), server may skip some
pongs. As a result, client may disconnect. But you either have to do
that or block the reader. There is no third way.

client:
- optional read & write timeouts
- optional ping/pong to measure latency
2017-08-10 17:53:49 -04:00
Ethan Buchman
8d7640894d Merge pull request #606 from tendermint/release-v0.10.3
Release v0.10.3
2017-08-10 10:25:48 -04:00
Ethan Buchman
c5a657f540 consensus: test proposal heartbeat 2017-08-10 01:24:23 -04:00
Ethan Buchman
1ea43e513d version bump 2017-08-10 00:14:49 -04:00
Ethan Buchman
c9e11de2a7 consensus: log ProposalHeartbeat msg 2017-08-10 00:12:16 -04:00
Ethan Buchman
f644fc5725 changelog 2017-08-10 00:04:07 -04:00
Ethan Buchman
49278a7f9c Merge pull request #579 from tendermint/feature/sync_status
Add fast-sync status to Status() call
2017-08-09 23:51:25 -04:00
Ethan Buchman
b0728260e9 comments 2017-08-09 23:51:09 -04:00
Ethan Buchman
92ada55e5a make conR.FastSync() thread safe 2017-08-09 14:55:21 -04:00
Ethan Buchman
8840ae6ae2 Merge pull request #597 from zramsay/tendermint-types-links
fix dead tendermint types links in specs
2017-08-08 22:19:10 -04:00
Ethan Buchman
21dab22f17 Merge pull request #599 from zramsay/docs-getting-started
docs fixes throughout
2017-08-08 22:17:44 -04:00
Ethan Buchman
10a849c27e Merge pull request #596 from zramsay/deduplications
Deduplications
2017-08-08 22:16:25 -04:00
Anton Kaliaev
236489aecf backlog must always have higher priority 2017-08-08 19:03:48 -04:00
Ethan Buchman
7108c66e3b Merge pull request #584 from tendermint/no-empty-blocks
No empty blocks
2017-08-08 18:10:04 -04:00
Ethan Buchman
797acbe911 ws: small comment 2017-08-08 17:33:17 -04:00
Ethan Buchman
0bf66deb3c fixes from review 2017-08-08 17:09:04 -04:00
Ethan Buchman
d2f3e9faf4 test CreateEmptyBlocksInterval 2017-08-08 16:35:25 -04:00
Ethan Buchman
37f1390473 CreateEmptyBlocks and CreateEmptyBlocksInterval 2017-08-08 16:22:37 -04:00
Anton Kaliaev
9b5f21a650 [ws-server] reset readTimeout when we receive something 2017-08-08 16:03:04 -04:00
Anton Kaliaev
8267920749 [ws-client] write normal close message 2017-08-08 16:02:37 -04:00
Anton Kaliaev
6c85e4be4f change server ping period to be less frequent
no need to ping ws every 10 sec
2017-08-08 13:21:59 -04:00
Anton Kaliaev
23a87304cc add a comment for PingPongLatencyTimer [ci skip] 2017-08-08 13:20:58 -04:00
Anton Kaliaev
c14b39da5f make RPC server's ping period and pong wait configurable via options 2017-08-07 18:29:55 -04:00
Anton Kaliaev
57eee2466b make WSClient thread-safe 2017-08-07 17:56:38 -04:00
Anton Kaliaev
5d66d1c28c fixes from review 2017-08-05 13:11:00 -04:00
Ethan Buchman
fb47ca6d35 fixes from review 2017-08-04 21:36:11 -04:00
Anton Kaliaev
0013053fae allow to change pong wait and ping period 2017-08-04 10:42:55 -04:00
Anton Kaliaev
1abbb11b44 do not exit from reconnectRoutine! 2017-08-03 22:44:18 -04:00
Anton Kaliaev
54903adeff add IsReconnecting and IsActive methods 2017-08-03 19:10:15 -04:00
Anton Kaliaev
c08618f7e9 expose latency timer on WSClient 2017-08-03 19:10:14 -04:00
Anton Kaliaev
d578f7f81e biff up WS client
What's new:
- auto reconnect
- ping/pong
- colored tests
2017-08-03 19:10:14 -04:00
Ethan Buchman
043c6018b4 Merge pull request #591 from tendermint/heartbeat
broadcast proposer heartbeat msg
2017-08-03 14:35:25 -04:00
Ethan Buchman
d0965cca05 forgot heartbeat file 2017-08-03 13:58:17 -04:00
Ethan Buchman
b8ac67e240 some fixes 2017-08-03 13:25:26 -04:00
Zach Ramsay
350d584af8 docs: tons of minor improvements
closes: https://github.com/zramsay/tendermint/issues/3
closes: https://github.com/zramsay/tendermint/issues/5
2017-08-01 15:52:16 -04:00
Zach Ramsay
e3e75376ec fix mintnet-kubernetes link 2017-08-01 14:31:38 -04:00
Ethan Buchman
ab753abfa0 Proposer->Proposal; sign heartbeats 2017-07-29 17:04:28 -04:00
Zach Ramsay
bab7877fa1 route links to godoc rather than deprecated internal implementation, closes https://github.com/zramsay/tendermint/issues/1 2017-07-29 14:33:49 -04:00
Ethan Buchman
10f8101314 fix race 2017-07-29 11:45:07 -04:00
Ethan Buchman
530626dab7 broadcast proposer heartbeat msg 2017-07-29 11:45:02 -04:00
Ethan Buchman
b96d28a42b test progress in higher round 2017-07-28 23:43:30 -04:00
Ethan Buchman
3444bee47f fixes from review; use mempool.TxsAvailable() directly 2017-07-28 23:42:43 -04:00
Ethan Buchman
cf3abe5096 consensus: remove rs from handleMsg 2017-07-28 23:42:19 -04:00
Ethan Buchman
ecdda69fab commit empty blocks when needed to prove app hash 2017-07-28 22:12:11 -04:00
Ethan Buchman
fc3fe9292f fixes from review 2017-07-28 22:12:11 -04:00
Ethan Buchman
d396053872 changelog 2017-07-28 22:11:45 -04:00
Ethan Buchman
e9a2389300 cmd: --consensus.no_empty_blocks 2017-07-28 22:11:45 -04:00
Ethan Buchman
678a9a2e42 TxsAvailable tests 2017-07-28 22:11:45 -04:00
Ethan Buchman
124032e3e9 NoEmptyBlocks config option 2017-07-28 22:11:45 -04:00
Ethan Buchman
4beac54bd9 no empty blocks 2017-07-28 22:11:45 -04:00
Ethan Buchman
39493bcd9a consensus: isProposer func 2017-07-28 22:11:10 -04:00
Zach Ramsay
f96771e753 cleanup CONTRIBUTING.md, part of https://github.com/zramsay/tendermint/issues/7 2017-07-28 16:45:03 -04:00
Zach Ramsay
62f94a7948 deduplicate install, closes https://github.com/zramsay/tendermint/issues/2 2017-07-28 16:34:38 -04:00
Ethan Buchman
e9b7221292 consensus: more comments 2017-07-20 00:59:28 -04:00
Anton Kaliaev
5fea1d2675 [.editorconfig] add rule for .proto files [ci skip] 2017-07-19 12:29:10 +03:00
Anton Kaliaev
7a492e3612 Merge pull request #549 from tendermint/rpc-server-proposal
RPC server ADR
2017-07-19 10:44:12 +03:00
Anton Kaliaev
b893df3348 add rpc server proposal [ci skip] 2017-07-19 10:43:30 +03:00
Anton Kaliaev
742b5b705f update link to contributing guidelines in README.md [ci skip] 2017-07-19 10:35:54 +03:00
Peng Zhong
0153d21f3b Update website links on README.md (#589) [ci skip]
* Update website links on README.md

Changed the blog links to Medium.
Updated Tendermint website links.

* correct link for Tendermint blog [ci skip]
2017-07-19 10:31:49 +03:00
Ethan Buchman
695ad5fe2d Merge pull request #588 from tendermint/comments_cleanup
Comments and cleanup
2017-07-17 13:32:23 -04:00
Ethan Buchman
d8ca0580a8 rpc: move grpc_test from test/ to grpc/ 2017-07-17 12:58:15 -04:00
Ethan Buchman
525fc0ae5b types: block comments 2017-07-17 12:58:15 -04:00
Ethan Buchman
311f18bebf mempool: comments 2017-07-17 12:58:10 -04:00
Ethan Buchman
d49a5166ac scripts/txs: add 0x and randomness 2017-07-17 12:57:30 -04:00
Ethan Buchman
e560dd839f Merge pull request #587 from ramilexe/feature/sync_status
fast sync status
2017-07-17 11:51:44 -04:00
ramil
6f8d385dfa fast sync status 2017-07-17 09:44:23 +03:00
caojingqi
086544e367 p2p: sw.peers.List() is empty in sw.OnStart 2017-07-10 20:43:38 -04:00
Ethan Buchman
eed0297ed5 Merge pull request #538 from zramsay/docs-rework
rework docs
2017-07-10 20:32:03 -04:00
Ethan Buchman
b467515719 Merge pull request #576 from tendermint/release-v0.10.2
Release v0.10.2
2017-07-10 16:22:09 -04:00
Ethan Buchman
75df0d91ba comments from review 2017-07-10 13:39:23 -04:00
Adrian Brink
05c0dfac12 First crack it providing fast-sync endpoint 2017-07-10 19:30:54 +02:00
Ethan Buchman
bcde80fc4f changelog 2017-07-09 18:49:22 -04:00
Ethan Buchman
5f6b996d22 breakup some long lines; add more comments to consensus reactor 2017-07-09 18:38:59 -04:00
Ethan Buchman
74a3a2b56a fix comments 2017-07-09 18:01:25 -04:00
Adrian Brink
b07d01f102 Add more comments on public functions and extra logging during 'enterPrevote'
Signed-off-by: Adrian Brink <adrian@brink-holdings.com>
2017-07-09 20:35:48 +02:00
Ethan Buchman
eed3959749 version bump 2017-07-09 13:17:01 -04:00
Zach Ramsay
278b2344fe move docs/architechture to docs/hidden 2017-07-08 14:25:15 -04:00
Zach Ramsay
05095954c9 use official golang site for installing 2017-07-08 14:09:56 -04:00
Zach Ramsay
6fef4b080e docs: add docs from website 2017-07-08 14:05:24 -04:00
Zach Ramsay
259111d0e8 address adrian's comment 2017-07-08 14:05:24 -04:00
Zach Ramsay
a707748893 add roadmap.md from site 2017-07-08 14:05:24 -04:00
Zach Ramsay
130ae133c1 fix link in changelog 2017-07-08 14:05:24 -04:00
Zach Ramsay
1d387d7452 contributing: use full version from site 2017-07-08 14:05:24 -04:00
Ethan Buchman
612726d9f6 consensus: better logging 2017-07-07 16:58:16 -04:00
Ethan Buchman
5888ddaab1 consensus: improve logging for conflicting votes 2017-07-07 13:41:50 -04:00
Ethan Buchman
e6cecb9595 p2p: fix test 2017-07-07 13:33:15 -04:00
Ethan Buchman
e36e507463 changelog 2017-07-07 13:30:30 -04:00
Ethan Buchman
3c10f7a122 add p2p flush throttle to config 2017-07-07 13:08:52 -04:00
Ethan Buchman
ca8c34f966 add consensus reactor sleep durations to the config 2017-07-07 12:39:40 -04:00
Ethan Buchman
8355fee16a Merge pull request #563 from tendermint/bugfix/ignore-tmhome-in-tests
Do some cleanup in the test, so it doesn't fail in my shell
2017-07-06 21:48:40 -04:00
Ethan Buchman
7f3c697b6e Merge pull request #559 from tendermint/release-v0.10.1
Release v0.10.1
2017-06-28 11:45:41 -04:00
Ethan Buchman
0d1fa8e884 fixes from review 2017-06-28 11:12:45 -04:00
Ethan Frey
2e0a4aafa7 Update glide files to proper versions 2017-06-28 13:05:51 +02:00
Ethan Buchman
bfecb5a135 some fixes from review 2017-06-27 16:05:21 -04:00
Ethan Frey
850da13622 Do some cleanup in the test, so it doesn't fail in my shell 2017-06-27 13:31:32 +02:00
Ethan Buchman
b284d39e05 update changelog 2017-06-26 17:29:39 -04:00
Ethan Buchman
23d8de8962 Merge branch 'develop' into release-v0.10.1 2017-06-26 17:22:57 -04:00
Ethan Buchman
3065059da7 update changelog 2017-06-26 17:20:27 -04:00
Ethan Buchman
e2ed15fa02 rpc: SetWriteDeadline for ws ping. fixes #553 2017-06-26 17:13:39 -04:00
Ethan Buchman
b92814c933 Merge pull request #560 from tendermint/feature/docker-build-automation
Docker build automation
2017-06-26 16:20:05 -04:00
Ethan Buchman
12c084c8c0 ParseGenesisFile -> types.GenesisDocFromFile 2017-06-26 16:16:54 -04:00
Ethan Frey
e4caf96bcb Calculate validator hash from genesis doc 2017-06-26 17:06:49 +02:00
Ethan Frey
10982f4d8f Add argument to ParseGenesis to use in light-client 2017-06-26 16:56:51 +02:00
Ethan Frey
6b38abd57b Cleanup for loop in genesis file load 2017-06-26 13:58:34 +02:00
Ethan Frey
58105dbd4e Refactored some commands to be more reusable 2017-06-26 13:58:34 +02:00
Anton Kaliaev
d0b1bf4e26 [docker] bump golang version to 1.8.3 2017-06-26 12:08:38 +04:00
Anton Kaliaev
aa7b3a73f5 [docker] remove dummy app as default [ci skip] 2017-06-26 12:05:50 +04:00
Anton Kaliaev
852375be00 [docker] update link to mintnet-k8s [ci skip] 2017-06-26 12:05:50 +04:00
Anton Kaliaev
9a80730f38 [docker] fix link to 0.10.0 Dockerfile [ci skip] 2017-06-26 12:05:40 +04:00
Anton Kaliaev
24a1b130f9 [docker] build and push scripts [ci skip] 2017-06-26 12:05:34 +04:00
Anton Kaliaev
e2fe4a6e9b [docker] bump alpine version [ci skip] 2017-06-26 12:05:23 +04:00
Ethan Buchman
4f5b6528a1 version bump 2017-06-24 22:56:31 -04:00
Ethan Buchman
10828ad063 changelog 2017-06-24 22:55:48 -04:00
Ethan Buchman
b6031d5f4b rpc/lib: set logger on ws conn 2017-06-24 21:55:31 -04:00
Ethan Buchman
5c29d7aba9 rpc/lib: test tcp and unix 2017-06-24 21:27:19 -04:00
Ethan Buchman
bdbefe334d Merge pull request #539 from tendermint/feature/readme_update
Add Code of Conduct
2017-06-24 00:14:08 -04:00
Ethan Buchman
77a3d03385 blockchain: explain isCaughtUp logic 2017-06-23 22:34:38 -04:00
Ethan Buchman
468982ffe4 fixes 2017-06-23 22:12:45 -04:00
Ethan Buchman
2750343de5 Merge branch 'apply-megacheck' into unstable 2017-06-23 21:38:22 -04:00
Ethan Buchman
3c0128a680 undo some megacheck suggestions 2017-06-23 21:36:47 -04:00
Ethan Buchman
4522456d55 Merge remote-tracking branch 'origin/feature/496-deduplicate-tests-in-rpc-tests-and-rpc-client' into unstable 2017-06-23 21:24:09 -04:00
Ethan Buchman
dcc538ff32 Merge remote-tracking branch 'origin/feature/506-tracing-logger' into unstable 2017-06-23 21:16:02 -04:00
Ethan Buchman
a22f7358cd Merge pull request #552 from tendermint/feature/551-default-to-tcp
httpDialer accepts no prefix or http:// as tcp://
2017-06-22 23:49:50 -04:00
Ethan Frey
aac85a14f0 httpDialer accepts no prefix or http:// as tcp:// 2017-06-22 20:56:57 +02:00
Anton Kaliaev
a676b2aa10 add indexing proposal [ci skip] 2017-06-21 15:07:45 +04:00
Adrian Brink
df934c1707 Add Code of Conduct 2017-06-19 15:46:15 +02:00
Anton Kaliaev
eaec0c8ea5 deduplicate tests in rpc/test and rpc/client (Refs #496) 2017-06-16 17:14:27 +04:00
Anton Kaliaev
4f0f50c62d Merge pull request #535 from tendermint/bugfix/fix-invalid-logger-keys
Fix invalid logger keys
2017-06-14 13:20:10 +04:00
Anton Kaliaev
b4ece65726 standardize key for errors (should be "err") 2017-06-14 12:50:49 +04:00
Anton Kaliaev
562dd67e16 fix invalid keys (space is prohibited by logfmt encoder) 2017-06-14 12:50:01 +04:00
Anton Kaliaev
da646a8986 Merge pull request #534 from hxzqlh/master
logger key doesn't support blank space
2017-06-14 12:38:13 +04:00
hxzqlh
b9b2782c3c logger key doesn't support space 2017-06-14 14:41:36 +08:00
Anton Kaliaev
f1c087116f Merge pull request #518 from tendermint/feature/504-move-log-level-parsing-to-cli-package
move log level parsing to tmlibs/cli package (Refs #504)
2017-06-12 19:47:22 +04:00
Anton Kaliaev
9dcf130d67 update tmlibs (Refs #504) 2017-06-12 19:25:34 +04:00
Anton Kaliaev
ed7183936d move log level parsing to tmlibs/cli package (Refs #504) 2017-06-12 19:08:39 +04:00
Ethan Buchman
e5342f4054 docker: update for 0.10.0 [ci skip]" 2017-06-03 21:37:59 -04:00
Ethan Buchman
2e173d4abf Merge branch 'master' into develop 2017-06-03 00:13:14 -04:00
Ethan Buchman
ca632c9e90 Merge pull request #527 from tendermint/release-v0.10.0
Release v0.10.0
2017-06-02 23:59:46 -04:00
Ethan Buchman
c94a92b30d update changelog and readme 2017-06-02 23:33:03 -04:00
Ethan Buchman
84fea82043 dist: dont mkdir in container 2017-06-02 23:20:02 -04:00
Ethan Buchman
d608e2b7ad bump version to 0.10.0 2017-06-02 23:19:30 -04:00
Ethan Buchman
d19d8e7914 update readme and changelog 2017-06-02 23:18:10 -04:00
zramsay
9c3eee0b00 Makefile: add megacheck & some additional fixes 2017-05-30 13:35:34 -04:00
zramsay
bf5181d9ca address PR comments 2017-05-30 13:27:08 -04:00
Anton Kaliaev
989cb6dd2e update Dockerfile [ci skip] 2017-05-30 16:33:48 +03:00
zramsay
cf31f8d06f core: apply megacheck vet tool (unused, gosimple, staticcheck) 2017-05-29 23:11:40 -04:00
Ethan Buchman
c7cd62b449 Merge branch 'master' into develop 2017-05-29 10:53:33 -04:00
Ethan Buchman
2b5b017253 Merge pull request #516 from tendermint/release-v0.10.0-rc2
fixes to changelog, config, default logging
2017-05-29 08:58:20 -04:00
Ethan Buchman
630c6ef7b5 bump version 2017-05-29 02:47:09 -04:00
Ethan Buchman
ee88272216 enable unsafe rpc routes in tests via flag 2017-05-26 14:20:23 -04:00
Ethan Buchman
bd7ec18c19 fix tests 2017-05-26 12:17:32 -04:00
Ethan Buchman
42626d9e16 [types] overwrite pubkey/addr in LoadPrivValidator. closes #500 2017-05-25 13:40:13 -04:00
Ethan Buchman
fc6611b2d9 [config] RPCConfig 2017-05-24 13:56:12 -04:00
Ethan Buchman
4f27752468 [rpc] dont enable unsafe by default; limit /blockchain_info to 20 blocks 2017-05-24 11:31:31 -04:00
Anton Kaliaev
9bc1790320 tracing logger (Refs #506)
DEPENDS ON https://github.com/tendermint/tmlibs/pull/21
2017-05-24 14:28:25 +02:00
Ethan Buchman
3fbe286e5a small fixes to changelog, config, default logging 2017-05-22 08:16:25 -04:00
Anton Kaliaev
aa22bd8464 Merge pull request #511 from spring1843/fix-typos
Fix commonly misspelled words
2017-05-21 13:24:35 +02:00
spring1843
cf686d4f83 Fix commonly misspelled words 2017-05-20 21:43:00 -07:00
Ethan Buchman
267f134d44 Merge pull request #508 from tendermint/release-v0.10.0-rc1
Release v0.10.0 rc1
2017-05-18 13:45:17 +02:00
Ethan Buchman
d4fa98de68 update version for rc1 2017-05-18 07:20:37 -04:00
Ethan Buchman
790e04ed3e add link to list of breaking funcs/methods 2017-05-18 12:32:34 +02:00
Ethan Buchman
772306cac8 update changelog and glide 2017-05-18 06:16:08 -04:00
Ethan Buchman
30a19fc899 [consensus] Info->Debug for is a validator log msg 2017-05-18 11:26:15 +02:00
Ethan Buchman
6a30a902c9 [types] more []byte->data.Bytes and some %X->%v 2017-05-17 01:08:41 +02:00
Ethan Buchman
883b71ca70 update CHANGELOG 2017-05-17 00:27:03 +02:00
Ethan Buchman
11b5d11e9e Merge pull request #505 from tendermint/dont-hash-accum
[types] dont hash validator.Accum
2017-05-17 00:19:28 +02:00
Ethan Buchman
6d83c60c40 [types] dont hash validator.Accum 2017-05-17 00:16:38 +02:00
Ethan Buchman
cc2b430e68 update glide and changelog 2017-05-17 00:12:56 +02:00
Ethan Buchman
9d7d8075d1 Merge remote-tracking branch 'origin/update-for-new-abci-api' into develop 2017-05-16 23:58:48 +02:00
Ethan Buchman
fe87623674 Merge pull request #501 from tendermint/feature/493-per-module-log-levels
Feature/493 per module log levels
2017-05-16 23:33:21 +02:00
Anton Kaliaev
91dc87e7c4 update for a new ABCI API 2017-05-16 19:06:35 +02:00
Anton Kaliaev
fb0df75de0 changes per Frey comments (Refs #493) 2017-05-16 15:16:50 +02:00
Ethan Buchman
e1792c1ea5 fix tx string format take 2 2017-05-16 14:12:48 +02:00
Ethan Buchman
d5113377e2 fix tx string format 2017-05-16 14:01:52 +02:00
Adrian Brink
eb9ca23250 log whether node is a validator in each round 2017-05-16 14:01:52 +02:00
Anton Kaliaev
05a8204508 per module log levels (Refs #493) 2017-05-16 13:57:28 +02:00
Adrian Brink
e041b2eee6 Merge pull request #502 from tendermint/adrianbrink-patch-1
Update README.md
2017-05-16 10:13:31 +02:00
Adrian Brink
0a4ab7e38f Update README.md 2017-05-16 09:50:52 +02:00
Ethan Buchman
c4ad0f76e6 Merge pull request #494 from tendermint/json-naming
Clean up json output
2017-05-15 19:03:25 +02:00
Ethan Buchman
0f1edcd57d Merge pull request #497 from tendermint/feature/color-code-different-consensus-instances
Color code different consensus instances in consensus tests
2017-05-15 19:02:02 +02:00
Adrian Brink
118d565534 Merge pull request #472 from tendermint/string_reprs
Add Tx String representation. Got the ok from Anton.
2017-05-15 09:49:40 +02:00
Anton Kaliaev
1dfb95f719 [consensus] color code different consensus instances in consensus tests
(Refs #492)
2017-05-15 09:35:29 +02:00
Ethan Buchman
33f807d9a1 Merge pull request #489 from tendermint/feature/adrian-#469
Use ld flags to set git hash instead of "revision_file"
2017-05-14 21:52:29 +02:00
Ethan Frey
926fb83e33 Re-added comment 2017-05-14 19:10:58 +02:00
Ethan Frey
2b324b7eb9 RPC returns pretty formated json 2017-05-14 19:06:34 +02:00
Ethan Frey
157ec8af2d Add json tags to validator set 2017-05-14 19:06:33 +02:00
Ethan Buchman
f14f167297 Merge pull request #491 from tendermint/feature/new-logging
New logging
2017-05-14 00:45:21 +02:00
Anton Kaliaev
4fe67652ff move SetLogger down 2017-05-14 00:24:58 +02:00
Anton Kaliaev
c5bccc5474 set missing logger on switch
```
panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x1 addr=0x0 pc=0x882cec]

goroutine 328 [running]:
github.com/tendermint/tendermint/p2p.(*Switch).DialPeerWithAddress(0xc42000a500, 0xc4202088d0, 0xc420403500, 0x0, 0x0, 0x0)
        /home/vagrant/go/src/github.com/tendermint/tendermint/p2p/switch.go:324 +0x2fc
github.com/tendermint/tendermint/p2p.(*PEXReactor).ensurePeers.func1(0xc4201663f0, 0xc4202088d0)
        /home/vagrant/go/src/github.com/tendermint/tendermint/p2p/pex_reactor.go:280 +0x3e
created by github.com/tendermint/tendermint/p2p.(*PEXReactor).ensurePeers
        /home/vagrant/go/src/github.com/tendermint/tendermint/p2p/pex_reactor.go:284 +0x5d4
```
2017-05-13 17:05:44 +02:00
Anton Kaliaev
f8fdbe3dbc changes as per Bucky's review 2017-05-13 16:22:51 +02:00
Anton Kaliaev
c9cd8de9c6 set logger 2017-05-13 10:25:00 +02:00
Anton Kaliaev
3e1343dc6b has as a base16 string 2017-05-13 10:24:59 +02:00
Anton Kaliaev
bc4e6566e7 [p2p] refactor upnp to use new logger 2017-05-13 10:24:59 +02:00
Ethan Buchman
16509ac3db p2p: fix race by peer.Start() before peers.Add() 2017-05-13 10:24:59 +02:00
Anton Kaliaev
f803544195 new logging 2017-05-13 10:24:58 +02:00
Anton Kaliaev
8eb07800b3 Merge pull request #473 from tendermint/logging-arch-proposal
Logging architecture proposal
2017-05-12 20:40:28 +02:00
Anton Kaliaev
538b325150 update arch proposal [ci skip] [circleci skip] 2017-05-12 20:32:57 +02:00
Adrian Brink
cd3c3c3bad Modify makefile 2017-05-09 11:39:46 +02:00
Adrian Brink
8c91014cd8 Add git commit hash to version. 2017-05-09 11:37:59 +02:00
Adrian Brink
6312eb91be Change "make build" to set GitCommit variable
As described above.
2017-05-06 12:37:48 +02:00
Ethan Frey
d2ae7e164a Make testify a testImport for consistency 2017-05-05 19:46:32 +02:00
Ethan Buchman
627a686f90 Merge pull request #487 from tendermint/fixp2ptests
One silly tests passes on osx, fails on linux...
2017-05-05 12:53:39 -04:00
Ethan Frey
57527f9f67 One silly tests passes on osx, fails on linux... comment out so i can develop 2017-05-05 18:48:39 +02:00
Ethan Buchman
14d0d395f2 Merge pull request #484 from tendermint/config
Config
2017-05-05 12:46:39 -04:00
Ethan Buchman
edd7263f06 fixes from review 2017-05-05 12:25:53 -04:00
Ethan Frey
2a9e89b34f Add basic tests on config, mainly to raise test coverage 2017-05-05 15:50:23 +02:00
Ethan Frey
dd1f5a2268 Test config parsing in root command 2017-05-05 15:30:39 +02:00
Ethan Buchman
8a0466d81d config: pex_reactor -> pex 2017-05-05 02:04:24 -04:00
Ethan Buchman
fb9d3842e4 test: p2p.seeds and p2p.pex 2017-05-05 01:28:43 -04:00
Ethan Buchman
8c3823545d update glide 2017-05-05 00:51:03 -04:00
Ethan Buchman
75989342b0 fixes from rebase 2017-05-04 23:03:42 -04:00
Ethan Buchman
46151720f8 fix tests 2017-05-04 22:46:41 -04:00
Ethan Buchman
9109b20852 SetRoot 2017-05-04 22:46:41 -04:00
Ethan Frey
6b059e0063 Accept relative paths in all configs, TODO: must SetRoot 2017-05-04 22:46:40 -04:00
Ethan Frey
92dee7ea3c Commands compile (mostly) with new config reading 2017-05-04 22:46:40 -04:00
Ethan Frey
604bf03f3a Pulled out all config structs (except p2p.PeerConfig) into config package 2017-05-04 22:46:40 -04:00
Ethan Buchman
f217f2b2c5 cleanup run_node flags 2017-05-04 22:46:13 -04:00
Ethan Buchman
92bafa7ecd consensus: fix tests 2017-05-04 22:46:13 -04:00
Ethan Buchman
6afee8f117 rpc: fix tests 2017-05-04 22:45:13 -04:00
Ethan Buchman
1ef7c1d25b cmd: fixes for new config 2017-05-04 22:43:55 -04:00
Ethan Buchman
7db7bbe464 node: ConfigFromViper 2017-05-04 22:43:55 -04:00
Ethan Buchman
57151d6043 p2p: use cmn instead of . 2017-05-04 22:43:55 -04:00
Ethan Buchman
5d660e073a remove viper from p2p 2017-05-04 22:43:55 -04:00
Ethan Buchman
4982cb4d1f fix tests for state and mempool 2017-05-04 22:43:55 -04:00
Ethan Buchman
24ce90fc72 fix up config defaults 2017-05-04 22:43:55 -04:00
Ethan Buchman
75b6c5215f fewer structs. remove viper from consensus 2017-05-04 22:43:55 -04:00
Ethan Buchman
d8fb226ec4 new config 2017-05-04 22:43:55 -04:00
Ethan Buchman
95c74b2ccd remove some more viper 2017-05-04 22:43:55 -04:00
Ethan Buchman
f0e7f0acf8 remove viper from rpc except test 2017-05-04 22:43:55 -04:00
Ethan Buchman
1fcc9dc654 remove viper from proxy 2017-05-04 22:39:22 -04:00
Ethan Buchman
7c0f51e24b remove viper from mempool 2017-05-04 22:39:22 -04:00
Ethan Buchman
29c0e6e4f4 remove viper from blockchain and state 2017-05-04 22:39:21 -04:00
Ethan Buchman
56a1a2d917 remove logrotate.config 2017-05-04 22:39:03 -04:00
Anton Kaliaev
4871e64b03 update docker README [ci skip] [circleci skip] 2017-05-04 13:36:27 +04:00
Anton Kaliaev
809e0e8c59 update Dockerfile [ci skip] [circleci skip] 2017-05-04 13:32:46 +04:00
Ethan Buchman
4305d054d6 Merge pull request #465 from tendermint/bytes
RPC Serialization Overhaul
2017-05-03 14:37:21 -04:00
Ethan Buchman
9860c8fee1 rpc: cleanup some comments [ci skip] 2017-05-03 14:33:07 -04:00
Ethan Frey
7ebf011fcd Fixed rpctypes.Request creation to new format 2017-05-03 16:58:21 +02:00
Ethan Frey
4a1b714ca4 All tests pass without go-wire json ptr madness 2017-05-03 16:45:00 +02:00
Ethan Frey
4c1d41c12e Test json rpc parsing 2017-05-03 16:26:18 +02:00
Ethan Frey
6ba799132c json.RawMessage in RPCRequest to defer parsing 2017-05-03 16:13:58 +02:00
Adrian Brink
e5d8fcd198 Merge pull request #474 from faddat/patch-4
Fix Mintnet Kubernetes link
2017-05-03 13:56:45 +02:00
Adrian Brink
f31d6ffb8c Fix Mintnet kubernetes url 2017-05-03 13:55:42 +02:00
Ethan Buchman
2608b95b4b Merge pull request #463 from tendermint/feature/adrian-initchain
InitChain message gets send at genesis.
2017-05-01 12:00:29 -04:00
Adrian Brink
2bf8c40cff Add extra memory to virtual machine and add coverage report to gitignore. 2017-05-01 17:29:44 +02:00
Jacob Gadikian
b5ab74fd38 Update README.md
updated mintnet to mintnet-kubernetes
2017-05-01 15:50:11 +07:00
Anton Kaliaev
556fbf0c4c logging arch proposal [ci skip] [circleci skip] 2017-05-01 11:58:43 +04:00
Jae Kwon
4c7a2be06a Add Tx String representation 2017-04-30 16:06:49 -07:00
Ethan Buchman
6dbcfb32d2 comment on copied wire file 2017-04-28 23:22:54 -04:00
Ethan Buchman
efeadcc0f4 some cleanup from review 2017-04-28 23:18:38 -04:00
Ethan Buchman
297772e009 Merge pull request #467 from tendermint/nowire
Nowire
2017-04-28 22:58:39 -04:00
Ethan Buchman
aa9e673ed7 test: jq .result[1] -> jq .result 2017-04-28 22:31:30 -04:00
Ethan Buchman
4e781961e9 remove TMResult. ::drinks champagne:: 2017-04-28 22:26:23 -04:00
Ethan Buchman
884060eb9b rpc/lib: no Result wrapper 2017-04-28 22:04:14 -04:00
Ethan Buchman
07e59e63f9 TMEventDataInner 2017-04-28 17:57:06 -04:00
Ethan Buchman
ac28b12fa8 add readReflectJSON from wire 2017-04-28 17:56:44 -04:00
Ethan Frey
257f45b768 ebuchman: added some demos on how to parse unknown types 2017-04-28 22:01:46 +02:00
Ethan Buchman
acfbea6d49 rpc: decode args without wire 2017-04-28 14:36:38 -04:00
Ethan Frey
6c60c07f16 BROKEN: attempt to replace go-wire.JSON with json.Unmarshall in rpc 2017-04-28 16:24:06 +02:00
Ethan Frey
bff8402fe8 Fix json for TMResult to not include "TMResultInner" 2017-04-28 15:26:06 +02:00
Ethan Frey
f6f1f1992c Prepare rpc responses for go-data compatibility, still use go-wire 2017-04-28 14:46:04 +02:00
Ethan Frey
194f345470 Use non-standard port so tests don't die when I am running basecoin 2017-04-28 14:45:34 +02:00
Ethan Buchman
2bf7e9c968 update glide 2017-04-27 19:58:12 -04:00
Ethan Buchman
c930f43cbe rpc: fix tests 2017-04-27 19:56:14 -04:00
Ethan Buchman
a518d08839 rpc: response types use Result instead of pb Response 2017-04-27 19:34:25 -04:00
Ethan Buchman
cdf650fba9 rpc: repsonse types use data.Bytes 2017-04-27 19:06:07 -04:00
Ethan Buchman
bdb34f9f4e types: []byte -> data.Bytes 2017-04-27 19:01:18 -04:00
Ethan Buchman
0be3480729 consensus: comment about test_data [ci skip] 2017-04-27 18:34:57 -04:00
Ethan Buchman
495283e2d4 fix replay tests and update test wals for InitChain 2017-04-27 18:30:43 -04:00
Adrian Brink
842609ddcb Send InitChain message from ABCI to Core on Genesis
InitChain is send from the ABCI to the Core node when the ABCI
app has no blocks stored.
2017-04-27 20:22:11 +02:00
Ethan Buchman
1310c72647 version bump and changelog 2017-04-26 20:06:45 -04:00
Ethan Buchman
cc6dde96c1 rpc -> rpc/lib and rpc/tendermint -> rpc 2017-04-26 19:57:33 -04:00
Ethan Buchman
cc7b2d26e5 Merge branch 'master' into develop 2017-04-26 19:21:06 -04:00
Ethan Buchman
1781a52147 Merge pull request #459 from tendermint/http_codes
rpc: use HTTP error codes
2017-04-26 19:05:43 -04:00
Ethan Buchman
0ba449c8ba Merge pull request #455 from tendermint/unstable
Unstable
2017-04-26 19:04:52 -04:00
Ethan Buchman
f6e28c4975 Merge pull request #461 from tendermint/release-v0.9.2
Release v0.9.2
2017-04-26 11:07:00 -04:00
Ethan Buchman
6bcd4242f1 CHANGELOG and version bump 2017-04-26 00:17:53 -04:00
Ethan Buchman
9851265d4f rpc: use HTTP error codes 2017-04-25 23:09:47 -04:00
Ethan Buchman
098646c5ff test: test_libs all use Makefile 2017-04-25 18:35:22 -04:00
Ethan Buchman
0e5cd6dc2f Merge pull request #442 from tendermint/viper
go-config -> viper, commands: Run -> RunE
2017-04-25 17:59:17 -04:00
Ethan Buchman
2fcb2b9232 remove unsafe_set_config 2017-04-25 17:58:26 -04:00
Ethan Buchman
fcf78a5da7 cleanup go-config/viper and some unnamed imports 2017-04-25 14:54:56 -04:00
rigel rozanski
72c4be35e8 tiny fix 2017-04-25 13:44:13 -04:00
Rigel Rozanski
5d0c2a1414 commands: Run -> RunE 2017-04-25 13:44:13 -04:00
Rigel Rozanski
7bb638e3b8 fix test_integrations error 2017-04-25 13:44:13 -04:00
Rigel Rozanski
7448753257 fixing tests 2017-04-25 13:43:57 -04:00
Rigel Rozanski
6e662337ff dont export resetPrivValidator 2017-04-25 13:43:57 -04:00
Rigel Rozanski
270b68a893 glide lock updates 2017-04-25 13:43:22 -04:00
Rigel Rozanski
cefb2bede0 adding viper
int

int
2017-04-25 13:42:22 -04:00
rigelrozanski
47852122d0 changed reset commands 2017-04-25 13:34:46 -04:00
Ethan Buchman
00055fa2e8 Merge pull request #456 from tendermint/repo-merge
Repo merge
2017-04-25 13:13:32 -04:00
Ethan Frey
bd93f76950 Improve rpc to properly format any alias for []byte in URIClient 2017-04-25 17:17:51 +02:00
Ethan Frey
803b1f2115 Improve client test cases 2017-04-25 16:49:01 +02:00
Ethan Buchman
3cdd2daf08 fix tests 2017-04-21 18:44:37 -04:00
Ethan Buchman
4e0afc55e6 glide update 2017-04-21 18:35:48 -04:00
Ethan Buchman
e160318eef glide update 2017-04-21 18:21:59 -04:00
Ethan Buchman
56c60fba23 go-p2p -> tendermint/p2p 2017-04-21 18:19:41 -04:00
Ethan Buchman
9e82d132ce go-rpc -> tendermint/rpc 2017-04-21 18:19:29 -04:00
Ethan Buchman
a70c95b79e tmlibs/common/test -> tmlibs/test 2017-04-21 18:18:22 -04:00
Ethan Buchman
d5b524e309 go-merkle -> merkleeyes/iavl and tmlibs/merkle 2017-04-21 18:16:05 -04:00
Ethan Buchman
e6fe6b5b76 go-data -> go-wire/data 2017-04-21 18:13:25 -04:00
Ethan Buchman
d1926bcad1 use tmlibs 2017-04-21 18:12:54 -04:00
Ethan Buchman
fa451fc55c tendermint/rpc -> tendermint/rpc/tendermint 2017-04-21 18:10:41 -04:00
Ethan Buchman
5da9b3a803 postmerge 2017-04-21 18:09:47 -04:00
Ethan Buchman
93c58d0b24 remove glide and license from rpc and p2p 2017-04-21 18:08:25 -04:00
Ethan Buchman
23a6a6f8fc move into p2p package 2017-04-21 18:07:52 -04:00
Ethan Buchman
63f546497b Merge remote-tracking branch 'p2p/develop' into repo-merge 2017-04-21 18:06:57 -04:00
Ethan Buchman
c55d83281a move into rpc package 2017-04-21 18:05:39 -04:00
Ethan Buchman
35f1db09a9 Merge remote-tracking branch 'rpc/develop' into repo-merge 2017-04-21 18:04:42 -04:00
Ethan Buchman
34965f610d crypto Wrap/Unwrap 2017-04-21 18:02:25 -04:00
Ethan Buchman
eaeb547938 use tmlibs 2017-04-21 17:53:22 -04:00
Ethan Buchman
15d5b2ac49 use tmlibs 2017-04-21 17:51:11 -04:00
Ethan Buchman
992b11c450 premerge2: rpc -> rpc/tendermint 2017-04-21 17:39:56 -04:00
Ethan Buchman
0017fb7ffe premerge 2017-04-21 17:38:40 -04:00
Ethan Buchman
3240ce21b8 update glide 2017-04-21 17:28:13 -04:00
Ethan Buchman
207798b09a Merge pull request #454 from tendermint/reset_fix
reset fix
2017-04-21 17:27:29 -04:00
Ethan Frey
543eea4f4e update deps to unstable 2017-04-21 16:56:10 -04:00
Ethan Frey
6d223d5526 Update to latest go-crypto 2017-04-21 16:55:58 -04:00
Ethan Frey
3d9ca32e95 Update all config for p2p integration tests 2017-04-21 16:55:38 -04:00
Ethan Frey
90abc61c56 Improve go-data json support in rpc 2017-04-21 16:55:37 -04:00
Ethan Frey
6a0217688f Ensure private validator addresses are hex 2017-04-21 16:51:17 -04:00
Ethan Frey
b798169c6e Update go-crypto to read/write properly with go-wire in wal files 2017-04-21 16:51:17 -04:00
Anton Kaliaev
7e56aad51a [consensus/test_data/build.sh] install tendermint if absent 2017-04-21 16:51:17 -04:00
Ethan Frey
e325ffc681 Lots of updates to use new go-crypto / json style 2017-04-21 16:51:17 -04:00
Ethan Frey
516e78ea54 Fix types to use updated go-crypto 2017-04-21 16:50:27 -04:00
rigel rozanski
c21cec002c reset fix 2017-04-21 16:39:50 -04:00
Ethan Buchman
f89279cf11 fix CHANGELOG 2017-04-21 13:39:02 -04:00
Ethan Buchman
44f25864d9 Merge pull request #451 from tendermint/release-v0.9.1
Release v0.9.1
2017-04-21 13:35:23 -04:00
Ethan Buchman
7f20eca892 update glide 2017-04-21 13:09:55 -04:00
Ethan Buchman
2c8df0ee6b Merge pull request #17 from tendermint/develop
v0.7.0
2017-04-21 13:08:14 -04:00
Ethan Buchman
e8f33a4784 Merge pull request #25 from tendermint/develop
v0.5.0
2017-04-21 13:06:44 -04:00
Ethan Buchman
58ccefa407 update changelog 2017-04-21 13:06:26 -04:00
Ethan Buchman
e8cad948e3 cli: ResetAll doesnt depend on cobra 2017-04-21 12:54:53 -04:00
Ethan Buchman
53e2b9693a export ResetAll cmd 2017-04-21 12:46:12 -04:00
Ethan Buchman
559613689d Merge pull request #18 from tendermint/bugfix/fix-backward-compatibility-for-ws
fix backward compatibility for WS
2017-04-21 12:20:34 -04:00
Ethan Buchman
a01cff9ce6 jsonParamsToArgsRPC func 2017-04-21 12:18:21 -04:00
Ethan Buchman
62860e4919 Merge pull request #453 from tendermint/feature/rename-txid-to-hash
Rename txid to hash
2017-04-21 12:16:08 -04:00
Anton Kaliaev
5e5fb37774 rename TxID to Hash 2017-04-21 18:39:02 +03:00
Anton Kaliaev
d6fd0c4ca0 fix backward compatibility for WS 2017-04-21 18:30:22 +03:00
Ethan Buchman
7cf773e2d3 cli: testnet cmd inits files for testnet 2017-04-20 18:22:42 -04:00
Ethan Buchman
f5b77d50b5 fix setting log level 2017-04-20 17:56:49 -04:00
Ethan Buchman
757a548edf update glide 2017-04-20 17:56:35 -04:00
Ethan Buchman
17124989a9 Merge pull request #10 from tendermint/pex-reactor-fixes-#9
Pex reactor fixes #9
2017-04-20 17:32:38 -04:00
Ethan Buchman
75bad132fc msgCountByPeer is a CMap 2017-04-20 17:29:43 -04:00
Ethan Buchman
391c738959 update comment about outbound peers and addrbook 2017-04-20 12:21:45 -04:00
Anton Kaliaev
8655e2456e it is non-deterministic (could fail sometimes) 2017-04-20 13:37:06 +04:00
Anton Kaliaev
17ec70fc09 revert 2710873 2017-04-20 13:36:40 +04:00
Anton Kaliaev
9ce71013df revert e448199 2017-04-20 13:36:40 +04:00
Anton Kaliaev
5ab8ca0868 fix race 2017-04-20 13:36:40 +04:00
Anton Kaliaev
4c0d1d3ad2 return wg to addrbook 2017-04-20 13:36:39 +04:00
Anton Kaliaev
0277e52bd5 fix merge 2017-04-20 13:36:39 +04:00
Anton Kaliaev
cf18bf2966 add public RemoveAddress API
after discussion with @ebuchman (https://github.com/tendermint/go-p2p/pull/10#discussion_r96471729)
2017-04-20 13:36:39 +04:00
Anton Kaliaev
324293f4cb note on preventing abuse [ci skip] 2017-04-20 13:36:39 +04:00
Anton Kaliaev
52d9cf080e make GoLint happy 2017-04-20 13:36:39 +04:00
Anton Kaliaev
590efc1040 call saveToFile OnStop
This is better than waiting because while we wait, anything could happen
(crash, timeout of the code who's using addrbook, ...). If we save
immediately, we have much greater chances of success.
2017-04-20 13:36:38 +04:00
Anton Kaliaev
5eeaffd38e do not create file, just temp dir 2017-04-20 13:36:38 +04:00
Anton Kalyaev
07e7b98c70 improve ensurePeers routine
optimizations:

- if we move peer to the old bucket as soon as connected and pick only
  from new group, we can skip alreadyConnected check
2017-04-20 13:36:38 +04:00
Anton Kalyaev
873d34157d prevent abuse from peers 2017-04-20 13:36:38 +04:00
Anton Kalyaev
47df1fb7d4 test PEXReactor#Receive 2017-04-20 13:36:38 +04:00
Anton Kalyaev
1a59b6a3b4 replace repeate timer with simple ticker
no need for repeate timer here (no need for goroutine safety)
2017-04-20 13:36:38 +04:00
Anton Kalyaev
0109f1e524 test ensurePeers goroutine 2017-04-20 13:36:37 +04:00
Anton Kalyaev
37d5a2cf3e implement RemovePeer for PEXReactor 2017-04-20 13:36:37 +04:00
Anton Kalyaev
3af7c67757 add Dockerfile 2017-04-20 13:36:37 +04:00
Anton Kalyaev
26f661a5dd prefer short names 2017-04-20 13:36:37 +04:00
Anton Kalyaev
057cfb30f1 remove unused error 2017-04-20 13:36:37 +04:00
Ethan Buchman
1a42f946dc version bump 2017-04-19 00:05:18 -04:00
Ethan Buchman
e05052b079 update glide 2017-04-19 00:01:55 -04:00
Ethan Buchman
7d5b62b61f CHANGELOG and version bump 2017-04-18 23:58:24 -04:00
Ethan Buchman
a75353da6d version bump 2017-04-18 23:21:57 -04:00
Ethan Buchman
083fe959e2 Update README [ci skip] 2017-04-18 23:14:10 -04:00
Ethan Buchman
480b24d9f0 CHANGELOG [ci skip] 2017-04-18 23:05:48 -04:00
Ethan Buchman
aecf860b26 update glide 2017-04-18 22:27:24 -04:00
Ethan Buchman
bd369cc451 Merge pull request #450 from tendermint/fix-fastsync
blockpool: fix removePeer bug
2017-04-18 22:21:10 -04:00
Ethan Buchman
07143a4353 Merge pull request #412 from tendermint/feature/237-tx-indexing
tx indexing (Refs #237)
2017-04-18 22:20:48 -04:00
Ethan Buchman
bf7521a6ab Merge branch 'develop' into feature/237-tx-indexing 2017-04-18 22:20:13 -04:00
Ethan Buchman
fdeceb9a74 Merge pull request #449 from tendermint/fix-replay
Fix replay
2017-04-18 22:18:34 -04:00
Ethan Buchman
52d03d0071 post rebase fixes 2017-04-18 21:35:00 -04:00
Ethan Buchman
29a893b193 update comment 2017-04-18 21:28:11 -04:00
Jae Kwon
cf4074cc80 defer gr.Close() fixes 2017-04-18 21:28:10 -04:00
Ethan Buchman
cb2ed5bb7c fixes from review 2017-04-18 21:28:10 -04:00
Ethan Buchman
2ba3656ffd wal: gr.Close() 2017-04-18 21:28:10 -04:00
Jae Kwon
cd9e9e9f45 s/ExecBlock/ValExecBlock/g; s/sm.ApplyBlock/sm.ExecCommitBlock/g 2017-04-18 21:28:10 -04:00
Ethan Buchman
f9d0096744 support #HEIGHT based WAL 2017-04-18 21:28:10 -04:00
Ethan Buchman
935f70a346 comments and cleanup 2017-04-18 21:28:10 -04:00
Ethan Buchman
5109746b1c Handshake uses ApplyBlock, no ConsensuState 2017-04-18 21:28:10 -04:00
Ethan Buchman
1684ec163f ABCIResponses not needed as field in state 2017-04-18 21:27:50 -04:00
Ethan Buchman
3a973b80ac update glide 2017-04-18 21:27:31 -04:00
Ethan Buchman
ed03cb5c17 consensus/replay: remove timeout 2017-04-18 21:27:31 -04:00
Ethan Buchman
54b26869d5 consensus/wal: #HEIGHT -> #ENDHEIGHT 2017-04-18 21:27:31 -04:00
Ethan Buchman
cb279bf662 state: ABCIResponses, s.Save() in ApplyBlock 2017-04-18 21:27:31 -04:00
Ethan Buchman
9d2de2b756 tx_indexer -> tx_index 2017-04-18 20:55:40 -04:00
Ethan Buchman
e6b7e66bbe Merge pull request #23 from tendermint/more-tests
More tests
2017-04-18 20:26:54 -04:00
Ethan Buchman
45876d0828 NewBatch takes size, batch.Add doesn't use append 2017-04-18 20:23:58 -04:00
Ethan Buchman
b6a04a3456 more fixes from review 2017-04-18 20:11:53 -04:00
Ethan Buchman
f4d0076344 TxResult includes Tx. /tx only works if indexer active 2017-04-18 19:56:41 -04:00
Ethan Buchman
d572bb0c5d state/txindex and pkg per indexer impl 2017-04-18 19:29:02 -04:00
Anton Kaliaev
2ac69176e1 add a comment for MConnection#CanSend
also add a note to TestMConnectionSend
2017-04-18 12:11:48 +04:00
Ethan Buchman
00847cdc6b blockpool: fix removePeer bug 2017-04-15 02:22:03 -04:00
Anton Kaliaev
fbedb426ce tests for NetAddress 2017-04-14 16:37:07 +04:00
Anton Kaliaev
6dc113aa80 [netaddress] panic only when normal run 2017-04-14 14:56:02 +04:00
Anton Kaliaev
ebe23f1379 refactor MConnection#sendBytes 2017-04-14 14:21:58 +04:00
Anton Kaliaev
06d219db8e test peer with no auth enc 2017-04-14 12:43:28 +04:00
Ethan Buchman
16bffdf7ab rpc/test: restore txindexer after setting null 2017-04-13 16:38:44 -04:00
Ethan Frey
c648bd5b31 Test /tx with indexer disabled 2017-04-13 22:26:07 +02:00
Ethan Buchman
6e065affe5 rpc: /tx allows height+hash 2017-04-13 16:04:36 -04:00
Ethan Frey
4ee9acb8a7 Improve tx tests for both prove true/false 2017-04-13 16:04:35 -04:00
Ethan Frey
20458564b2 Expose Tx method in the clients 2017-04-13 21:49:21 +02:00
Ethan Buchman
c848056438 rpc: better arg validation for /tx 2017-04-13 15:18:58 -04:00
Ethan Frey
b33a7c46ce Break new Tx rpc endpoint 2017-04-13 20:49:06 +02:00
Ethan Frey
a4ee7d25d1 Add TxIndexEnabled method to ResultStatus 2017-04-13 20:21:40 +02:00
Ethan Buchman
58c860ba11 rpc/test: /tx 2017-04-13 14:18:35 -04:00
Ethan Buchman
90d1ed87fd add tx_indexer to NodeInfo 2017-04-13 14:18:20 -04:00
Ethan Buchman
df35989742 /tx can take height+index or hash 2017-04-13 13:47:48 -04:00
Ethan Buchman
23dbd0c8c3 enable tx_indexer by default 2017-04-13 13:36:12 -04:00
Ethan Buchman
257d81ddd1 rpc/core/types: uintX -> int 2017-04-13 13:35:16 -04:00
Anton Kaliaev
1d01f6af98 2 kinds of peers: outbound and inbound 2017-04-13 12:36:16 +04:00
Anton Kaliaev
715b8c629f use the peer struct to simulate remote peer 2017-04-13 12:09:43 +04:00
Anton Kaliaev
a63e1bb2dc fix possible panic 2017-04-13 12:08:57 +04:00
Anton Kaliaev
5965578c56 [fuzz] only one way to set config variables 2017-04-13 11:55:14 +04:00
Ethan Buchman
4671c44b2d Merge pull request #13 from tendermint/allow-for-multiple-restarts
[WSClient] allow for multiple restarts
2017-04-12 19:32:24 -04:00
Ethan Buchman
052c2c1575 Merge pull request #11 from tendermint/feature/refactor-tests
WSClient failing to echo bytes
2017-04-12 19:32:14 -04:00
Ethan Buchman
4b30cb3083 test: check err on cmd.Wait 2017-04-12 19:30:05 -04:00
Ethan Buchman
585ce45a5e rpc: dial_seeds msg. addresses #403 2017-04-12 19:12:22 -04:00
Ethan Buchman
6899c91ebe add optional 'prove' flag to /tx 2017-04-12 18:55:00 -04:00
Ethan Buchman
7fb0e8b30b Merge branch 'feature/tx-proof' into feature/237-tx-indexing
Conflicts:
	types/tx.go
2017-04-12 18:48:39 -04:00
Ethan Buchman
a1387c7c17 remove expected panic in test 2017-04-12 18:45:37 -04:00
Ethan Buchman
ffe6d58a58 add Height to ResultBroadcastTxCommit and EventDataTx 2017-04-12 18:33:48 -04:00
Ethan Buchman
2a59cda77e /tx returns tx bytes 2017-04-12 18:18:17 -04:00
Ethan Buchman
8c38543357 fix error msg 2017-04-12 18:15:51 -04:00
Ethan Buchman
2742831fb9 Merge pull request #443 from tendermint/draw_deps
Draw deps
2017-04-12 17:50:38 -04:00
Adrian Brink
6bcbd14d5a Add line counting badge 2017-04-12 17:39:47 -04:00
Adrian Brink
cf875a51fd Fix draw_deps in Makefile and add resulting dependency graph 2017-04-12 17:39:44 -04:00
Ethan Buchman
c34e136be9 update go-rpc to support map and array params 2017-04-12 13:44:10 -04:00
Ethan Buchman
c3295f4878 RPCRequest.Params can be map[string]interface{} or []interface{} 2017-04-12 13:42:19 -04:00
Ethan Frey
705e7bd577 Implemented and tested Txs.Index, hopefully better coverage 2017-04-12 15:18:09 +02:00
Ethan Frey
285a2a7061 More thorough testing of mutated bytes, use fixed go-wire 2017-04-12 15:18:09 +02:00
Ethan Frey
fd68bc7cfd Test Tx proofs secure 2017-04-12 15:16:46 +02:00
Ethan Frey
28307fd4c9 Add proof generation for one tx 2017-04-12 15:16:46 +02:00
Anton Kaliaev
7dcc3dbcd1 test peer 2017-04-12 16:55:17 +04:00
Ethan Buchman
72b2be51ec Merge pull request #446 from tendermint/fix-develop
Fix develop
2017-04-11 16:16:10 -04:00
Ethan Buchman
9775ecde99 update glide 2017-04-11 15:45:21 -04:00
Ethan Frey
c0f026a9b3 update go-rpc to fix race condition 2017-04-11 15:45:16 -04:00
Ethan Buchman
ac86e664c7 Revert "Undo last two commits"
This reverts commit d1fc37ff9e.
2017-04-11 15:44:36 -04:00
Ethan Buchman
c39e001a95 Merge pull request #22 from tendermint/persistent
fix closing conn
2017-04-11 13:40:06 -04:00
Ethan Buchman
8067cdb5f2 fix closing conn 2017-04-11 12:42:11 -04:00
Ethan Frey
9d18cbe74e Remove race condition between read go-routine and stop 2017-04-11 13:38:15 +02:00
Ethan Frey
d1fc37ff9e Undo last two commits 2017-04-11 12:57:06 +02:00
Ethan Buchman
7fbe8e47d4 fix tests 2017-04-10 17:32:48 -04:00
Ethan Buchman
d7c5690f17 index by bytes. add TxID to broadcast_tx responses 2017-04-10 17:21:37 -04:00
Ethan Frey
d3069b0f5b Update abci develop 2017-04-10 22:46:03 +02:00
Ethan Buchman
ebd3929c0d Merge pull request #18 from tendermint/13-reconnect-to-seeds
persistent peers (Refs 13)
2017-04-10 16:21:02 -04:00
Ethan Buchman
9a1a6c56b4 dont expose makePersistent 2017-04-10 16:05:00 -04:00
Ethan Buchman
b6f744c732 fix AddPeerWithConnection 2017-04-10 16:03:14 -04:00
Ethan Buchman
a9bb6734e7 SetDeadline for authEnc. Stop peer if Add fails 2017-04-10 16:02:01 -04:00
Ethan Frey
e4e17a2c95 Play well with go-{rpc,crypto,data}:develop 2017-04-10 21:16:41 +02:00
Anton Kaliaev
8bb3a2e1d7 persistent peers (Refs #13) 2017-04-10 22:47:05 +04:00
Anton Kaliaev
f88d56b2f8 add glide 2017-04-10 22:47:04 +04:00
Anton Kaliaev
5b0489cdb4 use plain struct instead of go-config 2017-04-10 22:46:49 +04:00
Anton Kaliaev
b8a939a894 test non persistent mconnection 2017-04-10 22:46:48 +04:00
Anton Kaliaev
2b02843453 remove unused const 2017-04-10 22:46:48 +04:00
Anton Kaliaev
5be72672fe use golang time datatype instead of time units in name 2017-04-10 22:46:48 +04:00
Anton Kaliaev
549d3bd09a tests for MConnection 2017-04-10 22:46:48 +04:00
Anton Kaliaev
868017cf1a import go-common as cmn 2017-04-10 22:46:48 +04:00
Anton Kaliaev
3478de50a1 no need for map - tx responses should arrive in order (Refs #237)
```
me: so we are executing them in order and receiving them in order and there is no way we could receive them out of order (due to network or something else), correct?
ebuchman: if we receive them out of order, ABCI is broken
ebuchman: so it is possible, if the ABCI server we're talking to is not implementing the spec
ebuchman: but that shouldn't justify us building a map
```
2017-04-10 22:44:08 +04:00
Anton Kaliaev
63704454a3 expose /tx?hash="XXXXXXXXXXXX" RPC call 2017-04-10 22:44:07 +04:00
Anton Kaliaev
b08f29cb71 add config option for tx indexing and disable it by default 2017-04-10 22:44:07 +04:00
Anton Kaliaev
d62e85757f execution test 2017-04-10 22:44:07 +04:00
Anton Kaliaev
c3f1b08b6a tx indexing (Refs #237)
save transactions to blockstore

move to a separate module

benchmark KVIndexer

batch write transactions

Benchmarks:

```
BenchmarkKVIndexerIndex-2         100000            516300 ns/op
PASS
ok      github.com/tendermint/tendermint/blockchain/tx  56.506s

5,16 s for 10000 transactions
1 s for 2000 transactions
```

```
BenchmarkKVIndexerIndex-2       h 3000000             8622 ns/op
PASS
ok      github.com/tendermint/tendermint/blockchain/tx  34.210s

86 ms for 10000 transactions
16 ms for 2000 transactions
```

```
BenchmarkKVIndexerIndex1-2               5000000              7160 ns/op
BenchmarkKVIndexerIndex500-2               20000           1750411 ns/op
BenchmarkKVIndexerIndex1000-2              10000           3573973 ns/op
BenchmarkKVIndexerIndex2000-2               5000           7836851 ns/op
BenchmarkKVIndexerIndex10000-2              1000          33438980 ns/op
PASS
ok      github.com/tendermint/tendermint/blockchain/tx  209.482s

7,8 ms for 2000 transactions
```

[state] write test for ApplyBlock

review comments

- move txindexer to state
- fix type

save Tx Index as well

do not store tx itself in the result
2017-04-10 22:44:07 +04:00
Ethan Buchman
fc95c9872f Merge pull request #438 from tendermint/replay-fix
consensus: timeout on replayLastBlock
2017-04-10 10:33:48 -04:00
Ethan Buchman
09f7dabd5e update comment 2017-03-28 14:06:03 -04:00
Ethan Buchman
4fd1471f11 remove BaseService.OnStart 2017-03-28 12:09:11 -04:00
Ethan Buchman
85e83934a1 fixes from review 2017-03-28 12:07:32 -04:00
Anton Kaliaev
ba5382b70e open result&error channels on start 2017-03-28 14:17:40 +04:00
Anton Kaliaev
b0d2032488 use BaseService.OnReset method to recreate channels 2017-03-28 14:01:22 +04:00
Ethan Buchman
162fbdd17b Merge pull request #419 from tendermint/cli_cobra
added use of Cobra CLI
2017-03-27 17:16:43 -04:00
Ethan Buchman
0413a87eb4 fix typo 2017-03-27 16:59:54 -04:00
Ethan Buchman
c1dc1a1a45 Merge pull request #437 from tendermint/feature/431-data-flag
rename TMROOT to TMHOME
2017-03-27 15:47:02 -04:00
Ethan Buchman
077cf13a1f consensus: timeout on replayLastBlock 2017-03-27 15:41:45 -04:00
Anton Kaliaev
a416c37ebd Merge pull request #12 from tendermint/close-ws-connection
close ws connection on Stop
2017-03-27 20:50:18 +04:00
Anton Kaliaev
12ead6cc7e make changes backwards compatible (Refs #431) 2017-03-27 20:41:00 +04:00
Anton Kaliaev
5f6de800a0 rename TMROOT to TMHOME (Refs #431) 2017-03-27 15:17:10 +04:00
Anton Kaliaev
d6587be7bc [WSClient] allow for multiple restarts
needed for 3044f66ba9
See https://github.com/tendermint/tools/issues/6
2017-03-21 22:08:08 +04:00
Anton Kaliaev
afc39febed close ws connection on Stop 2017-03-21 22:02:25 +04:00
Anton Kaliaev
b54b9b4ecc update url to network monitor [ci skip] [circleci skip] 2017-03-13 14:25:57 +04:00
Anton Kaliaev
5d19a008ce add Call method to WSClient, which does proper encoding of params 2017-03-10 15:33:45 +04:00
Anton Kaliaev
3233c9c003 WSClient failed to "echo_bytes"
Error:
```
Expected nil, but got: encoding/hex: invalid byte: U+0078 'x'
```
2017-03-10 14:56:04 +04:00
Anton Kaliaev
c88257b038 rename rpc function status to echo
echo means we're returning the input, which is exactly what this
function does.
2017-03-10 12:57:14 +04:00
Anton Kaliaev
0874c72819 refactor tests 2017-03-10 12:52:40 +04:00
Anton Kaliaev
d66ebbd904 use testify package 2017-03-10 12:03:16 +04:00
Anton Kaliaev
1a3573bf17 Merge pull request #10 from tendermint/feature/4-rename-http-clients
rename ClientURI -> URIClient, ClientJSONRPC -> JSONRPCClient
2017-03-10 10:42:22 +04:00
Anton Kaliaev
e6c083f589 rename ClientURI -> URIClient, ClientJSONRPC -> JSONRPCClient (Refs #4) 2017-03-10 10:41:10 +04:00
Anton Kaliaev
759060f47e Merge pull request #9 from tendermint/feature/8-http-interface-and-1-key-value-params-json-rpc
support key-value params in JSONRPC
2017-03-10 10:29:00 +04:00
Ethan Frey
715f78e26a Properly encode json.RawMessage 2017-03-10 10:20:38 +04:00
Anton Kaliaev
db69845ded introduce errors pkg 2017-03-09 19:01:37 +04:00
Anton Kaliaev
ff90224ba8 fix "Expected map but got type string" error
Error from tendermint:

```
panic: Expected map but got type string [recovered]
        panic: Expected map but got type string

goroutine 82 [running]:
testing.tRunner.func1(0xc420464000)
        /usr/local/go/src/testing/testing.go:622 +0x29d
panic(0xa1fda0, 0xc4201eecd0)
        /usr/local/go/src/runtime/panic.go:489 +0x2cf
github.com/tendermint/tendermint/rpc/test.waitForEvent(0xc420464000, 0xc420064000, 0xae6fae, 0x8, 0xae6f01, 0xc2e998, 0xc2e9a0)
        /home/vagrant/go/src/github.com/tendermint/tendermint/rpc/test/helpers.go:179 +0x53a
github.com/tendermint/tendermint/rpc/test.TestWSNewBlock(0xc420464000)
        /home/vagrant/go/src/github.com/tendermint/tendermint/rpc/test/client_test.go:190 +0x12e
testing.tRunner(0xc420464000, 0xc2e9a8)
        /usr/local/go/src/testing/testing.go:657 +0x96
created by testing.(*T).Run
        /usr/local/go/src/testing/testing.go:697 +0x2ca
```
2017-03-09 19:01:32 +04:00
Anton Kaliaev
720b74d89e read from ErrorsCh also 2017-03-09 17:44:00 +04:00
Anton Kaliaev
05e1a22d5b encode params before sending in JSONRPC 2017-03-09 13:46:48 +04:00
Anton Kaliaev
cf11e6ba65 add CHANGELOG 2017-03-09 12:43:24 +04:00
Anton Kaliaev
1ddb60b6e7 refactor jsonParamsToArgs
Suggested in https://github.com/tendermint/go-rpc/pull/9#discussion_r105098390
2017-03-09 12:23:21 +04:00
Ethan Buchman
5420254b36 changelog: add prehistory 2017-03-09 01:34:11 -05:00
Ethan Buchman
55b3c22d99 publish.sh to push build to s3 2017-03-09 01:34:11 -05:00
Anton Kaliaev
fed84f875c fix jsonParamsToArgsWS index error
Error from tendermint:
```
panic: runtime error: index out of range

goroutine 82 [running]:
github.com/tendermint/tendermint/vendor/github.com/tendermint/go-rpc/server.jsonParamsToArgsWS(0xc4200960e0, 0xc42024d4a0, 0xc420215380, 0x3, 0x0, 0x0, 0xc420215383, 0x9, 0xc42024d4a0, 0xf1ecc0, ...)
        /home/vagrant/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-rpc/server/handlers.go:184 +0x654
github.com/tendermint/tendermint/vendor/github.com/tendermint/go-rpc/server.(*wsConnection).readRoutine(0xc4201fd0e0)
        /home/vagrant/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-rpc/server/handlers.go:496 +0x3a9
created by github.com/tendermint/tendermint/vendor/github.com/tendermint/go-rpc/server.(*wsConnection).OnStart
        /home/vagrant/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-rpc/server/handlers.go:377 +0x45
```
2017-03-08 17:55:08 +04:00
Anton Kaliaev
1842e03315 revert using local import
this breaks the client's code (e.g. tendermint)
2017-03-08 17:33:46 +04:00
Anton Kaliaev
d033cd54b8 add editorconfig 2017-03-08 17:17:42 +04:00
Anton Kaliaev
2dc6ab3896 use golang default if an arg is missing (Refs #7) 2017-03-08 17:16:01 +04:00
Anton Kaliaev
6d66cc68ed make sure we are using correct server
also remove it afterwards
2017-03-08 16:55:15 +04:00
Anton Kaliaev
51d760f29f use local import for testing 2017-03-08 16:23:38 +04:00
Anton Kaliaev
a4154e76c5 update docker readme [ci skip] [circleci skip] 2017-03-08 14:09:54 +04:00
Anton Kaliaev
524f3b2d57 Merge pull request #429 from tendermint/update-docker-image-for-0.9.0
update Dockerfile for 0.9.0 release
2017-03-08 14:06:57 +04:00
Anton Kaliaev
d474baeeea update Dockerfile for 0.9.0 release 2017-03-08 14:05:32 +04:00
Anton Kaliaev
22ba8bdef8 fix Call method signature in HTTPClient interface 2017-03-08 10:26:13 +04:00
Anton Kaliaev
d43e3db978 fix circleci 2017-03-07 19:28:00 +04:00
Anton Kaliaev
26ccb4c94a remove private call methods
Q: what was the reason to create them?
2017-03-07 19:27:52 +04:00
Anton Kaliaev
c128957723 "must remove file for test to run again" - no way I am doing this by hands, too lazy :) 2017-03-07 19:27:38 +04:00
Anton Kaliaev
66867bf949 remove "rpc" prefix from package imports 2017-03-07 19:27:32 +04:00
Anton Kaliaev
e1d5873bdf support key-value params in JSONRPC (Refs #1)
More changes:

- remove Client interface (reason: empty)
- introduce HTTPClient interface, which can be used for both ClientURI
  and ClientJSONRPC clients (so our users don't have to create their own) (Refs #8)
- rename integration tests script to `integration_test.sh`
- do not update deps on `get_deps`
2017-03-07 19:27:27 +04:00
Anton Kaliaev
b03facd828 add Dockerfile 2017-03-07 18:34:13 +04:00
rigelrozanski
4e743649be glide update 2017-03-06 17:36:53 -05:00
rigelrozanski
fab518fc98 flag fix, glide update
squash
2017-03-06 17:32:42 -05:00
rigelrozanski
fa609366d4 melekes change request 2017-03-06 17:30:06 -05:00
rigelrozanski
569fd474c2 added use of Cobra CLI
squash
2017-03-06 17:30:06 -05:00
Ethan Buchman
d4f6254551 Merge pull request #426 from tendermint/release-0.9.0
Release 0.9.0
2017-03-06 05:34:45 -05:00
Ethan Buchman
e31ed6dc2f Merge branch 'master' into release-0.9.0 (woops) 2017-03-06 04:27:38 -05:00
Ethan Buchman
8449e9794a CHANGELOG 2017-03-06 04:25:55 -05:00
Ethan Buchman
07a9242dba update glide 2017-03-06 04:02:09 -05:00
Ethan Buchman
097da55a2c test/p2p: shellcheck 2017-03-06 03:49:48 -05:00
Ethan Buchman
97a5ed2d1a Merge pull request #16 from tendermint/develop
v0.4.0
2017-03-06 03:11:04 -05:00
Ethan Buchman
caaafa192b test/persist: use unix socket for rpc 2017-03-06 02:42:00 -05:00
Ethan Buchman
53d777a2d5 CHANGELOG.md 2017-03-06 01:30:41 -05:00
Ethan Buchman
fc6d22db32 test: better client naming 2017-03-06 01:11:00 -05:00
Ethan Buchman
d58a666445 test/persist: bump sleep to 5 for bound ports release 2017-03-06 00:32:24 -05:00
Ethan Buchman
22d95c7b51 test: docker exec doesnt work on circle 2017-03-05 23:38:11 -05:00
Ethan Buchman
b1cd677711 types: valSet LastProposer->Proposer and Proposer()->GetProposer() 2017-03-05 23:28:42 -05:00
Ethan Buchman
1208296dc0 DialSeeds takes an AddrBook 2017-03-05 23:14:15 -05:00
Ethan Buchman
cfc7fed31c test/pex: dial_seeds 2017-03-05 23:14:11 -05:00
Ethan Buchman
beb3eda438 fix addrbook start/stop 2017-03-05 22:59:18 -05:00
Ethan Buchman
c94bc2bc2b DialSeeds takes an addrbook 2017-03-05 21:57:07 -05:00
Ethan Buchman
e4e70ece3f test: fix docker and apps 2017-03-05 20:39:52 -05:00
Ethan Buchman
0fa34f7f67 fix ProposerSelection by persisting proposer 2017-03-05 19:45:24 -05:00
Ethan Buchman
55602b9be6 failing ProposerSelection test 2017-03-05 15:05:36 -05:00
Ethan Buchman
749df0536f test/docker: install abci apps first 2017-03-05 14:59:02 -05:00
Ethan Buchman
2037d2631a fix race 2017-03-05 03:40:36 -05:00
Ethan Buchman
de0153a1c4 consensus: some more informative logging 2017-03-05 02:15:46 -05:00
Ethan Buchman
d93d754972 test/p2p/fast_sync: use --pex on restart 2017-03-05 02:03:49 -05:00
Ethan Buchman
a5ce4f6c36 update glide 2017-03-05 00:19:53 -05:00
Ethan Buchman
05d8cd50b5 update glide and node.go for update to p2p.AddrBook 2017-03-04 23:45:54 -05:00
Anton Kaliaev
af5cd5cc75 [p2p tests] test other peers connect to us
if we have neither seeds nor the addrbook
2017-03-04 23:23:02 -05:00
Anton Kaliaev
4090a31d19 save seeds to addrBook (Refs #335) 2017-03-04 23:23:02 -05:00
Anton Kalyaev
163fe1731b test p2p pex reactor (Refs #335) 2017-03-04 23:22:48 -05:00
Anton Kalyaev
eef9124d1b fix typo 2017-03-04 23:21:57 -05:00
Ethan Buchman
56eebb95ee Merge pull request #12 from tendermint/bugfix/pex-issues-335
PEX issues #335
2017-03-04 23:19:51 -05:00
Ethan Buchman
88b5c724f2 remove public addr book funcs from pex 2017-03-04 22:55:42 -05:00
Anton Kaliaev
65b1756978 expose 2 API functions for tendermint#node/node.go 2017-03-04 22:44:25 -05:00
Anton Kaliaev
108beae7a8 more tests for AddrBook 2017-03-04 22:44:25 -05:00
Anton Kaliaev
2773410de4 prevent nil addr
Error:

```
Error: runtime error: invalid memoryaddress or nil pointer dereference\nStack:
goroutine 549 [running]:\nruntime/debug.Stack(0x0, 0x0,
0x0)\n\t/usr/local/go/src/runtime/debug/stack.go:24
+0x80\ngithub.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p.(*MConnection)._recover(0xc821723b00)\n\t/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p/connection.go:173
+0x53\npanic(0xbe1500, 0xc820012080)\n\t/usr/local/go/src/runtime/panic.go:443
+0x4e9\ngithub.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p.(*NetAddress).Valid(0x0,
0x0)\n\t/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p/netaddress.go:125
+0x1c\ngithub.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p.(*NetAddress).Routable(0x0,
0xc8217bb740)\n\t/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p/netaddress.go:117
+0x25\ngithub.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p.(*AddrBook).addAddress(0xc820108380,
0x0,
0xc821739590)\n\t/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p/addrbook.go:524
+0x45\ngithub.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p.(*AddrBook).AddAddress(0xc820108380,
0x0,
0xc821739590)\n\t/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p/addrbook.go:160
+0x286\ngithub.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p.(*PEXReactor).Receive(0xc82000be60,
0xc820149f00, 0xc8218163f0, 0xc82184e000, 0x5b,
0x1000)\n\t/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p/pex_reactor.go:109
+0x457\ngithub.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p.newPeer.func1(0xc82011d500,
0xc82184e000, 0x5b,
0x1000)\n\t/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p/peer.go:58
+0x202\ngithub.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p.(*MConnection).recvRoutine(0xc821723b00)\n\t/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p/connection.go:439
+0x1177\ncreated by
github.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p.(*MConnection).OnStart\n\t/go/src/github.com/tendermint/tendermint/vendor/github.com/tendermint/go-p2p/connection.go:138
+0x1a1\n
```
2017-03-04 22:40:48 -05:00
Anton Kalyaev
e7656873c1 public save API 2017-03-04 22:40:48 -05:00
Anton Kalyaev
332f7056f7 start/stop the book with reactor
Refs https://github.com/tendermint/tendermint/issues/335
2017-03-04 22:40:48 -05:00
Ethan Buchman
027cb8dc6b glide: use versions where applicable 2017-03-04 22:11:44 -05:00
Ethan Buchman
c7386b139b glide update 2017-03-04 22:05:14 -05:00
rigelrozanski
f5c4fdc82a seeds fix 2017-03-04 21:43:03 -05:00
Ethan Buchman
8352ec4e5d circle sigh 2017-03-03 19:58:17 -05:00
Ethan Buchman
8192bb0aaf stop rpc listeners in node.OnStop() 2017-03-03 19:47:39 -05:00
Ethan Buchman
b13924701e test/persist: wait for ports to be freed 2017-03-03 18:38:40 -05:00
Ethan Buchman
17e6ae813f Merge pull request #15 from tendermint/seedsfix
Seedsfix
2017-03-03 17:33:23 -05:00
Ethan Buchman
dab31d0166 version bump to 0.4.0 2017-03-03 17:30:38 -05:00
Ethan Buchman
0e7baf027b some dial seeds fixes 2017-03-03 16:42:10 -05:00
rigelrozanski
26275ba66c dial seeds error handling 2017-03-03 16:42:10 -05:00
Ethan Buchman
7098e5c7eb glide update 2017-03-03 01:33:13 -05:00
Ethan Buchman
4747f14a2c version bump to 0.9.0 2017-03-02 23:58:55 -05:00
Ethan Buchman
692691938c remove comment 2017-03-02 23:57:28 -05:00
Ethan Buchman
a200505ae5 Merge pull request #422 from tendermint/fix-race
Fix race
2017-03-02 23:56:18 -05:00
Ethan Buchman
8ba79252c8 types: use mtx on PartSet.String() 2017-03-02 23:50:59 -05:00
Ethan Buchman
6456654307 test: add extra kill after fail index triggered 2017-03-02 20:46:30 -05:00
Ethan Frey
21501815dd Fix EventSwitch usage in WaitForOneEvent 2017-02-27 14:55:29 +01:00
Ethan Frey
d56cb2ab4b fix typo 2017-02-24 23:40:05 +01:00
Ethan Frey
4fead237f0 Client embeds EventSwitch, client.HTTP properly un/subscribes events over websocket 2017-02-24 21:26:17 +01:00
Ethan Frey
6282fad518 Clean up event switch add helper function 2017-02-24 19:59:40 +01:00
Ethan Frey
175bb329e4 Expose EventSwitch on top of websocket client 2017-02-24 19:15:22 +01:00
Ethan Frey
9be3064904 Expose and test EventSwitch in client.Local 2017-02-24 17:51:19 +01:00
Ethan Frey
98450ee2db Client: DumpConsensusState, not DialSeeds. Cleanup 2017-02-24 17:05:15 +01:00
Ethan Frey
931af6a072 Combine local and http into client package, unify tests with table-driven tests 2017-02-24 17:05:15 +01:00
Ethan Frey
202146e4ce Fix up checktx/delivertx in broadcastTx(A)sync 2017-02-24 17:05:15 +01:00
Ethan Frey
9693795c4c Move common code to merkleeyes/testutil 2017-02-24 17:05:15 +01:00
Ethan Frey
cd9ee9d84b cleanup 2017-02-24 17:05:15 +01:00
Ethan Frey
42a9b847ec Make all client tests safe to run in parallel 2017-02-24 17:05:15 +01:00
Ethan Frey
d92a5b1074 Reworked WaitForHeight to avoid race conditions 2017-02-24 17:05:14 +01:00
Ethan Frey
f7f7cf576a Fix race condition in websocket event listening 2017-02-24 17:05:14 +01:00
Ethan Frey
26f4b5c98e Clean up package names 2017-02-24 17:05:14 +01:00
Ethan Frey
70f19e809b Add MockStatus, WaitForHeight helper 2017-02-24 17:05:14 +01:00
Ethan Frey
0905332f1d MockClient for real abci app 2017-02-24 17:05:14 +01:00
Ethan Frey
df172fa840 Provide mock interfaces for calling abci app over tendermint rpc 2017-02-24 17:05:14 +01:00
Ethan Frey
ce044dbb76 Extracted Clients into a consistent interface, fixed type issue in http.Client 2017-02-24 17:05:14 +01:00
Ethan Frey
7c26be3242 Begin implementation of local client 2017-02-24 17:05:13 +01:00
Ethan Frey
bf1ee89b27 Moved httpclient into subpackage 2017-02-24 17:05:13 +01:00
Ethan Frey
a0bdae4f9c Added missing pkg/errors dependency 2017-02-24 17:05:13 +01:00
Ethan Frey
64feaa05f4 Full test coverage for rpc client 2017-02-24 17:05:13 +01:00
Ethan Frey
5ea3f24304 test info 2017-02-24 17:05:13 +01:00
Ethan Frey
c9d36cd713 Add dependencies, pull out HTTPClient test code 2017-02-24 17:05:13 +01:00
Ethan Frey
2c75c9daf9 Clean up tests, remove panics 2017-02-24 17:05:12 +01:00
Ethan Frey
d971416d12 collision merge of light-client code 2017-02-24 17:05:12 +01:00
Anton Kaliaev
1f1dcead3d [Vagrantfile] go 1.8 and permissions fix 2017-02-24 13:31:27 +04:00
Anton Kaliaev
d38a6e329f verbose output when get_deps 2017-02-24 13:30:46 +04:00
Anton Kaliaev
f73f53c486 [Dockerfile.develop] fix error "/bin/sh: #: not found" when building 2017-02-23 12:17:20 +04:00
Ethan Buchman
b8279d424c Merge pull request #414 from tendermint/ci
Ci
2017-02-21 15:17:16 -05:00
Ethan Buchman
98a509ed97 Merge pull request #373 from melekes/bugfix/174-peer-send-failures-are-not-checked
Check `peer.Send` failures
2017-02-21 15:00:50 -05:00
Ethan Buchman
7c1e79cbc5 test/persists: wait for tendermint proc 2017-02-21 14:14:08 -05:00
Ethan Buchman
7fab31fbe3 test: more logging 2017-02-21 11:18:40 -05:00
Anton Kaliaev
2c724d5eee remove warning messages in favor of "Send failed" 2017-02-21 13:25:16 +04:00
Anton Kaliaev
6dbe9febce log warning if peer send failed (Refs #174)
make lint happy

remove dead code

remove not needed go-common dependency

check peer.Send failures (Refs #174)
2017-02-21 11:57:33 +04:00
Ethan Buchman
d754d210cd test: only use syslog on circle 2017-02-21 01:28:58 -05:00
Ethan Buchman
62adbe69ff Merge pull request #413 from tendermint/ci
test: forward CIRCLECI var through docker
2017-02-20 23:11:22 -05:00
Ethan Buchman
f3da6d23cb test: forward CIRCLECI var through docker 2017-02-20 22:53:14 -05:00
Ethan Buchman
a4d5ec491e Merge pull request #411 from tendermint/bugfix/init-should-not-overwrite-existing-files
do not overwrite existing files when doing `tendermint init`
2017-02-20 22:03:22 -05:00
Ethan Buchman
bed86da8ae Merge pull request #408 from tendermint/mock_app
handshake replay through consensus using mockApp
2017-02-20 22:01:26 -05:00
Ethan Buchman
0c4b6cd071 consensus: more handshake replay tests 2017-02-20 21:45:53 -05:00
Ethan Buchman
f9df4294f3 move some interfaces to types/services.go 2017-02-20 20:09:15 -05:00
Ethan Buchman
0765613778 move handshake to consensus package 2017-02-20 19:52:36 -05:00
Ethan Buchman
1fa6e7f3b1 test: shellcheck 2017-02-20 18:51:00 -05:00
Ethan Buchman
2b1b8da58d test/persist: dont use log files on circle 2017-02-20 18:41:29 -05:00
Ethan Buchman
756213c5f5 check appHash 2017-02-20 17:08:38 -05:00
Ethan Buchman
bc67859672 make ReplayBlocks logic exhaustive 2017-02-20 16:32:48 -05:00
Anton Kaliaev
a99885cd43 do not overwrite existing files when doing tendermint init (Fixes #410) 2017-02-20 11:14:27 +04:00
Ethan Buchman
44d472ddd3 comments from review 2017-02-18 22:15:59 -05:00
Ethan Buchman
7228b11e3f state: remove StateIntermediate 2017-02-17 19:13:35 -05:00
Ethan Buchman
0bec99fbd4 consensus: handshake replay test using wal 2017-02-17 19:12:05 -05:00
Ethan Buchman
3c5adebcd3 applyBlock to simplify replay of many blocks. still wip 2017-02-17 11:32:56 -05:00
Ethan Buchman
edc5e272db consensus: nice error msg if ApplyBlock fails 2017-02-17 10:57:09 -05:00
Ethan Buchman
6403b2f468 fixes for handshake replay through consensus 2017-02-17 10:51:05 -05:00
Ethan Buchman
cbe6dbe7a1 handshake replay through consensus using mockApp 2017-02-16 17:56:45 -05:00
Ethan Buchman
3ebd69db1b Merge pull request #405 from tendermint/rpc-commit
Rpc commit
2017-02-16 16:11:39 -05:00
Ethan Buchman
a3898fae0f rpc: fix SeenCommit condition 2017-02-16 15:35:34 -05:00
Ethan Buchman
75c856ed3f Merge pull request #404 from tendermint/feature/develop-docker-container
dockerfile for develop branch
2017-02-16 13:21:54 -05:00
Ethan Buchman
d081485e6a Merge pull request #402 from tendermint/feature/collect-logs-from-docker-containers
collect and add docker logs to CircleCI artifacts (Refs #387)
2017-02-16 13:13:13 -05:00
Ethan Buchman
bb5688b1be make: dont use -v on go test 2017-02-14 17:09:47 -05:00
Ethan Buchman
6f83f0bd4e glide update 2017-02-14 17:09:12 -05:00
Ethan Buchman
99b068b313 BlockMeta uses BlockID 2017-02-14 17:06:58 -05:00
Ethan Buchman
e229c8c3d7 rpc: /commit 2017-02-14 17:06:47 -05:00
Anton Kaliaev
6b499e2a8b add Makefile for docker files [ci skip] [circleci skip] 2017-02-15 01:10:29 +04:00
Anton Kaliaev
a756a9feba add readme mirroring https://hub.docker.com/r/tendermint/tendermint/ 2017-02-15 01:10:29 +04:00
Anton Kaliaev
d0ca0cb308 otherwise we end up with unmount errors due to busy disk
```
local_testnet_1
Failed to remove container (local_testnet_1): Error response from daemon: Unable to remove filesystem for 74e1104c705d4f21137bbe9e6710f33511948fc04d26475b482d1314fe70d537: remove /var/lib/docker/containers/74e1104c705d4f21137bbe9e6710f33511948fc04d26475b482d1314fe70d537/shm: device or resource busy
local_testnet_2
Failed to remove container (local_testnet_2): Error response from daemon: Unable to remove filesystem for 6f2ec44e01afd85875c1d9958afa957f1623ed9464df2b4fcac06feb8254145e: remove /var/lib/docker/containers/6f2ec44e01afd85875c1d9958afa957f1623ed9464df2b4fcac06feb8254145e/shm: device or resource busy
local_testnet_3
Failed to remove container (local_testnet_3): Error response from daemon: Unable to remove filesystem for 6160c73d45376920d90473a487a07f0e283e383011a0d23050b22cd82ab5d255: remove /var/lib/docker/containers/6160c73d45376920d90473a487a07f0e283e383011a0d23050b22cd82ab5d255/shm: device or resource busy
local_testnet_4
Failed to remove container (local_testnet_4): Error response from daemon: Driver btrfs failed to remove root filesystem c93a30d66ff3710617915a8f6075755ebc45aebf73569420225105cc81003e2f: Failed to destroy btrfs snapshot /var/lib/docker/btrfs/subvolumes for cac56069a3682b6d133e239f479fb82a67c4ccd09b877794d9f440a1125d59d6: operation not permitted

* [15:37:40] stopping rsyslog container
Failed to remove container (rsyslog): Error response from daemon: Driver btrfs failed to remove root filesystem 477287a170a48156e663c55092257064e1f14770d0b6c634a9972893636d9451: Failed to destroy btrfs snapshot /var/lib/docker/btrfs/subvolumes for 76b66d582a478743c099f479bf88eb334ad303ef607f91021dfa58d28c9161eb: operation not permitted
make: *** [test_integrations] Error 1
```
2017-02-14 20:40:23 +04:00
Anton Kaliaev
86f85525dd dockerfile for develop branch 2017-02-14 20:30:15 +04:00
Anton Kaliaev
ad354c4c48 stop containers to avoid futher errors
Error:

```
Failed to remove container (rsyslog): Error response from daemon: Unable to remove filesystem
```
2017-02-14 19:23:28 +04:00
Anton Kaliaev
b5bb1657d2 increase memory quota for Vagrant users
`make test_integrations` requires > 2Gi of memory
2017-02-14 19:09:03 +04:00
Anton Kaliaev
1275458c3f collect and add docker logs to CircleCI artifacts (Refs #387)
How: 1) we start syslog docker container 2) all other containers use
syslog logging driver to ship their logs to that container
2017-02-14 19:02:11 +04:00
Ethan Buchman
ac971c1a19 some docs fixes 2017-02-13 21:40:26 -05:00
Ethan Buchman
7d91d4300b update glide 2017-02-13 21:07:26 -05:00
Ethan Buchman
e972b942e6 Merge pull request #399 from tendermint/feature/cli-cleanup-gen-validator-output
[cli] cleanup gen_validator output
2017-02-09 13:32:30 -05:00
Anton Kaliaev
4896364952 [cli] cleanup gen_validator output (Fixes #396)
so we can pipe result to a file:

```
tendermint gen_validator > example.json
```

before this we had to cut first 3 lines:

```
tendermint gen_validator | sed 1,3d > example.json
```
2017-02-08 23:24:19 +04:00
Anton Kaliaev
ca21b6be93 update Vagrantfile
* glide now gets installed as a part of make get_vendor_deps
* rm go .tar.gz file
* autoremove garbage
* set LC_ALL to en_US.UTF-8
2017-02-08 22:56:17 +04:00
Ethan Frey
d4b3dde853 make install now uses vendored dependencies 2017-02-08 19:28:25 +01:00
Ethan Buchman
1aceeb7116 Merge pull request #392 from tendermint/feature/issue-template
ISSUE_TEMPLATE for Github
2017-02-08 02:17:11 -05:00
Ethan Buchman
930b3bcf5c Merge pull request #393 from tendermint/feature/CONTRIBUTING.md
contributing.md
2017-02-08 02:16:22 -05:00
Ethan Buchman
937c06a0c9 Merge pull request #395 from tendermint/feature/alpine-docker-base-image
[docker] move to alpine base image
2017-02-08 02:11:57 -05:00
Ethan Buchman
77cc15a77a Merge pull request #394 from tendermint/feature/improve-circleci-setup
Improve CircleCI setup (WIP)
2017-02-07 09:25:07 -05:00
Anton Kaliaev
d5d7286cb6 improve circleci config
- update docker machine version to 0.9.0
- save coverage.txt as artifact
- save docker logs as artifact
- test if coverage.txt exists
- 2>&1 redirect stderr to stdout in tests
2017-02-07 13:16:47 +04:00
Anton Kaliaev
bf64dd21fd [docker] move to alpine base image
813Mb => 29.5Mb
2017-02-06 00:11:03 +04:00
Ethan Frey
36b5d86eda [ci skip] [circle skip] Document research on backing dbs 2017-02-05 16:29:37 +01:00
Ethan Frey
1bf5ae9c8d Finish main argument on merkle data store architecture 2017-02-03 19:44:08 +01:00
Ethan Frey
5c2ead741c Lots more text on transactions and interface 2017-02-03 18:54:19 +01:00
Ethan Frey
b31e5d7764 Starting some thoughts on merkle storage 2017-02-03 15:39:35 +01:00
Anton Kaliaev
e5ef3e3019 add ISSUE_TEMPLATE for github [ci skip] [circle skip] 2017-02-03 13:07:59 +04:00
Anton Kaliaev
d696550494 add CONTRIBUTING.md [ci skip] [circle skip] 2017-02-03 13:07:11 +04:00
Ethan Frey
5fe0440916 Strawman docs/architecture dir 2017-02-02 20:10:56 +01:00
Ethan Buchman
d545ac4c51 Merge pull request #383 from tendermint/feature/rename-dockerimage-to-tendermint
Rename docker image to tendermint
2017-01-31 11:18:18 -08:00
Ethan Buchman
23eb8691a8 Merge pull request #386 from tendermint/bugfix/385-dist-build-error
permissions error during make dist
2017-01-31 11:07:28 -08:00
Anton Kaliaev
f849e2c414 copy instead of move (Fixes #385)
```
mv: cannot move ‘./build/dist/windows_386.zip’ to ‘./build/dist/tendermint_0.8.0_windows_386.zip’: Permission denied
```
2017-01-31 11:30:54 +04:00
Anton Kaliaev
1f527c5013 fix go version in Vagrantfile 2017-01-30 12:03:09 +04:00
Anton Kaliaev
65dfacac4b do we really have to build in order to test? 2017-01-30 12:02:24 +04:00
Anton Kaliaev
c0e7d05b5c rename tmbase image to tendermint
The main reason is people usually expect docker image to have the same
name as the repo. Plus, tendermint is cleaner than tmbase.

tmbase would make sense if we had multiple docker images within
tendermint, but we don't.
2017-01-30 11:59:35 +04:00
Jae Kwon
67ab574e98 Cleanup, add stub for VerifyCommitAny 2017-01-29 13:50:53 -08:00
Ethan Buchman
846e6d3bda fix readme links [ci skip] 2017-01-29 13:38:54 -08:00
Ethan Buchman
9707cb4471 README for local testnets [ci skip] 2017-01-28 19:25:28 -05:00
Jae Kwon
7c15b54ccc Fix test/app/dummy_test.sh 2017-01-28 09:11:31 -08:00
Jae Kwon
1af930441c Support new Query message for proofs 2017-01-28 08:27:13 -08:00
Ethan Buchman
9257d648bf test: update docker to 1.7.4 2017-01-28 00:12:39 -05:00
Ethan Buchman
f890ae696a Merge remote-tracking branch 'anton/feature/binaries' into unstable 2017-01-27 23:22:47 -05:00
Ethan Buchman
82828524fe Merge remote-tracking branch 'anton/improvement/dockerfile' into unstable 2017-01-27 22:59:01 -05:00
Ethan Buchman
d120c328c9 Merge remote-tracking branch 'anton/feature/output-all-tendermint-commands' into unstable 2017-01-27 22:54:14 -05:00
rigelrozanski
449a29b817 fixed README link for contributing guidelines 2017-01-27 22:44:01 -05:00
Anton Kaliaev
ce18332b52 update Dockerfile
- update golang to 1.7.4
- version as env variable
- change DATA_ROOT from /tendermint/data to /tendermint (it's not just
  data that gets stored in DATA_ROOT; we create data folder on start; as
  a result we get /tendermint/data/data, which is confusing)
- remove noninteractive env vars (do we really need these?)
- remove nodejs dep (some apps may require nodejs, but core is not one
  of them; it was convenient before, but now I believe we ought to
  remove it because other people who are using java do not want a
  bloated container with nodejs)
- build tendermint inside a container (once again, it was convenient
  before, but now I am testing kubernetes and I don't want to wait every
  time TM compiles)
2017-01-27 21:10:13 +04:00
Anton Kaliaev
3b7a1d7149 check that we have enough arguments
Otherwise:

```
panic: runtime error: index out of range

goroutine 1 [running]:
panic(0xbb8de0, 0xc82000e080)
        /usr/local/go/src/runtime/panic.go:464 +0x3e6
main.main()
        /go/src/github.com/tendermint/tendermint/cmd/tendermint/main.go:48 +0x811
```
2017-01-24 21:20:29 +04:00
Anton Kaliaev
17e822757b output all commands 2017-01-24 21:19:45 +04:00
Anton Kaliaev
a388ff198d try to get version from version/version.go 2017-01-23 15:23:39 +04:00
Anton Kaliaev
cc2457f7d5 dist command to make binaries and package them for distribution 2017-01-23 14:45:13 +04:00
Anton Kaliaev
c6375e414d refactor Makefile
- mute most of the commands
- replace github.com/tendermint/tendermint with just "."
- introduce PACKAGES variable
- delete unused NEWLINE
2017-01-22 18:04:58 +04:00
Anton Kaliaev
e825d77736 add .editorconfig to maintain consistent coding style 2017-01-22 18:00:08 +04:00
Ethan Buchman
ce026f4099 Merge pull request #369 from tendermint/node_refactor
Refactor Node; Node is a simple BaseService
2017-01-20 14:19:37 -05:00
Jae Kwon
9a2dd8bc92 Refactor Node; Node is a simple BaseService 2017-01-15 16:59:10 -08:00
Jae Kwon
a073b1db9c Refactor replay console -> replay_file in consensus/replay_file.go 2017-01-15 16:19:02 -08:00
Jae Kwon
cf0cb9558a Clean glide files 2017-01-14 21:03:12 -08:00
Jae Kwon
0aecfe2dae Merge pull request #368 from tendermint/release-0.8.0
Merge release-0.8.0 to develop
2017-01-13 16:03:27 -08:00
Jae Kwon
764091dfbb Merge pull request #366 from tendermint/release-0.8.0
Release 0.8.0
2017-01-13 15:59:34 -08:00
Ethan Buchman
ab1fa4db8c test: split up test/net/test.sh 2017-01-13 17:20:03 -05:00
Ethan Buchman
9123e63a33 more glide updates 2017-01-13 00:54:06 -05:00
Ethan Buchman
ba7ca4f372 fix tests 2017-01-13 00:54:01 -05:00
Ethan Buchman
1e25e9f58f glide update for go-db test fix 2017-01-12 22:49:52 -05:00
Ethan Buchman
9b4660b458 version bump to 0.8.0 2017-01-12 22:07:55 -05:00
Ethan Buchman
16a5c6b2c8 update all glide deps to master 2017-01-12 22:05:03 -05:00
Ethan Buchman
fcea0cda21 Merge pull request #6 from tendermint/develop
v0.6.0
2017-01-12 22:02:40 -05:00
Ethan Buchman
6177eb8398 love you circley 2017-01-12 22:01:20 -05:00
Ethan Buchman
ac443fa61f run tests from bash script 2017-01-12 21:59:02 -05:00
Ethan Buchman
08f2b5bc84 get deps for testing 2017-01-12 21:51:34 -05:00
Ethan Buchman
de56442660 Merge branch 'master' into develop 2017-01-12 21:40:43 -05:00
Ethan Buchman
3d98f675f3 Merge pull request #11 from tendermint/develop
Develop
2017-01-12 21:39:57 -05:00
Ethan Buchman
67c9086b74 optional panic on AddPeer err 2017-01-12 21:09:24 -05:00
Ethan Buchman
e47722ecb2 Connect2Switches: panic on err 2017-01-12 20:49:48 -05:00
Jae Kwon
2b750ea49f Make Connect2Switches blocking 2017-01-12 20:49:48 -05:00
Ethan Buchman
58e42397f8 close conns on filter; fix order in MakeConnectedSwitch 2017-01-12 20:49:48 -05:00
Jae Kwon
bd353e004a QuitService->BaseService 2017-01-12 20:49:48 -05:00
Ethan Buchman
f347143b3d Merge branch 'master' into develop
Conflicts:
	cmd/tendermint/flags.go
	glide.lock
	glide.yaml
	node/node.go
	rpc/core/routes.go
	version/version.go
2017-01-12 20:48:10 -05:00
Ethan Buchman
c1952523cd update glide 2017-01-12 20:22:23 -05:00
Ethan Buchman
1afe0cb45f test: always rebuild grpc_client 2017-01-12 18:45:41 -05:00
Ethan Buchman
7075a8ed81 Merge pull request #365 from tendermint/rename
Rename
2017-01-12 16:41:52 -05:00
Ethan Buchman
d83ca54b36 file name fixes 2017-01-12 16:17:43 -05:00
Ethan Buchman
e0aead0be2 update glide 2017-01-12 16:12:41 -05:00
Ethan Buchman
94b6dd65ee AppendTx -> DeliverTx 2017-01-12 15:55:03 -05:00
Ethan Buchman
c147b41013 TMSP -> ABCI 2017-01-12 15:53:32 -05:00
Ethan Buchman
3a55339114 Merge pull request #364 from tendermint/collapse_info
tmsp: ResponseInfo and ResponseEndBlock
2017-01-12 15:43:59 -05:00
Ethan Buchman
2dd7030579 tmsp: ResponseInfo and ResponseEndBlock 2017-01-12 15:21:20 -05:00
Ethan Buchman
e7a12f8e38 cs.Wait() 2017-01-12 14:44:42 -05:00
Ethan Buchman
0525e8ed5c rearrange common_test.go; EnsureDir for privVal 2017-01-12 12:38:09 -05:00
Ethan Buchman
1d091bafe9 update glide 2017-01-12 11:00:43 -05:00
Ethan Buchman
814ef37f75 fix tests 2017-01-12 10:58:44 -05:00
Ethan Buchman
94fed25975 fix test 2017-01-12 10:22:23 -05:00
Ethan Buchman
56341de5eb Merge remote-tracking branch 'mappum/rpc-tests' into unstable 2017-01-12 02:46:10 -05:00
Ethan Buchman
3c589dac19 startConsensusNet and stopConsensusNet 2017-01-12 02:29:53 -05:00
Ethan Buchman
0eb278ad3b version bump 0.6.0 2017-01-12 00:13:20 -05:00
Ethan Buchman
b494cc5219 Merge pull request #5 from mappum/develop
Fix hex string handling
2017-01-12 00:12:11 -05:00
Ethan Buchman
618fce8d32 update glide 2017-01-11 23:47:28 -05:00
Ethan Buchman
ce0c638005 little fix 2017-01-11 18:37:36 -05:00
Ethan Buchman
15d3d12098 Merge pull request #342 from akalyaev/feature/update-vagrant-setup
Feature: Update Vagrant setup
2017-01-11 18:03:20 -05:00
Ethan Buchman
76b4a45f98 Merge pull request #360 from tendermint/optional-skip-timeout-commit
Optional skip timeout commit
2017-01-11 18:02:46 -05:00
Anton Kalyaev
535fc6cd63 test we can make blocks with skip_timeout_commit=false 2017-01-11 18:00:27 -05:00
Anton Kalyaev
3308ac7d83 set skip_timeout_commit to true for tests
For the tests its better to not use the timeout_commit, and to wait for all the
votes, because otherwise we can end up with timing dependencies in the testing
code which can lead to nondeterministic failures. That was part of the reason
for this change originally.
2017-01-11 18:00:26 -05:00
Anton Kalyaev
a1fd312bb1 make progress asap on full precommit votes optional (Refs #348) 2017-01-11 18:00:26 -05:00
Anton Kalyaev
b096651e10 fix glide error: unable to export dependencies to vendor directory
```
[ERROR] Unable to export dependencies to vendor directory: remove /home/vagrant/go/src/github.com/tendermint/tendermint/vendor/golang.org/x/sys/unix: directory not empty
```
2017-01-11 17:59:05 -05:00
Ethan Buchman
44f939c841 Merge pull request #359 from tendermint/val-set-changes
Val set changes
2017-01-11 17:56:52 -05:00
Ethan Buchman
d68cdce2d5 consensus: check HasAll when TwoThirdsMajority 2017-01-11 17:53:46 -05:00
Jae Kwon
43fdc4a1ce Fix #341 2017-01-11 08:57:10 -08:00
Anton Kalyaev
cb2f2b94ee log stages to stdout 2017-01-11 10:35:04 -05:00
Anton Kalyaev
4722410e5e test validator set changes more extensively 2017-01-11 10:35:04 -05:00
Ethan Buchman
55b4bfa1fe consensus: let time.Timer handle non-positive durations 2017-01-11 10:24:40 -05:00
Matt Bell
4d7aa62a10 Added test for unexpected hex string type HTTP args 2017-01-07 20:40:45 -08:00
Matt Bell
86506cd4f8 Handle quoted and hex string type HTTP args for both 'string' and '[]byte' type function args 2017-01-07 20:40:29 -08:00
Matt Bell
1532879c64 Fixed RPC client tests 2017-01-07 14:35:54 -08:00
Matt Bell
af1212897c Exit early in bash tests 2017-01-07 14:00:27 -08:00
Matt Bell
34a806578a Handle hex strings and quoted strings in HTTP params
Use 0x-prefixed hex strings in client

server: Decode hex string args

Encode all string args as 0x<hex> without trying to encode as JSON

Added tests for special string arguments

Fix server handling quoted string args

Added string arg handling test cases to bash test script
2017-01-07 13:59:33 -08:00
Ethan Buchman
12d92fd5db Merge pull request #343 from tendermint/restart_test
Crash/Restart tests
2017-01-06 11:55:05 -08:00
Ethan Buchman
bae0bc02a6 consensus: be more explicit when we need to write height after handshake 2017-01-05 20:16:42 -08:00
Anton Kalyaev
99974ddc8b update vagrant setup
I am in favor of docker, but people say that running docker containers
inside another container is bad.

Things included in provision:

- docker (latest)
- jq
- curl
- shellcheck
- golang 1.7
- glide
2016-12-26 21:21:06 +04:00
Ethan Buchman
f30a9752e2 more fixes from review 2016-12-23 11:11:22 -05:00
Ethan Buchman
c90985d309 test: set log_level=info 2016-12-22 22:25:47 -05:00
Ethan Buchman
bd222d6e3c test: more unique container names 2016-12-22 22:10:40 -05:00
Ethan Buchman
0c01b0ded9 state.State and wal.writeHeight after handshake 2016-12-22 22:10:36 -05:00
Ethan Buchman
e5fb681615 consensus: remove crankTimeoutPropose from tests 2016-12-22 22:03:42 -05:00
Ethan Buchman
c9698e4848 fixes from review 2016-12-22 22:03:42 -05:00
Ethan Buchman
0e7694ca94 state: AppHashIsStale -> IntermediateState 2016-12-22 15:01:22 -05:00
Ethan Buchman
f4e6cf4439 consensus: sync wal.writeHeight 2016-12-22 15:01:02 -05:00
Ethan Buchman
e4921733df test/persist: use fail-test failure indices 2016-12-22 02:49:54 -05:00
Anton Kalyaev
69a449a073 test/p2p: use PROXY_APP=persistent_dummy 2016-12-22 01:43:23 -05:00
Anton Kalyaev
30328548f7 test/p2p: kill and restart all nodes 2016-12-22 01:42:51 -05:00
Anton Kalyaev
57f3592411 fix 2 errors when running p2p tests more than once
Error #1:

```
Error response from daemon: network with name local_testnet already exists
```

Fixed by stopping and removing local_testnet containers and removing
the network

Error #2:

```
docker: Error response from daemon: Conflict. The name "/test_container_basic" is already in use by container a7cd15d479a964675e7f259de4ed852e7dfef85b447514728f437cd0b980a709. You have to remove (or rename) that container to beable to reuse that name..
```

Fixed by adding `--rm` flag.
2016-12-21 19:18:18 -05:00
Anton Kalyaev
1c24031dd2 rename COUNT to ID 2016-12-21 19:18:18 -05:00
Anton Kalyaev
3d47ef9d74 fix typo 2016-12-21 19:18:18 -05:00
Anton Kalyaev
6488894210 add .vagrant to .gitignore 2016-12-21 19:18:18 -05:00
Ethan Buchman
2f0d31b4b6 test: remove codecov patch threshold 2016-12-20 01:47:59 -05:00
Ethan Buchman
b2376058a1 blockchain: thread safe store.Height() 2016-12-20 00:45:45 -05:00
Ethan Buchman
e981ff4e7d tests: shorten timeouts 2016-12-20 00:17:41 -05:00
Ethan Buchman
b126ca0606 consensus: no internal vars in reactor.String() 2016-12-20 00:17:37 -05:00
Ethan Buchman
40b08f2494 consensus: mv timeoutRoutine into TimeoutTicker 2016-12-19 22:29:32 -05:00
Ethan Buchman
8211fa6ce4 enterNewRound on HasAll 2016-12-19 20:12:37 -05:00
Ethan Buchman
706dd1d6c5 test: dont start cs until all peers connected 2016-12-19 19:50:40 -05:00
Ethan Buchman
6bc3b8dc6d test: circle artifacts 2016-12-19 15:42:39 -05:00
Ethan Buchman
faf23aa0d4 consensus: TimeoutTicker, skip TimeoutCommit on HasAll 2016-12-19 15:42:36 -05:00
Ethan Buchman
18b3821e06 glide: update go-wire 2016-12-18 00:18:59 -05:00
Ethan Buchman
1bd700ee52 test: automate building consensus/test_data 2016-12-18 00:15:10 -05:00
Ethan Buchman
38783e7fa1 types: SignatureEd25519 -> Signature 2016-12-18 00:14:07 -05:00
Ethan Buchman
dcbb35089f consensus: wal.Flush() and cleanup replay tests 2016-12-17 23:43:17 -05:00
Ethan Buchman
f33cc3fb3b Merge pull request #325 from tendermint/sign_bytes
Sign bytes
2016-12-17 21:48:19 -05:00
Ethan Buchman
1b3766d802 types: canonical_json.go 2016-12-17 21:21:27 -05:00
zachary balder
da8b043612 sign bytes w struct literals 2016-12-17 21:21:27 -05:00
Ethan Buchman
ed42f70248 types: benchmark WriteSignBytes 2016-12-17 21:21:27 -05:00
Ethan Buchman
0204d3c6a6 Merge pull request #330 from tendermint/fix_tests
Fix tests
2016-12-17 21:18:14 -05:00
Ethan Buchman
81f91aebc2 test: crank circle timeouts 2016-12-17 15:16:58 -05:00
Ethan Buchman
de6bba4609 test: randConsensusNet takes more args 2016-12-17 14:45:20 -05:00
Ethan Buchman
c3a3cc76d8 Merge pull request #334 from tendermint/release-0.7.4
shame: version bump 0.7.4
2016-12-14 10:08:12 -05:00
Ethan Buchman
74ff489e63 shame: version bump 0.7.4 2016-12-14 10:05:25 -05:00
Ethan Buchman
55b47bcb8e Merge pull request #323 from tendermint/release-0.7.4
Release 0.7.4: feature flag: pex reactor
2016-12-14 09:44:34 -05:00
Ethan Buchman
bcd8712ec3 test: more cleanup on p2p 2016-12-12 16:00:21 -05:00
Ethan Buchman
b212aa0db3 fixes from review 2016-12-12 14:12:37 -05:00
Ethan Buchman
8390e88e27 fix flowrate dep and test 2016-12-09 01:28:08 -05:00
Ethan Buchman
bc95700dcf update README 2016-12-09 00:31:56 -05:00
Ethan Buchman
12c6594c9b rpc: remove restriction on DialSeeds 2016-12-09 00:31:53 -05:00
Ethan Buchman
d800a51da4 test: crank it to eleventy 2016-12-07 20:13:52 -05:00
Ethan Buchman
73502fab0d shame: forgot a file 2016-12-06 23:17:53 -05:00
Ethan Buchman
2425711734 blockchain: use ApplyBlock 2016-12-06 23:01:55 -05:00
Ethan Buchman
6be5bda8c9 types: copy commit bit array 2016-12-06 23:01:25 -05:00
Ethan Buchman
2abcde03ad tests: cleanup and fix scripts 2016-12-06 23:00:39 -05:00
Ethan Buchman
69ef1da58c types: copy vote set bit array 2016-12-06 20:53:02 -05:00
Ethan Buchman
8df32cd540 test: increase proposal timeout 2016-12-06 19:54:10 -05:00
Jae Kwon
3aa06d0851 Try CircleCI timeout extension again 2016-12-06 04:28:05 -08:00
Jae Kwon
e611e97339 Try to extend CircleCI timeout 2016-12-06 04:25:31 -08:00
Jae Kwon
3000c8b349 Update glide w/ TMSP updates 2016-12-06 04:04:08 -08:00
Jae Kwon
6f88d04ac4 call db.SetSync when necessary 2016-12-06 02:52:07 -08:00
Jae Kwon
1c16ce8cf0 Update go-db and tmsp 2016-12-06 02:18:13 -08:00
Jae Kwon
070728429b Upgrade autofile and merkle 2016-12-06 01:59:21 -08:00
Jae Kwon
918f76f96a Remove flowcontrol 2016-12-06 01:26:05 -08:00
Jae Kwon
4202c4bf20 Fix Merge pull request #319 2016-12-06 01:16:13 -08:00
Jae Kwon
eab2baa363 use go-flowrate instead of flowcontrol 2016-12-04 18:20:37 -08:00
Ethan Buchman
dc436e72f9 Merge pull request #255 from tendermint/broadcast_tx_grpc
broadcast_tx via grpc
2016-12-02 00:31:40 -05:00
Ethan Buchman
b74a97a4f6 update grpc broadcast tx 2016-12-02 00:29:25 -05:00
Ethan Buchman
2ef695da97 include check/append responses in broadcast_tx_commit 2016-12-02 00:29:25 -05:00
Ethan Buchman
db437e7a45 broadcast_tx via grpc 2016-12-02 00:29:25 -05:00
Ethan Buchman
538a50c9e8 Merge pull request #319 from tendermint/valset
Validator Set Changes
2016-12-02 00:28:07 -05:00
Ethan Buchman
0fe53dc5cf remove privValIndex; Stale->AppHashIsStale 2016-12-02 00:27:36 -05:00
Ethan Buchman
8b80f8ee05 feature flag: pex reactor 2016-11-30 23:07:45 -05:00
Ethan Buchman
2cee364692 addrbook: toggle strict routability 2016-11-30 22:57:21 -05:00
Ethan Buchman
3e7c7f51fa update glide 2016-11-23 19:44:25 -05:00
Ethan Buchman
2f9063c1d6 consensus: test validator set change 2016-11-23 18:20:46 -05:00
Ethan Buchman
65496ace20 test: tmsp query result is json 2016-11-22 21:50:54 -05:00
Ethan Buchman
64c7a0ad0d update glide 2016-11-22 21:28:57 -05:00
Ethan Buchman
5046d5b181 more handshake replay cleanup 2016-11-22 20:38:14 -05:00
Ethan Buchman
6f8c91b651 use NewValidator; fix setPrivValidatorIndex 2016-11-22 20:38:14 -05:00
Ethan Buchman
e0db20c0cf update privValidatorIndex on valset change 2016-11-22 20:38:14 -05:00
Ethan Buchman
e1e2c1c740 cleanup ReplayBlocks 2016-11-22 20:38:14 -05:00
Ethan Buchman
655b6300f5 val set changes 2016-11-22 20:38:14 -05:00
Ethan Buchman
d7f6c0775a remove LastCommitHeight 2016-11-22 20:38:14 -05:00
Ethan Buchman
a3d863f83b consensus: track index of privVal 2016-11-22 20:38:14 -05:00
Jae Kwon
deb4c428fd Update go-autofile 2016-11-21 20:29:30 -08:00
Jae Kwon
b8e94b1d30 Update autofile 2016-11-21 20:19:49 -08:00
Jae Kwon
a151216e5e Update go-autofile dependency; fixed checkTotalSizeLimit 2016-11-21 19:58:40 -08:00
Jae Kwon
e09950d3fb Use new Group semantics 2016-11-21 19:16:19 -08:00
Ethan Buchman
3206e101f5 Merge pull request #265 from tendermint/handshake
Handshake
2016-11-16 17:00:01 -05:00
Ethan Buchman
c6a648fad7 consensus: lock before loading commit 2016-11-16 16:47:31 -05:00
Ethan Buchman
904eeddf36 update glide 2016-11-16 16:25:52 -05:00
Ethan Buchman
07597dfd45 post rebase fixes for BlockID, partSize 2016-11-16 16:13:17 -05:00
Ethan Buchman
4360c360a4 move handshake to state, use Handshaker, more tests 2016-11-16 13:29:22 -05:00
Ethan Buchman
befd8b0cb2 post rebase fixes 2016-11-16 13:27:06 -05:00
Ethan Buchman
3f90fcae48 fail tests and fix 2016-11-16 13:26:39 -05:00
Ethan Buchman
8ec1839f5d save block b4 apply; track stale apphash 2016-11-16 13:26:39 -05:00
Ethan Buchman
fb9735ef46 rebase fixes and BeginBlock(hash,header) 2016-11-16 13:25:13 -05:00
Ethan Buchman
138de19e1e test: app persistence 2016-11-16 13:25:13 -05:00
Ethan Buchman
d3ae920bd0 state: ApplyBlock 2016-11-16 13:25:13 -05:00
Ethan Buchman
f37f56d4f1 fixes 2016-11-16 13:25:13 -05:00
Ethan Buchman
a0e4253edc handshake 2016-11-16 13:25:13 -05:00
Ethan Buchman
c3d5634efa begin block 2016-11-16 13:23:57 -05:00
Ethan Buchman
c05b2c5c59 Merge pull request #314 from tendermint/bft_fix_rebase
Bft fix rebase
2016-11-16 01:52:54 -05:00
Ethan Buchman
f763a9ef56 scripts/txs/random.sh 2016-11-16 01:32:13 -05:00
Ethan Buchman
81e6df0d57 cswal: write #HEIGHT:1 for empty wal 2016-11-16 01:23:19 -05:00
Jae Kwon
d83fc02597 MakePartSet takes partSize from config. fix replay test 2016-11-16 01:23:16 -05:00
Jae Kwon
95c8bb4252 Fixing issues from review in #229 2016-11-15 18:48:35 -05:00
Jae Kwon
c1729addce Fix BFT issue where VoteSetMaj23Message wasn't being sent where prs.Round == blockStore.Round() 2016-11-15 18:48:35 -05:00
Jae Kwon
3e3b034252 Make ConsensusReactor use ConsensusState's blockstore; debug functions 2016-11-15 18:48:34 -05:00
Ethan Buchman
9d0c7f6ec7 fix bft test. still halts 2016-11-15 18:47:19 -05:00
Ethan Buchman
c5a803a146 DataChannel -> StateChannel for Maj23Msg 2016-11-15 18:45:36 -05:00
Ethan Buchman
5f55ed2a40 consensus: ensure dir for cswal on reactor tests 2016-11-15 18:45:36 -05:00
Ethan Buchman
7afcf92539 consensus: fix panic on POLRound=-1 2016-11-15 18:45:36 -05:00
Ethan Buchman
57da2e4af5 make byzantine logic testable 2016-11-15 18:45:36 -05:00
Ethan Buchman
f837252ff1 consensus: test reactor 2016-11-15 18:37:33 -05:00
Jae Kwon
fd128c7180 Fix comments from review 2016-11-15 18:37:00 -05:00
Jae Kwon
ea4b60a602 Fix compile bug 2016-11-15 18:37:00 -05:00
Jae Kwon
b73a6905a1 Initial pass at bft_fix_2 completion 2016-11-15 18:37:00 -05:00
Jae Kwon
655d829314 Fix proposal sign bytes. Start tracking blockID in POL 2016-11-15 18:35:17 -05:00
Jae Kwon
1173a85c85 Use BlockID everywhere 2016-11-15 18:34:58 -05:00
Jae Kwon
40791d886d Add test for new VoteSet 2016-11-15 18:33:16 -05:00
Jae Kwon
7221887330 VoteSet can handle conflicting votes. TODO: add more tests 2016-11-15 18:33:16 -05:00
Jae Kwon
3c5a2f55c2 Add validator index and address to Vote. 2016-11-15 18:33:16 -05:00
Ethan Buchman
0b098a2eee use glide in install_tmsp_apps.sh 2016-11-15 18:05:38 -05:00
Ethan Buchman
1765d3c866 update glide 2016-11-15 15:57:03 -05:00
Ethan Buchman
1fedf5b332 Merge branch 'consensus_wal_autofile' into develop_old 2016-11-15 15:43:22 -05:00
Ethan Buchman
f94836783c Merge branch 'master' into develop_old 2016-11-15 15:43:10 -05:00
Jae Kwon
2aecb2a4a3 Ensure *_wal_dir exists 2016-11-05 09:15:34 -07:00
Jae Kwon
bf1bceec87 Use go-flowcontrol 2016-11-04 06:46:34 -07:00
Ethan Buchman
01a3ac50af update glide 2016-11-03 20:16:44 -04:00
Ethan Buchman
3ff9355e7b change some logs to debug 2016-11-03 20:13:39 -04:00
Ethan Buchman
94ac890859 send BeginBlock 2016-11-03 19:51:22 -04:00
Jae Kwon
3d3d8b5b7b cswal -> cs_wal_dir 2016-10-30 03:55:27 -07:00
Jae Kwon
1788a68b1c Consensus WAL uses AutoFile/Group 2016-10-28 15:01:14 -07:00
Jae Kwon
480f44f16c QuitService->BaseService 2016-10-28 12:14:24 -07:00
Jae Kwon
161e36fd56 QuitService->BaseService 2016-10-28 12:04:58 -07:00
Jae Kwon
9a089482dc Unnest 2016-10-28 11:58:09 -07:00
Jae Kwon
fc31b463b1 Don't use io.Seek*, not supported in older versions 2016-10-26 22:19:44 -07:00
Jae Kwon
539f8f91bd Update glide file w/ go-common develop branch & go-autofile 2016-10-26 21:59:56 -07:00
Jae Kwon
830e84adc4 Fix minor bug in Consensus WAL; Fix AutoFile dependency 2016-10-26 21:51:03 -07:00
Ethan Buchman
40f2a128b8 Merge pull request #307 from tendermint/release-0.7.3
Release 0.7.3
2016-10-20 21:36:40 -04:00
Ethan Buchman
e6e3853dc7 Merge pull request #3 from tendermint/develop
use EventSwitch interface; less logging
2016-10-20 21:31:26 -04:00
Ethan Buchman
1786890e32 Merge branch 'master' into release-0.7.3 2016-10-20 21:11:17 -04:00
Ethan Buchman
435d1e3da7 test: install glide for network test 2016-10-20 12:30:22 -04:00
Jae Kwon
642a24dc9c Mempool WAL 2016-10-17 16:54:51 -07:00
Jae Kwon
eab4e1cfa1 Remove redundant cs.WAL from NewNode() 2016-10-17 16:37:32 -07:00
Jae Kwon
a9d8039082 Fix peer memleak; stop goroutine when peer is offline 2016-10-17 11:29:43 -07:00
Ethan Buchman
2113b6f4bb rpc: use interfaces for pipe 2016-10-14 21:38:49 -04:00
Ethan Buchman
7d493774c7 log: move some Info to Debug 2016-10-14 20:27:50 -04:00
Ethan Buchman
de0fc87c1c test: use glide with mintnet/netmon 2016-10-12 12:28:34 -04:00
Ethan Buchman
f0871e4f5e update some scripts 2016-10-12 12:27:37 -04:00
Ethan Buchman
1b37c8affd version: bump 0.7.3 2016-10-12 00:24:24 -04:00
Ethan Buchman
3e29f2bdc2 Merge pull request #297 from tendermint/docs
remove INSTALL dir, add INSTALL.md, update DOCKER
2016-10-11 23:30:38 -04:00
Ethan Buchman
3f4af438c5 remove INSTALL dir, add INSTALL.md, update DOCKER 2016-10-11 23:27:59 -04:00
Ethan Buchman
2cb13bf852 Merge pull request #298 from tendermint/get_round_state
consensus: hvs.StringIndented() was missing a lock. addresses #284
2016-10-11 22:25:37 -04:00
Ethan Buchman
0098387fbf consensus: hvs.StringIndented needed a lock. addresses #284 2016-10-11 19:12:39 -04:00
Ethan Buchman
7e07919d9d Merge pull request #296 from tendermint/replay_fixes
Replay fixes
2016-10-11 16:36:21 -04:00
Ethan Buchman
71baad59df replay: ensure cs.height and wal.height match 2016-10-11 16:06:46 -04:00
Ethan Buchman
9365d33243 replay: more tests 2016-10-11 12:55:04 -04:00
Ethan Buchman
3c18d841fa replay: larger read buffer 2016-10-11 12:51:48 -04:00
Ethan Buchman
7dcb567e53 replay test data 2016-10-11 11:44:07 -04:00
Ethan Buchman
7a424e6b12 Merge pull request #291 from tendermint/type-safe-fire-event
Type safe fire event
2016-10-10 17:36:52 -04:00
Ethan Buchman
302bbc5dbd Merge pull request #295 from tendermint/codecov
add codecov.yml to lower threshold
2016-10-10 17:32:00 -04:00
Ethan Buchman
97a51c130f Merge pull request #290 from tendermint/mempool_txcache
Fix race condition; Refactor out txCache
2016-10-10 17:20:42 -04:00
Ethan Buchman
00d53714f9 add codecov.yml to lower threshold 2016-10-10 17:18:34 -04:00
Ethan Buchman
a07063f119 add test for mempool deadlock 2016-10-10 17:05:50 -04:00
Ethan Buchman
9393be7a49 update glide 2016-10-10 14:55:54 -04:00
Ethan Buchman
1eb390680d Merge pull request #8 from tendermint/develop
update MakeConnectedSwitches
2016-10-10 14:48:58 -04:00
Ethan Buchman
9d331715c0 Merge pull request #293 from ethanfrey/type-safe-fire-event
Add test for proper tx event
2016-10-10 14:36:01 -04:00
Ethan Frey
0665bc6e4b Add test for proper tx event 2016-10-10 09:55:47 +02:00
Ethan Buchman
855255d73e use EventSwitch interface; less logging 2016-10-10 03:22:34 -04:00
Ethan Buchman
35d4cca8bb type safe events 2016-10-10 03:10:29 -04:00
Jae Kwon
b38748ad1a Fix race condition; Refactor out txCache 2016-10-07 15:30:17 -07:00
Ethan Frey
22979d9365 Fire proper EventData object on append transaction 2016-10-01 22:12:48 +02:00
Ethan Buchman
be3592adf6 Merge pull request #280 from tendermint/develop
Develop
2016-09-26 00:44:53 +09:00
Ethan Buchman
a5f6069967 Merge pull request #279 from tendermint/codecov
Codecov and badges
2016-09-26 00:29:23 +09:00
Ethan Buchman
c481d2bcbb README shields 2016-09-26 00:17:58 +09:00
Ethan Buchman
a1649f774e test: codecov 2016-09-25 22:08:48 +09:00
Jae Kwon
22155df759 Merge pull request #276 from silasdavis/mempool-reap
Fix mistake in Mempool Reap documentation
2016-09-16 08:31:11 -07:00
Silas Davis
7f31ec3398 Fix doc comment on mempool reap 2016-09-16 17:09:18 +02:00
Ethan Buchman
153ac88672 update MakeConnectedSwitches 2016-09-14 00:57:53 -04:00
Ethan Buchman
121714c040 Merge branch 'master' into develop 2016-09-12 12:01:42 -04:00
Ethan Buchman
bd43cf2442 Merge pull request #272 from tendermint/hotfix-1.7.2
Hotfix 1.7.2
2016-09-11 16:29:23 -04:00
Ethan Buchman
c7e578ac0d check tmsp client err and set mustConnect=false 2016-09-11 16:08:46 -04:00
Ethan Buchman
0fd8c98301 test starting tendermint before app 2016-09-11 16:08:46 -04:00
Ethan Buchman
e36e79a474 Merge pull request #271 from tendermint/release-0.7.1
Release 0.7.1
2016-09-10 21:14:44 -04:00
Ethan Buchman
0b919f4fd2 proxy: nil -> nilapp 2016-09-10 20:46:12 -04:00
Ethan Buchman
25839d0bb5 test: add killall to dockerfile. cleanup 2016-09-10 20:11:58 -04:00
Ethan Buchman
7f538266ea test: add xxd dep to dockerfile 2016-09-10 19:00:02 -04:00
Ethan Buchman
364932238a bump version 0.7.1 2016-09-10 18:05:13 -04:00
Ethan Buchman
34024291af glide update 2016-09-10 18:04:16 -04:00
Ethan Buchman
a58e8d47c6 Merge pull request #270 from tendermint/query_rpc
Query rpc
2016-09-10 17:44:41 -04:00
Ethan Buchman
28ec26462a test: test dummy using rpc query 2016-09-10 17:42:12 -04:00
Ethan Buchman
caeda30b72 proxy: wrap NewTMSPClient in ClientCreator 2016-09-10 17:19:47 -04:00
Ethan Buchman
41918d619c expose query and info through rpc 2016-09-10 17:14:42 -04:00
Ethan Buchman
bfa690b6f7 config: reduce timeouts during test 2016-09-10 15:16:23 -04:00
Ethan Buchman
035ca7ef61 proxy: NewAppConns takes a NewTMSPClient func 2016-09-09 23:55:24 -04:00
Ethan Buchman
206d00ed8c fixes from review 2016-09-09 23:50:25 -04:00
Ethan Buchman
9fb84d66be Merge pull request #268 from tendermint/replay
consensus: no sign err in replay; fix a race
2016-09-09 23:04:39 -04:00
Ethan Buchman
525378a145 Merge pull request #267 from tendermint/fastsync_fix
Fastsync fix
2016-09-09 20:10:06 -04:00
Ethan Buchman
398428d711 Merge pull request #266 from tendermint/peer_filter
Peer filter
2016-09-09 20:00:53 -04:00
Ethan Buchman
f508f3f20b Merge pull request #6 from tendermint/develop
filter conn by addr/pubkey. closes #3
2016-09-09 19:45:12 -04:00
Ethan Buchman
987dac9ee0 consensus: no sign err in replay; fix a race 2016-09-08 19:00:59 -04:00
Ethan Buchman
9bb32f41f1 config: filter_peers defaults to false 2016-09-08 18:56:02 -04:00
Ethan Buchman
bf7ba17932 test/p2p: name client conts so we dont need to rm them because circle 2016-08-27 17:20:34 -04:00
Ethan Buchman
7bec333017 fix fast sync 2016-08-27 14:50:10 -04:00
Ethan Buchman
1bfd67dfc6 test: refactor bash; test fastsync (failing) 2016-08-27 14:50:07 -04:00
Ethan Buchman
943ad0e93f filter peers by addr/pubkey. closes #244 2016-08-25 14:20:11 -04:00
Ethan Buchman
72c44efd84 fix query conn 2016-08-25 14:16:28 -04:00
Ethan Buchman
642901d5aa filter conn by addr/pubkey. closes #3 2016-08-25 13:46:43 -04:00
Ethan Buchman
d9205a85d5 query conn 2016-08-24 01:45:45 -04:00
Ethan Buchman
3a7ee13ece proxy: typed app conns 2016-08-24 01:45:45 -04:00
Ethan Buchman
4802145e8f Merge pull request #249 from tendermint/lastsig
types: privVal.LastSignature. closes #247
2016-08-23 11:42:28 -04:00
Ethan Buchman
7df79d9339 Merge pull request #263 from silasdavis/fix-unsubscribe
Fix unsubscribe
2016-08-23 11:41:01 -04:00
Ethan Buchman
678599c7d4 consensus: add note about replay test 2016-08-23 11:33:18 -04:00
Silas Davis
92736f22e8 Fix unsubscribe 2016-08-23 10:40:42 +01:00
Ethan Buchman
3998bdbfc1 fixes from review 2016-08-17 23:08:43 -04:00
Ethan Buchman
1110c5d37d privVal.LastSignBytes and more replay tests 2016-08-14 13:33:03 -04:00
Ethan Buchman
a1c20ce866 types: privVal.LastSignature. closes #247 2016-08-14 13:33:03 -04:00
Ethan Buchman
4776a7bcbe fix circle.yml 2016-08-14 13:32:19 -04:00
Ethan Buchman
c4764ff916 update glide.lock 2016-08-10 02:16:44 -04:00
Ethan Buchman
bd429f3d4f config: all urls use tcp:// or unix:// prefix 2016-08-10 02:16:41 -04:00
Ethan Buchman
479510be0e support full urls (with eg tcp:// prefix) 2016-08-10 01:13:13 -04:00
Ethan Buchman
c90bde3187 some comments 2016-08-09 20:31:53 -04:00
Ethan Buchman
cdfbf05e8c Merge branch 'master' into develop 2016-08-07 00:17:42 -04:00
Ethan Buchman
64f773c886 Merge pull request #242 from tendermint/release-0.7.0
Release 0.7.0
2016-08-07 00:03:23 -04:00
Ethan Buchman
444077505b fix README 2016-08-06 23:41:12 -04:00
Ethan Buchman
deb295f738 Merge branch 'master' into release-0.7.0 (GPL->ASL) 2016-08-06 23:34:57 -04:00
Ethan Buchman
34f607fe49 test: README.md 2016-08-06 23:31:06 -04:00
Ethan Buchman
3ac9ff0dcc test: dont run cloud test on push to master 2016-08-06 23:30:46 -04:00
Ethan Buchman
628528da5a test/net: cleanup 2016-08-05 21:20:01 -04:00
Ethan Buchman
45ff05d47d test/net: use MACH_PREFIX 2016-08-05 20:42:57 -04:00
Ethan Buchman
0dde260c05 meow circle 2016-08-05 20:24:32 -04:00
Ethan Buchman
3aebc17bff net test 2016-08-05 20:02:08 -04:00
Ethan Buchman
dcf368632c test/net: install mintnet, netmon 2016-08-05 20:01:32 -04:00
Ethan Buchman
5ab3336c91 meow circle 2016-08-05 19:59:29 -04:00
Ethan Buchman
6fef314423 version bump and release branch 2016-08-05 19:15:14 -04:00
Ethan Buchman
6643e4969f tests: add throughput benchmark using mintnet and netmon 2016-08-05 19:02:43 -04:00
Ethan Buchman
f7086d0a4d circle: docker 1.10.0 2016-07-24 15:39:24 -04:00
Ethan Buchman
8987d29bee tests: broadcast_tx with tmsp; p2p 2016-07-24 14:08:47 -04:00
Ethan Buchman
8fd216b4f6 run CI tests in docker container 2016-07-23 19:38:44 -04:00
Ethan Buchman
cb6c3fb0b6 integrations tests and coverage badge 2016-07-23 13:38:30 -04:00
Ethan Buchman
eac43dc62b glide: update lock and add util scripts 2016-07-23 12:47:36 -04:00
Ethan Buchman
dea910cd3e Makefile: go test --race 2016-07-22 01:15:52 -04:00
Ethan Buchman
39ee59c26e server: return result with error 2016-07-22 01:13:16 -04:00
Jae Kwon
ded154fd28 GPLv3 -> Apache2.0 2016-07-18 11:51:37 -04:00
Ethan Buchman
ce97902897 Merge pull request #233 from tendermint/broadcast_commit
BroadcastCommit and remove txs from mempool cache
2016-07-12 15:05:38 -04:00
Ethan Buchman
05136ff09d update some comments 2016-07-12 14:58:16 -04:00
Ethan Buchman
7bf34d1fae rpc: unsafe_flush_mempool. closes #190 2016-07-12 14:58:06 -04:00
Ethan Buchman
54357bcf8f crank consensus timeout parameters for tests (see #236) 2016-07-12 14:25:27 -04:00
Ethan Buchman
f44336d57d consensus: don't print shared vars in cs.String() 2016-07-12 12:47:13 -04:00
Ethan Buchman
a1a90fd41f consensus: increase mempool_test timeout 2016-07-11 22:37:42 -04:00
Ethan Buchman
adab114674 glide: update go-common 2016-07-11 22:37:42 -04:00
Ethan Buchman
33d9877599 consensus: hvs.Reset(height, valSet) 2016-07-11 22:37:42 -04:00
Ethan Buchman
47acada2cb consensus: t.Fatal -> panic 2016-07-11 22:37:39 -04:00
Ethan Buchman
dd788c5631 consensus: fix race from OnStop accessing cs.Height 2016-07-11 20:55:07 -04:00
Ethan Buchman
e4c795f15c consensus: fix more races in tests 2016-07-11 20:40:48 -04:00
Ethan Buchman
a43d53ac6e rpc/tests: panic dont t.Fatal. use random txs for broadcast 2016-07-11 20:40:24 -04:00
Ethan Buchman
cadb9e8bfe mempool: don't remove committed txs from cache 2016-07-11 12:32:24 -04:00
Ethan Buchman
f3f257a626 fix glide grpc 2016-07-06 17:29:04 -04:00
Ethan Buchman
e8271c8a4b update tmsp glide 2016-07-06 17:14:57 -04:00
Ethan Buchman
4e5cdd6abb bash tests for broadcast_tx through rpc 2016-07-06 13:51:21 -04:00
Ethan Buchman
8ca615c301 wait until txs removed from mempool to fire tx events 2016-07-05 17:03:09 -04:00
Ethan Buchman
bc0b52293e update circle and glide 2016-07-05 15:40:53 -04:00
Ethan Buchman
7e3e9ee9d2 rpc: broadcast tests. closes #219 2016-07-05 14:54:33 -04:00
Ethan Buchman
65ebc344ac broadcast_commit 2016-07-05 14:26:20 -04:00
Ethan Buchman
5fb171edff mempool: remove bad txs from cacheMap 2016-07-05 14:26:10 -04:00
Ethan Buchman
574d735a81 Merge pull request #231 from tendermint/blockpool_race_fix_jae
Blockpool race fix
2016-07-05 13:33:57 -04:00
Jae Kwon
b25cfb0e0b Unify blockpool mtxs 2016-06-28 18:02:27 -07:00
Ethan Buchman
929cf433b9 fix chDesc race 2016-06-26 00:34:34 -04:00
Ethan Buchman
711d2541f5 MakeConnectedSwitches function 2016-06-26 00:34:23 -04:00
Ethan Buchman
ca674304c5 fix blockpool races. closes #188 2016-06-24 20:38:59 -04:00
Ethan Buchman
a8ac819139 link issue from readme 2016-06-23 20:40:16 -04:00
Ethan Buchman
a44e0e0f4b add test example 2016-06-23 20:37:35 -04:00
Ethan Buchman
0c70a4636a add better docs to readme 2016-06-23 20:33:04 -04:00
Ethan Buchman
7ea86f6506 fix test race and update readme 2016-06-21 15:19:56 -04:00
Ethan Buchman
7376a72dd7 circle badge 2016-06-21 14:40:24 -04:00
Ethan Buchman
981c6868ad fix race conditions in tests 2016-06-21 14:35:29 -04:00
Jae Kwon
aaea0c5d2e Update README.md 2016-06-20 03:03:14 -07:00
Ethan Buchman
bfd9940248 add circleci badge to readme 2016-06-16 19:24:23 -04:00
Jae Kwon
dd30b78fd6 Add CircleCI yaml file 2016-06-11 21:54:27 -07:00
Ethan Buchman
cac3cefd98 set log level. use p2p config 2016-06-11 20:19:58 -07:00
Ethan Buchman
6365c5efb5 bring back unsafe_set_config 2016-06-11 20:19:40 -07:00
Jae Kwon
c126ccd744 Fix glide, improve Makefile 2016-06-11 20:14:44 -07:00
Jae Kwon
16987fe143 Merge pull request #215 from tendermint/new_protobuf
Protobuf + GRPC
2016-06-11 11:14:24 -07:00
Ethan Buchman
2a1e7a427d support tmsp via grpc 2016-05-23 14:46:32 -04:00
Ethan Buchman
7383ead106 updates for new tmsp protobuf 2016-05-23 14:35:36 -04:00
Jae Kwon
2700510039 Fix glide lock for log15 2016-05-18 11:14:47 -07:00
Ethan Buchman
55ef4b225f link to website guides from readme 2016-05-16 11:16:53 -04:00
Jae Kwon
9a25ad7f24 Glide up to new tendermint/log15 2016-05-14 13:26:20 -07:00
Ethan Buchman
1f4a086fb6 Update README.md 2016-05-14 12:02:53 -04:00
Ethan Buchman
ffd703622e Update README with install directions 2016-05-14 12:02:12 -04:00
Ethan Buchman
5bd7692323 version bump 2016-05-12 00:10:46 -04:00
Ethan Buchman
6684a18730 fix test 2016-05-12 00:08:41 -04:00
Ethan Buchman
0dc6ebc325 configurable fuzz conn 2016-05-12 00:00:52 -04:00
Ethan Buchman
ffbd6d8782 drop the p2p_ 2016-05-11 23:47:51 -04:00
Ethan Buchman
b2e612fb79 default empty seeds. some node methods 2016-05-11 14:45:20 -04:00
Jae Kwon
d9c91f9c47 Glide update 2016-05-10 19:05:25 -07:00
Jae Kwon
ad17090a0f No global config 2016-05-08 15:00:58 -07:00
Jae Kwon
7d997ca8e6 No global config 2016-05-08 14:59:27 -07:00
Jae Kwon
1d9e89812a Remove go-alert dependency 2016-05-08 14:58:28 -07:00
Jae Kwon
4c114680a4 Remove spurious genesis.json 2016-05-05 11:39:14 -07:00
Jae Kwon
1f6ecdfdb9 Update README.md 2016-05-04 14:10:36 -07:00
Jae Kwon
0832a41a38 Update README.md 2016-05-04 14:10:15 -07:00
Jae Kwon
9b2dd6a137 Update README.md 2016-05-04 14:01:51 -07:00
Ethan Buchman
e8538d606a add blank client interface 2016-05-04 10:39:43 -04:00
Jae Kwon
99c19bae21 test100 2016-04-29 15:32:50 -07:00
Ethan Buchman
850d769273 allow no recheck if empty block 2016-04-29 14:23:04 -07:00
Ethan Buchman
39344a601d flush before commit 2016-04-29 14:23:04 -07:00
Ethan Buchman
5296507665 some mempool log statements 2016-04-29 14:23:04 -07:00
Ethan Buchman
0d308c7c0e update glide 2016-04-29 14:23:04 -07:00
Ethan Buchman
8e5e5c689f lock mempool for commit and update. closes #202 2016-04-29 14:23:04 -07:00
Ethan Buchman
09fe44a6b3 test for mempool commit/update concurrency bug 2016-04-29 14:23:04 -07:00
Jae Kwon
46d2a13288 Merge pull request #205 from tendermint/develop
Variety of optimization and some dev features
2016-04-28 21:24:13 -07:00
Ethan Buchman
501c4e4bac fixes from review 2016-04-26 22:17:13 -04:00
Ethan Buchman
523a170c3e EventDataTypeNewBlockHeader 2016-04-19 20:59:52 -04:00
Ethan Buchman
08d12a5c84 glide update 2016-04-19 20:45:33 -04:00
Ethan Buchman
922f720cf6 cswal_light logs own votes; fix tests 2016-04-19 20:45:33 -04:00
Ethan Buchman
16208dc172 glide update 2016-04-19 20:45:33 -04:00
Ethan Buchman
eaf222a756 check vote exists before verifiying 2016-04-19 20:45:33 -04:00
Ethan Buchman
ae295bd9b6 bump rpc version; add consensus version 2016-04-19 20:45:33 -04:00
Ethan Buchman
ae07c0171d light weight block event 2016-04-19 20:45:33 -04:00
Ethan Buchman
27eede190a glide go-p2p:develop 2016-04-19 20:45:33 -04:00
Ethan Buchman
d23f38b4f3 txs.Hash() to avoid extra allocs 2016-04-19 20:45:33 -04:00
Ethan Buchman
a34f9e082e lazy part_set reader 2016-04-19 20:45:33 -04:00
Ethan Buchman
cb80a7aa42 rpc: unsafe_write_heap_profile 2016-04-19 20:45:33 -04:00
Ethan Buchman
79c9a9f03a don't verify own block parts 2016-04-19 20:45:33 -04:00
Ethan Buchman
5e42c96267 crank the part size; prioritize data channel 2016-04-19 20:45:33 -04:00
Ethan Buchman
898f44ddda config: disable_data_hash (for testing) 2016-04-19 20:43:54 -04:00
Ethan Buchman
196af01707 maxTxs=-1 for Reap to return empty 2016-04-19 20:43:54 -04:00
Ethan Buchman
f5be3cd8f9 rpc: start/stop cpu profiler 2016-04-19 20:43:54 -04:00
Ethan Buchman
2215ad74ff consensus: cswal doesnt write any consensus msgs in light mode 2016-04-19 20:43:54 -04:00
Ethan Buchman
df25a22469 rpc: num_unconfirmed_txs (avoid sending txs back) 2016-04-19 20:43:54 -04:00
Ethan Buchman
0df4a723e9 support in process tmsp apps 2016-04-13 19:24:12 -04:00
Jae Kwon
39d72d5811 Remove fees 2016-04-03 04:51:44 -07:00
Jae Kwon
f17c4c1d57 s/Validation/Commit/g 2016-04-02 09:10:16 -07:00
Ethan Buchman
78c9d526c3 change some log.Info to log.Debug 2016-03-29 11:37:51 -07:00
Jae Kwon
4baf007fb8 Merge pull request #2 from tendermint/develop
make some params configurable
2016-03-27 20:44:10 -07:00
Jae Kwon
daa76dcff0 Fix CheckTx/Update race condition 2016-03-25 08:29:03 -07:00
Jae Kwon
d5ab243cfd Fix #198; Do not fast-sync when lone validator 2016-03-24 18:08:18 -07:00
Jae Kwon
a8ee0377d5 Use tmsp.Client interface 2016-03-24 10:42:05 -07:00
Jae Kwon
c3980cb165 Warn on proxy hash mismatch, not fail 2016-03-23 20:22:45 -07:00
Jae Kwon
8183e3201b CommitSync() returns tmsp.Result 2016-03-23 02:49:30 -07:00
Jae Kwon
de6f76758d Group (code,data,log) return values into types.Result 2016-03-20 17:10:59 -07:00
Jae Kwon
9b4b533f2f Pretty print JSON 2016-03-19 16:58:15 -07:00
Ethan Buchman
69c7ae5e3f version bump 2016-03-17 05:05:02 -04:00
Ethan Buchman
114d90bec8 don't reallocate on recvMsgPacket 2016-03-17 05:05:02 -04:00
Jae Kwon
3f6f149584 Revert "Fix tendermint_test config -- Address() spec has changed"
This reverts commit 8598283735.
2016-03-15 15:57:18 -07:00
Jae Kwon
8598283735 Fix tendermint_test config -- Address() spec has changed 2016-03-15 15:18:19 -07:00
Jae Kwon
81ba1e6177 Use go-crypto's CRand* 2016-03-13 10:01:32 -07:00
Jae Kwon
10619248c6 Use go-crypto CRand* 2016-03-13 09:42:36 -07:00
Ethan Buchman
389e4b8b69 config: toggle authenticated encryption 2016-03-10 19:07:01 -05:00
Jae Kwon
18d0da4ea3 Remove BeginBlock 2016-03-06 18:02:29 -08:00
Jae Kwon
3adb579cf1 Merge branch 'blockchain_aware' 2016-03-06 15:08:52 -08:00
Jae Kwon
2c1504f93c Reap takes maxTxs 2016-03-06 15:08:32 -08:00
Jae Kwon
03115cbf93 Fix tests; Tests run in their own directory 2016-03-06 15:05:50 -08:00
Jae Kwon
1bc871162d Conform to new go-config behavior; ApplyConfig not needed 2016-03-06 12:33:07 -08:00
Ethan Buchman
f28f791fff make some params configurable 2016-03-06 12:24:01 -08:00
Jae Kwon
fd85d0ef35 Merge pull request #192 from tendermint/params
configurable params, other fixes
2016-03-06 11:27:19 -08:00
Jae Kwon
16437867ff Starting to use tmsp.BlockchainAware 2016-03-05 20:57:36 -08:00
Ethan Buchman
08df13b16e update glide.lock 2016-03-05 17:22:59 -05:00
Ethan Buchman
06a7bb531b consensus: dont allow peer round states to decrease 2016-03-05 16:41:54 -05:00
Ethan Buchman
94f3d201e1 drop mempool_reap. use block_size=-1 instead 2016-03-05 16:41:54 -05:00
Jae Kwon
7f6aad20fb Add note on nondeterminism of Broadcast 2016-03-04 22:04:05 -08:00
Jae Kwon
11e0f7ed8e Update README.md 2016-03-03 16:54:23 -08:00
Ethan Buchman
085b3bc1f2 consensus: don't wait for wal if conS not running 2016-03-03 06:32:08 +00:00
Ethan Buchman
05af306a8d rpc: unsafe_set_config 2016-03-03 06:32:08 +00:00
Ethan Buchman
4430073fab dont log bad block part if round mismatch 2016-03-03 06:32:03 +00:00
Ethan Buchman
3891e4d66d config: cswal_light, mempool_broadcast, mempool_reap 2016-03-03 06:31:59 +00:00
Ethan Buchman
69d906f7dd drain internalMsgQueue and wait for cswal on quit 2016-02-29 18:02:22 -05:00
Ethan Buchman
c9ec9cf00e config: block size, consensus timeouts, recheck tx 2016-02-29 17:04:33 -05:00
Ethan Buchman
2c1324656b support local app reqRes 2016-02-27 07:03:31 +00:00
Ethan Buchman
94a1978ce4 allow nil or dummy for in-proc 2016-02-26 21:29:46 -05:00
Ethan Buchman
e2920d9702 use nil-app for in-proc 2016-02-26 20:07:04 -05:00
Jae Kwon
b987d38505 s/TMSPClient/Client/g 2016-02-21 23:56:46 -08:00
Jae Kwon
5266b56f43 Conform to TMSP NewServer 2016-02-21 23:45:10 -08:00
Ethan Buchman
ade64693bd w(oop)s 2016-02-19 02:11:50 +00:00
Ethan Buchman
254baa19f3 fixes for go-rpc unix socket updates 2016-02-19 02:06:11 +00:00
Ethan Buchman
1410693eae support unix domain websockets 2016-02-19 02:05:24 +00:00
Ethan Buchman
254693bf86 rpc_laddr is a list 2016-02-19 00:21:07 +00:00
Ethan Buchman
74130008f7 deduplicate dialFunc 2016-02-19 00:20:20 +00:00
Ethan Buchman
6607232a5d add support for unix sockets 2016-02-18 22:45:55 +00:00
Jae Kwon
cc18b5f38e Add update_deps 2016-02-15 17:29:52 -08:00
Jae Kwon
d31d3c58ad Recheck txs 2016-02-14 17:00:33 -08:00
Jae Kwon
d17d4fa106 Fix tmsp/example import paths 2016-02-14 15:03:55 -08:00
Jae Kwon
a6d37a49a2 s/GetHash/Commit/g 2016-02-14 13:11:01 -08:00
Jae Kwon
1da8729e09 Fix license. It should have been GPLv3 2016-02-09 08:42:17 -08:00
Jae Kwon
6a209ba3a8 Fix a block condition where cb is called immediately 2016-02-08 15:38:18 -08:00
Jae Kwon
a7523015f7 Fix fix -- ignore cb if mempool broadcastTx cb is nil 2016-02-08 15:25:25 -08:00
Jae Kwon
7613557528 Fix bug in mempool broadcastTx for duplicate txs 2016-02-08 15:22:49 -08:00
Jae Kwon
3092d4bbe9 Fix typo, broadcast_tx_asyn(c) 2016-02-08 15:14:41 -08:00
Jae Kwon
df2933d40d Merge branch 'blackstar' 2016-02-08 13:49:27 -08:00
Jae Kwon
1370f89864 Fix bug in receiveEventsRoutine error handling 2016-02-08 02:20:34 -08:00
Jae Kwon
8b7969d6ea Add comments about goroutine-safety 2016-02-08 00:58:12 -08:00
Jae Kwon
a4f57e164b BroadcastTx results 2016-02-08 00:48:58 -08:00
Ethan Buchman
50ac66f79b fast sync fixes 2016-02-07 16:56:59 -08:00
Ethan Buchman
cbf7ad61f3 change local app to dummy from counter 2016-02-06 11:07:50 -05:00
Ethan Buchman
16cd15b048 expose ports in dockerfile 2016-02-05 23:46:45 -05:00
Jae Kwon
baa18fb0f7 Docker image has home dir 2016-02-04 22:11:47 -08:00
Jae Kwon
f9da9fbfed Improved README.md 2016-02-04 21:21:13 -08:00
Jae Kwon
6c9428a3c9 Add support for nodejs5 2016-02-04 20:27:35 -08:00
Jae Kwon
f1b48ff009 Use protobuf enums for CodeType 2016-02-04 18:41:29 -08:00
Jae Kwon
a73a65a45b Use protobuf enums 2016-02-04 18:41:29 -08:00
Jae Kwon
3f49b509d2 Conform to protobuf TMSP 2016-02-04 18:41:29 -08:00
Ethan Buchman
45f57198cc client: wsc.String() 2016-02-03 02:01:28 -05:00
Ethan Buchman
fe660580a4 catchup replay fix 2016-02-02 23:05:24 -05:00
Ethan Buchman
c0024cc7b2 log invalid txs 2016-01-31 20:00:02 -05:00
Jae Kwon
24af8e3da2 Merge branch 'tmsp_v02' 2016-01-28 20:03:34 -08:00
Jae Kwon
0f1cf243fd Merge remote-tracking branch 'origin/replay' 2016-01-28 19:53:22 -08:00
Jae Kwon
8a3bba48e3 s/*EventDataRoundState/EventDataRoundState/g 2016-01-28 19:44:44 -08:00
Jae Kwon
236c7afe9e Conform to TMSP v0.2 2016-01-25 14:34:08 -08:00
Jae Kwon
26d64208d1 Use TMSPClient 2016-01-22 15:48:13 -08:00
Jae Kwon
254331485a ... 2016-01-22 12:48:04 -08:00
Jae Kwon
d6aa43fcda Fix broken test due to config requiring ~/.tendermint_test 2016-01-22 11:55:24 -08:00
Ethan Buchman
fbc5ac8052 print method in client log 2016-01-21 23:03:39 -05:00
Ethan Buchman
77a66f079f version folder, rpc core version 2016-01-20 16:25:26 -05:00
Ethan Buchman
3cce757adc move DialSeeds to go-p2p and add to rpc 2016-01-20 13:12:42 -05:00
Ethan Buchman
b9eec7e438 version bump 2016-01-20 13:07:57 -05:00
Ethan Buchman
9bc75eaf24 move DialSeeds in from tendermint/tendermint/node 2016-01-20 11:32:23 -05:00
Jae Kwon
4b40a58c0e Fix rpc/test import; Remove ~/.tendermint_test on each test 2016-01-18 13:18:45 -08:00
Ethan Buchman
273a65724d replayCatchup test 2016-01-18 16:13:54 -05:00
Jae Kwon
8be32257e7 Make subscribeToEvent have capacity 1 2016-01-18 12:18:09 -08:00
Ethan Buchman
26f0e2bc2d msgLogFP -> write ahead log 2016-01-18 14:44:45 -05:00
Jae Kwon
0380e404bd Conform to go-wire version 0.6.0 2016-01-17 21:30:06 -08:00
Ethan Buchman
3b06368569 rebase fixes 2016-01-14 20:15:33 -05:00
Ethan Buchman
6bcf53195f consensus: use replay log to avoid sign regression 2016-01-14 18:58:12 -05:00
Ethan Buchman
bc2a721a0a clean up replay output 2016-01-14 18:58:12 -05:00
Ethan Buchman
56076d4d0e some cleanup; log time with consensus msgs 2016-01-14 18:58:11 -05:00
Ethan Buchman
9fc0726504 timeoutProposeDelta 2016-01-14 18:58:11 -05:00
Ethan Buchman
298928dc44 fix replay bug from timeoutRoutine 2016-01-14 18:58:11 -05:00
Ethan Buchman
c0c2a4b968 use validation round in reconstructLastCommit 2016-01-14 18:58:11 -05:00
Ethan Buchman
2b13386d7b consensus: replay console 2016-01-14 18:58:11 -05:00
Ethan Buchman
6aaa5fb0bf consensus: msg saving and replay 2016-01-14 18:58:11 -05:00
Ethan Buchman
892174997b Merge pull request #178 from tendermint/rpc_tests
Rpc tests
2016-01-14 14:26:19 -05:00
Jae Kwon
f100404362 Make EventDataRoundState use json:"-" instead of Getter/Setter 2016-01-14 11:07:31 -08:00
Jae Kwon
3f1b567129 Remove signer from JSON output 2016-01-14 08:06:02 -08:00
Ethan Buchman
14735d5eb5 RawMessage fix 2016-01-13 22:16:56 -05:00
Ethan Buchman
91c734d02e client: ResultsCh chan json.RawMessage, ErrorsCh 2016-01-13 21:21:16 -05:00
Ethan Buchman
8e776a252b rpc: test cleanup 2016-01-13 21:20:25 -05:00
Ethan Buchman
3fdb4c03ab rpc: TMResult and TMEventData 2016-01-13 18:38:55 -05:00
Ethan Buchman
aff561d8c3 RPCResponse.Result is json.RawMessage 2016-01-13 18:37:35 -05:00
Ethan Buchman
799efb0629 merge/rebase fixes 2016-01-12 19:39:53 -05:00
Ethan Buchman
ee449a94c8 move ResultEvent to go-events 2016-01-12 19:15:10 -05:00
Ethan Buchman
fb59255095 use TendermintResult for rpctypes.Result 2016-01-12 19:15:10 -05:00
Ethan Buchman
0be13d1d27 move alert, events, rpc into own repos 2016-01-12 19:15:10 -05:00
Ethan Buchman
96547d0ca8 ws fixes; rpc tests 2016-01-12 19:14:02 -05:00
Jae Kwon
790cde028b Remove NewNodeDefault... 2016-01-12 16:04:34 -08:00
Jae Kwon
c9dbd81178 Merge remote-tracking branch 'remotes/origin/signer'
Conflicts:
	types/priv_validator.go
2016-01-12 15:58:48 -08:00
Ethan Buchman
0bcae125c2 use comma separated string for arg names 2016-01-12 18:29:31 -05:00
Ethan Buchman
3d59e13dd8 move from tendermint/tendermint 2016-01-12 16:50:06 -05:00
Ethan Buchman
c52524a215 Initial commit 2016-01-12 15:26:00 -05:00
Jae Kwon
4c12de6203 Flush msgs to remoteProxyApp automatically 2016-01-10 09:20:54 -08:00
Jae Kwon
7cf85c5e71 Change commit timeout to 1 sec for testing 2016-01-09 20:22:10 -08:00
Jae Kwon
37bb8868de Fixing Makefile to get_deps before install 2016-01-09 19:06:14 -08:00
Jae Kwon
5d06bb964b Fix comments about AppHash, rollbacks, etc 2016-01-09 12:09:31 -08:00
Jae Kwon
3e3c0083c7 Make order be decided first; Remove TMSP Commit/Rollback 2016-01-08 16:51:20 -08:00
Jae Kwon
792759c414 Updated Makefile to include test_novendor 2016-01-06 12:58:10 -08:00
Jae Kwon
cf3dc5a6ff Remove accidental files 2016-01-05 23:55:33 -08:00
Jae Kwon
9d71a0409c Add Glide files for project management 2016-01-05 13:19:41 -08:00
Jae Kwon
f0c80837a6 Include p2p connection status in RPC net_info 2016-01-03 06:21:56 -08:00
Jae Kwon
1d34bb173e HTTP responses are pretty JSON 2016-01-03 06:21:04 -08:00
Jae Kwon
1f2c1d0760 Fix prioritization logic; Add Status() 2016-01-03 06:20:18 -08:00
Jae Kwon
3abc18d7ba Add MConnection.Status() 2016-01-02 20:53:10 -08:00
Jae Kwon
ccbcb9f418 Reduce commit timeout for tests 2016-01-02 20:22:36 -08:00
Jae Kwon
74cdadec9f Refactor RPC to be more general 2016-01-02 16:23:29 -08:00
Jae Kwon
6132017f82 Remove mempool log bypass 2016-01-02 16:22:25 -08:00
Jae Kwon
9357e8ecf8 IsCaughtUp requires a peer 2016-01-02 16:21:40 -08:00
Jae Kwon
9247b0fbd2 Fix HeightVoteSet bug where first catchup vote doesn't get added 2015-12-31 15:11:51 -08:00
Jae Kwon
0e7b069cd8 Remove broken mmm benchmark that doesn't belong 2015-12-31 14:30:50 -08:00
Jae Kwon
dcc1caaf68 Make Receive() logging consistent 2015-12-31 14:27:05 -08:00
Jae Kwon
708ee232bc Add more unit benchmarks 2015-12-31 00:34:44 -08:00
Jae Kwon
5a8a9bfd69 Make fast_sync=true by default, with more relaxed conditions 2015-12-31 00:32:54 -08:00
Ethan Buchman
94194fea46 fix logging proposal when we might not have it 2015-12-29 15:39:24 -05:00
Jae Kwon
0c9b9fe8bb Change license to Apache2.0 2015-12-23 14:08:39 -08:00
Jae Kwon
ceb6e1e95f Make consensus logs use default log handler 2015-12-21 17:26:08 -08:00
Jae Kwon
d58b3d54b1 tendermint init makes random chain ID 2015-12-21 16:30:28 -08:00
Jae Kwon
a204f59ecb Merge pull request #171 from tendermint/init
Init
2015-12-21 16:28:04 -08:00
Jae Kwon
d87667a0c2 Conform to go-wire new TypeByte behavior for broadcasts 2015-12-21 15:18:16 -08:00
Ethan Buchman
6f5baa8414 rpc: add app_hash to /status 2015-12-21 18:13:42 -05:00
Jae Kwon
b9519391c2 Conform to go-wire new TypeByte behavior for PrivValidator as well 2015-12-21 15:02:37 -08:00
Ethan Buchman
5cbb5d2541 tendermint init 2015-12-21 17:52:00 -05:00
Jae Kwon
08d7980d80 Conform to go-wire new TypeByte behavior 2015-12-21 14:48:44 -08:00
Jae Kwon
44d8e62689 Confirm to go-wire new TypeByte behavior 2015-12-21 12:55:52 -08:00
Jae Kwon
5bf7796004 Add synchronous file write benchmark 2015-12-20 11:37:54 -08:00
Jae Kwon
e57f3596a1 Use go-wire's new Read/Write LengthPrefixed methods 2015-12-20 09:23:30 -08:00
Jae Kwon
f288e58c81 Prefix TMSP messages with length 2015-12-20 08:18:39 -08:00
Jae Kwon
0316dfc6f2 Update code.google.com to use golang.org 2015-12-17 13:27:30 -08:00
Ethan Buchman
28ec3d48fa signer interface for validators 2015-12-16 13:07:07 -05:00
Ethan Buchman
c3a8f202ab consensus: fix negative timeout; log levels 2015-12-15 14:44:58 -05:00
Jae Kwon
c95b89e98c Merge remote-tracking branch 'origin/consensus_refactor' into consensus_refactor_jae 2015-12-14 09:33:11 -08:00
Ethan Buchman
b9e143d956 Fireable -> EventSwitch; rs in EventDataRoundState; fixes from review 2015-12-14 00:38:19 -05:00
Ethan Buchman
261647a012 Enter* -> enter*. Comments/fixes from Jae 2015-12-13 20:48:09 -05:00
Ethan Buchman
4483971776 conR uses events to trigger newstep & hasvote broadcasts 2015-12-13 19:30:15 -05:00
Ethan Buchman
9dea9539b4 fix consensus tests 2015-12-13 16:41:13 -05:00
Jae Kwon
855cb0f906 Merge remote-tracking branch 'origin/develop' into consensus_refactor 2015-12-12 19:34:39 -08:00
Ethan Buchman
07a96a703e move updateToState back 2015-12-12 17:22:48 -05:00
Ethan Buchman
e30d1bbd04 updateRoundStep consistency 2015-12-12 16:25:49 -05:00
Ethan Buchman
334cab82c2 fix tests: propose and full round suites 2015-12-12 01:28:53 -05:00
Ethan Buchman
736bc1f02f public interface; max steps; move updateToState 2015-12-12 01:28:33 -05:00
Ethan Buchman
c3f880e758 fire timeout events in handleTimeout; internalMsgQueue 2015-12-11 11:57:15 -05:00
Jae Kwon
34f6f50a07 Conform to go-merkle SimpleProof.Aunts 2015-12-10 11:09:25 -08:00
Ethan Buchman
d9b55101e5 move routines to consensus state. drop locks and other go routines 2015-12-10 11:41:18 -05:00
Jae Kwon
ab1e8a35c6 Shorten consensus log events 2015-12-09 17:09:06 -08:00
Jae Kwon
f534410e57 Fix state/execution ExecBlock() not rolling back 2015-12-09 17:08:40 -08:00
Jae Kwon
d3d7ff4818 Add mempool cache to reduce proxyapp pressure 2015-12-09 14:10:31 -08:00
Jae Kwon
8b308c1c08 Tweak send/recv rates for performance test 2015-12-09 13:53:50 -08:00
Jae Kwon
dfdd3cf18f Tweak channel for performance test 2015-12-09 13:53:31 -08:00
Jae Kwon
ea378c5565 Improve logging 2015-12-09 12:30:42 -08:00
Jae Kwon
15b751107e Tweak logging; allow consensus to bypass filter 2015-12-09 09:38:09 -08:00
Jae Kwon
d0b8650edf Fix tests for counter application using uin64 2015-12-09 09:37:36 -08:00
Jae Kwon
ac4c43c3e6 Adding wire.JSON vs wire.Binary vs protobuf benchmarks 2015-12-08 15:33:26 -08:00
Ethan Buchman
4b6e992a47 timeoutRoutine 2015-12-08 16:00:59 -05:00
Jae Kwon
a62c7bfef1 Add benchmarking for RPC & wire 2015-12-08 08:11:29 -08:00
Jae Kwon
53f74d052f Fix deadlock bug in websocket client impl 2015-12-07 21:11:12 -08:00
Jae Kwon
3da76496b0 Fix BlockchainReactor bug w/ mismatched state.LastBlockHeight vs store.Height
This is due to a non-atomic saves of state.State vs blockchain.Store.
This is a simple hack.
2015-12-07 16:57:33 -08:00
Jae Kwon
12c7f00c44 Merge pull request #164 from tendermint/proxy_fix
didSend -> willSend
2015-12-06 10:07:36 -08:00
Ethan Buchman
2c595284d8 msgQueue and msgProcessor 2015-12-05 23:47:41 -05:00
Jae Kwon
67e74756f4 Remove PEX/AddrBook 2015-12-05 18:10:26 -08:00
Ethan Buchman
a7d0998bc0 didSend -> willSend 2015-12-05 21:06:36 +00:00
Jae Kwon
4347b91b89 Remove wrong comment 2015-12-05 09:48:08 -08:00
Jae Kwon
432a37857d Add RemoteAddr and ListenAddr to NodeInfo; Refactor IPRange logic 2015-12-05 09:44:03 -08:00
Jae Kwon
f37f578b1d Add RemoteAddr and ListenAddr to NodeInfo 2015-12-05 09:13:21 -08:00
Jae Kwon
35abb4df92 Allow for test apps to return nil hashes 2015-12-04 00:59:02 -08:00
Jae Kwon
e5b9a5e849 Add proxy_app as node flag 2015-12-04 00:47:11 -08:00
Jae Kwon
e67f385574 Conform to go-common WriteFile*(path,mode) 2015-12-04 00:03:09 -08:00
Jae Kwon
c37e25e76b Conform to go-common WriteFile*(path, mode) 2015-12-04 00:02:44 -08:00
Jae Kwon
543ca16b6f Conform to go-common EnsureDir(path, mode) 2015-12-03 23:50:17 -08:00
Jae Kwon
b52cd4969b Update README.md 2015-12-03 09:58:05 -08:00
Jae Kwon
465cb6d327 Make benchmarks a real package for go get ./... 2015-12-03 09:56:15 -08:00
Jae Kwon
09351996a4 Add GenesisDoc.SaveAs utility method 2015-12-03 09:51:10 -08:00
Jae Kwon
1df2d7b8eb Remove spurious programs 2015-12-01 22:05:44 -08:00
Jae Kwon
ef43af19ab Tendermint <-> Application refactor 2015-12-01 20:12:01 -08:00
Jae Kwon
a8dc417cd9 Add ProxyApp logic 2015-11-10 14:01:57 -08:00
Ethan Buchman
df9ef1e733 check peerMempoolChan for nil on Reset 2015-11-10 13:41:54 -08:00
Ethan Buchman
209bcf905e proposer selection tests. closes #53 2015-11-10 13:41:49 -08:00
Jae Kwon
d69b5c5ab6 Conform to go-wire 1.0 2015-11-10 13:10:43 -08:00
Jae Kwon
1c628a97ad Conform to go-wire 1.0 2015-11-10 12:29:43 -08:00
Jae Kwon
37b6255e42 Move process to go-process 2015-11-08 17:43:48 -08:00
Jae Kwon
e12f9d10e7 Bare consensus refactor 2015-11-01 11:34:08 -08:00
Jae Kwon
abc3a2cc3c initial commit 2015-10-25 18:21:51 -07:00
Jae Kwon
5abf2e3c43 Fixed docker file 2015-10-23 14:57:12 -07:00
Jae Kwon
b9f741e635 Updated Godeps with project factor 2015-10-22 19:49:57 -07:00
Jae Kwon
c4ed55d801 Refactor to move common libraries out of project 2015-10-22 17:39:06 -07:00
Jae Kwon
7c12c5aee3 Fix config bug where chain_id is default magic. Always read from genesis 2015-10-20 17:39:03 -07:00
Jae Kwon
df733fbaa5 Docker run.sh passes seeds and moniker; wire json pretty print 2015-10-18 14:44:52 -07:00
Jae Kwon
d51741df72 fix main compile bug 2015-10-18 09:04:46 -07:00
Jae Kwon
cc6e845364 go get -d for DOCKER 2015-10-18 08:55:53 -07:00
Jae Kwon
f70b548fb6 exit status 1 for unknown command 2015-10-18 08:45:18 -07:00
Jae Kwon
26905b1260 Make Tendermint genesis agnostic; wait for file to start node 2015-10-18 07:20:05 -07:00
Jae Kwon
313e25adf1 Edit DOCKER script 2015-10-17 22:46:48 -07:00
Jae Kwon
14356a7739 Added BufferCloser 2015-10-17 22:41:05 -07:00
Jae Kwon
82c65e423b fix mempool PeerState nil conversion bug 2015-10-17 15:25:18 -07:00
Jae Kwon
5102f7a9cb refactor process.Process to take files 2015-10-17 15:13:19 -07:00
Ethan Buchman
10de637496 upgraded DOCKER instructions 2015-10-13 12:57:34 -07:00
Jae Kwon
6d66223bf6 remove fast_sync from docker 2015-10-13 08:53:58 -07:00
Jae Kwon
fb62e1eb75 bump chain_id to 11.c 2015-10-12 17:43:17 -07:00
Jae Kwon
cb3a1fd095 Fixed a blockchain pool goroutine-leak bug 2015-10-12 16:49:46 -07:00
Jae Kwon
fd9f816050 refactor variable names, pool.requests -> pool.requesters 2015-10-12 16:39:05 -07:00
Jae Kwon
5631b1a728 fixes #152 and #153 2015-10-12 15:19:55 -07:00
Jae Kwon
0a28cabd57 remove temporary limit on num block transactions 2015-10-12 09:42:53 -07:00
Jae Kwon
13e25ef164 Merge remote-tracking branch 'origin/consensus_tests' into develop 2015-10-11 18:20:19 -07:00
Jae Kwon
fa956596dc Merge remote-tracking branch 'origin/config' into develop 2015-10-11 18:18:53 -07:00
Jae Kwon
fbf4a4323b fix memory leaks in VM 2015-10-11 17:59:38 -07:00
Jae Kwon
28c5e9b4ec variable name changes 2015-10-11 14:57:20 -07:00
Jae Kwon
252a7ed7d6 Merge branch 'mempool' into develop 2015-10-11 14:41:28 -07:00
Jae Kwon
898d1dc138 HACK FIX config chain_id
need to change this...
2015-10-06 09:51:32 -04:00
Ethan Buchman
b59ed8c9d2 refactor some state functions into state/types 2015-10-05 20:21:02 -04:00
Jae Kwon
8db93b874c added testnet addresses 2015-10-05 12:01:22 -07:00
Jae Kwon
2f60b5b674 fix mempool test 2015-09-29 12:31:37 -04:00
Jae Kwon
ceed000c58 Use ResetFor... callback instead of EventSwitch for mempool new blocks 2015-09-29 12:31:34 -04:00
Ethan Buchman
cccb722ba8 mempool tests 2015-09-29 12:30:46 -04:00
Ethan Buchman
12566f51af better mempool queueing 2015-09-28 22:58:02 -04:00
Jae Kwon
beff6216fe GPLv3 2015-09-28 09:19:31 -07:00
Ethan Buchman
bb662b8861 more config options 2015-09-25 11:58:11 -04:00
Ethan Buchman
a26e0b4d48 consensus tests 2015-09-23 10:56:17 -04:00
Jae Kwon
4e6ea7f9f7 Merge pull request #143 from tendermint/versioning
more versioning
2015-09-22 18:48:07 -07:00
Jae Kwon
2feb3ea651 Merge pull request #144 from tendermint/namereg
update namereg with longer names, more allowed chars
2015-09-22 18:43:50 -07:00
Ethan Buchman
b54522c60f more versioning 2015-09-16 05:08:06 +00:00
Ethan Buchman
e4f0e2b399 update namereg with longer names, more allowed chars 2015-09-15 19:43:22 -04:00
Ethan Buchman
632e77c1cf rs.CommitRound 2015-09-15 16:13:39 -04:00
Ethan Buchman
aab024f18d consensus events 2015-09-15 14:41:23 -04:00
Ethan Buchman
2b8157ce2a addVote takes index 2015-09-15 14:26:42 -04:00
Ethan Buchman
a61a8176f1 fixes https://github.com/tendermint/halt/blob/master/case1/analysis.txt 2015-09-15 14:26:21 -04:00
Ethan Buchman
555ecb095d precommit nil if locked and no POL 2015-09-15 14:25:50 -04:00
Jae Kwon
78768082a1 Merge branch 'json_time2' into develop 2015-09-15 00:56:16 -07:00
Jae Kwon
726f5475b0 rpc client SetPingHandler with 30 second timeout; wire time json test 2015-09-15 00:55:51 -07:00
Jae Kwon
47eee5ddd5 blockchain pool race condition fix 2015-09-12 08:47:59 -07:00
Jae Kwon
6e27837cbf Fix SetREMA() -- increments m.samples so it doesn't get reset 2015-09-12 08:47:15 -07:00
Jae Kwon
b468baf7ac IsCaughtUp works with new networks 2015-09-11 21:09:47 -07:00
Jae Kwon
891ad9c1f0 log_level is notice. add testnet addrs 2015-09-11 21:09:47 -07:00
Jae Kwon
1c17ea3b14 blockchain parameter && log tweaks 2015-09-11 21:09:27 -07:00
Jae Kwon
21d45023d3 various bug fixes 2015-09-11 21:09:01 -07:00
Jae Kwon
5e015bc669 Probable fix for #140 2015-09-11 21:09:01 -07:00
Jae Kwon
3a5741f70f Fix blockchain pool tests 2015-09-11 21:09:00 -07:00
Jae Kwon
625f23af13 Blockpool better timeouts, download rate observation, quicker switching to consensus; Id -> ID (sorry, this doesn't belong here) 2015-09-11 21:09:00 -07:00
Jae Kwon
65ecf4b3a2 bump testnet 2015-09-11 21:09:00 -07:00
Jae Kwon
c6e5948534 time writes milliseconds using ISO8601 format 2015-08-31 13:00:20 -07:00
Ethan Buchman
586498331b fix suicide 2015-08-26 18:02:13 -04:00
Jae Kwon
b9cbb0dac5 testnet10 2015-08-14 15:36:40 -07:00
Jae Kwon
ab24ae1da8 get_account fix 2015-08-14 14:47:25 -07:00
Jae Kwon
56b195a899 tendermint send_tx 2015-08-14 14:11:11 -07:00
828 changed files with 40742 additions and 88574 deletions

26
.codecov.yml Normal file
View File

@@ -0,0 +1,26 @@
#
# This codecov.yml is the default configuration for
# all repositories on Codecov. You may adjust the settings
# below in your own codecov.yml in your repository.
#
coverage:
precision: 2
round: down
range: 70...100
status:
# Learn more at https://codecov.io/docs#yaml_default_commit_status
project:
default:
threshold: 1% # allow this much decrease on project
changes: false
comment:
layout: "header, diff"
behavior: default # update if exists else create new
ignore:
- "docs"
- "*.md"
- "*.rst"

16
.editorconfig Normal file
View File

@@ -0,0 +1,16 @@
# top-most EditorConfig file
root = true
# Unix-style newlines with a newline ending every file
[*]
charset = utf-8
end_of_line = lf
insert_final_newline = true
trim_trailing_whitespace = true
[*.{sh,Makefile}]
indent_style = tab
[*.proto]
indent_style = space
indent_size = 2

4
.github/CODEOWNERS vendored Normal file
View File

@@ -0,0 +1,4 @@
# CODEOWNERS: https://help.github.com/articles/about-codeowners/
# Everything goes through Bucky and Anton. For now.
* @ebuchman @melekes

41
.github/ISSUE_TEMPLATE vendored Normal file
View File

@@ -0,0 +1,41 @@
<!-- Thanks for filing an issue! Before hitting the button, please answer these questions.-->
**Is this a BUG REPORT or FEATURE REQUEST?** (choose one):
<!--
If this is a BUG REPORT, please:
- Fill in as much of the template below as you can.
If this is a FEATURE REQUEST, please:
- Describe *in detail* the feature/behavior/change you'd like to see.
In both cases, be ready for followup questions, and please respond in a timely
manner. We might ask you to provide additional logs and data (tendermint & app)
in a case of bug.
-->
**Tendermint version** (use `tendermint version` or `git rev-parse --verify HEAD` if installed from source):
**ABCI app** (name for built-in, URL for self-written if it's publicly available):
**Merkleeyes version** (use `git rev-parse --verify HEAD`, skip if you don't use it):
**Environment**:
- **OS** (e.g. from /etc/os-release):
- **Install tools**:
- **Others**:
**What happened**:
**What you expected to happen**:
**How to reproduce it** (as minimally and precisely as possible):
**Anything else do we need to know**:

11
.gitignore vendored
View File

@@ -9,3 +9,14 @@ rpc/test/.tendermint
.tendermint
remote_dump
.revision
vendor
.vagrant
test/p2p/data/
test/logs
.glide
coverage.txt
docs/_build
docs/tools
scripts/wal2json/wal2json
scripts/cutWALUntil/cutWALUntil

546
CHANGELOG.md Normal file
View File

@@ -0,0 +1,546 @@
# Changelog
## Roadmap
BREAKING CHANGES:
- Upgrade the header to support better proofs on validtors, results, evidence, and possibly more
- Better support for injecting randomness
- Pass evidence/voteInfo through ABCI
- Upgrade consensus for more real-time use of evidence
FEATURES:
- Peer reputation management
- Use the chain as its own CA for nodes and validators
- Tooling to run multiple blockchains/apps, possibly in a single process
- State syncing (without transaction replay)
- Add authentication and rate-limitting to the RPC
IMPROVEMENTS:
- Improve subtleties around mempool caching and logic
- Consensus optimizations:
- cache block parts for faster agreement after round changes
- propagate block parts rarest first
- Better testing of the consensus state machine (ie. use a DSL)
- Auto compiled serialization/deserialization code instead of go-wire reflection
BUG FIXES:
- Graceful handling/recovery for apps that have non-determinism or fail to halt
- Graceful handling/recovery for violations of safety, or liveness
## 0.14.0 (December 11, 2017)
BREAKING CHANGES:
- consensus/wal: removed separator
- rpc/client: changed Subscribe/Unsubscribe/UnsubscribeAll funcs signatures to be identical to event bus.
FEATURES:
- new `tendermint lite` command (and `lite/proxy` pkg) for running a light-client RPC proxy.
NOTE it is currently insecure and its APIs are not yet covered by semver
IMPROVEMENTS:
- rpc/client: can act as event bus subscriber (See https://github.com/tendermint/tendermint/issues/945).
- p2p: use exponential backoff from seconds to hours when attempting to reconnect to persistent peer
- config: moniker defaults to the machine's hostname instead of "anonymous"
BUG FIXES:
- p2p: no longer exit if one of the seed addresses is incorrect
## 0.13.0 (December 6, 2017)
BREAKING CHANGES:
- abci: update to v0.8 using gogo/protobuf; includes tx tags, vote info in RequestBeginBlock, data.Bytes everywhere, use int64, etc.
- types: block heights are now `int64` everywhere
- types & node: EventSwitch and EventCache have been replaced by EventBus and EventBuffer; event types have been overhauled
- node: EventSwitch methods now refer to EventBus
- rpc/lib/types: RPCResponse is no longer a pointer; WSRPCConnection interface has been modified
- rpc/client: WaitForOneEvent takes an EventsClient instead of types.EventSwitch
- rpc/client: Add/RemoveListenerForEvent are now Subscribe/Unsubscribe
- rpc/core/types: ResultABCIQuery wraps an abci.ResponseQuery
- rpc: `/subscribe` and `/unsubscribe` take `query` arg instead of `event`
- rpc: `/status` returns the LatestBlockTime in human readable form instead of in nanoseconds
- mempool: cached transactions return an error instead of an ABCI response with BadNonce
FEATURES:
- rpc: new `/unsubscribe_all` WebSocket RPC endpoint
- rpc: new `/tx_search` endpoint for filtering transactions by more complex queries
- p2p/trust: new trust metric for tracking peers. See ADR-006
- config: TxIndexConfig allows to set what DeliverTx tags to index
IMPROVEMENTS:
- New asynchronous events system using `tmlibs/pubsub`
- logging: Various small improvements
- consensus: Graceful shutdown when app crashes
- tests: Fix various non-deterministic errors
- p2p: more defensive programming
BUG FIXES:
- consensus: fix panic where prs.ProposalBlockParts is not initialized
- p2p: fix panic on bad channel
## 0.12.1 (November 27, 2017)
BUG FIXES:
- upgrade tmlibs dependency to enable Windows builds for Tendermint
## 0.12.0 (October 27, 2017)
BREAKING CHANGES:
- rpc/client: websocket ResultsCh and ErrorsCh unified in ResponsesCh.
- rpc/client: ABCIQuery no longer takes `prove`
- state: remove GenesisDoc from state.
- consensus: new binary WAL format provides efficiency and uses checksums to detect corruption
- use scripts/wal2json to convert to json for debugging
FEATURES:
- new `certifiers` pkg contains the tendermint light-client library (name subject to change)!
- rpc: `/genesis` includes the `app_options` .
- rpc: `/abci_query` takes an additional `height` parameter to support historical queries.
- rpc/client: new ABCIQueryWithOptions supports options like `trusted` (set false to get a proof) and `height` to query a historical height.
IMPROVEMENTS:
- rpc: `/genesis` result includes `app_options`
- rpc/lib/client: add jitter to reconnects.
- rpc/lib/types: `RPCError` satisfies the `error` interface.
BUG FIXES:
- rpc/client: fix ws deadlock after stopping
- blockchain: fix panic on AddBlock when peer is nil
- mempool: fix sending on TxsAvailable when a tx has been invalidated
- consensus: dont run WAL catchup if we fast synced
## 0.11.1 (October 10, 2017)
IMPROVEMENTS:
- blockchain/reactor: respondWithNoResponseMessage for missing height
BUG FIXES:
- rpc: fixed client WebSocket timeout
- rpc: client now resubscribes on reconnection
- rpc: fix panics on missing params
- rpc: fix `/dump_consensus_state` to have normal json output (NOTE: technically breaking, but worth a bug fix label)
- types: fixed out of range error in VoteSet.addVote
- consensus: fix wal autofile via https://github.com/tendermint/tmlibs/blob/master/CHANGELOG.md#032-october-2-2017
## 0.11.0 (September 22, 2017)
BREAKING:
- genesis file: validator `amount` is now `power`
- abci: Info, BeginBlock, InitChain all take structs
- rpc: various changes to match JSONRPC spec (http://www.jsonrpc.org/specification), including breaking ones:
- requests that previously returned HTTP code 4XX now return 200 with an error code in the JSONRPC.
- `rpctypes.RPCResponse` uses new `RPCError` type instead of `string`.
- cmd: if there is no genesis, exit immediately instead of waiting around for one to show.
- types: `Signer.Sign` returns an error.
- state: every validator set change is persisted to disk, which required some changes to the `State` structure.
- p2p: new `p2p.Peer` interface used for all reactor methods (instead of `*p2p.Peer` struct).
FEATURES:
- rpc: `/validators?height=X` allows querying of validators at previous heights.
- rpc: Leaving the `height` param empty for `/block`, `/validators`, and `/commit` will return the value for the latest height.
IMPROVEMENTS:
- docs: Moved all docs from the website and tools repo in, converted to `.rst`, and cleaned up for presentation on `tendermint.readthedocs.io`
BUG FIXES:
- fix WAL openning issue on Windows
## 0.10.4 (September 5, 2017)
IMPROVEMENTS:
- docs: Added Slate docs to each rpc function (see rpc/core)
- docs: Ported all website docs to Read The Docs
- config: expose some p2p params to tweak performance: RecvRate, SendRate, and MaxMsgPacketPayloadSize
- rpc: Upgrade the websocket client and server, including improved auto reconnect, and proper ping/pong
BUG FIXES:
- consensus: fix panic on getVoteBitArray
- consensus: hang instead of panicking on byzantine consensus failures
- cmd: dont load config for version command
## 0.10.3 (August 10, 2017)
FEATURES:
- control over empty block production:
- new flag, `--consensus.create_empty_blocks`; when set to false, blocks are only created when there are txs or when the AppHash changes.
- new config option, `consensus.create_empty_blocks_interval`; an empty block is created after this many seconds.
- in normal operation, `create_empty_blocks = true` and `create_empty_blocks_interval = 0`, so blocks are being created all the time (as in all previous versions of tendermint). The number of empty blocks can be reduced by increasing `create_empty_blocks_interval` or by setting `create_empty_blocks = false`.
- new `TxsAvailable()` method added to Mempool that returns a channel which fires when txs are available.
- new heartbeat message added to consensus reactor to notify peers that a node is waiting for txs before entering propose step.
- rpc: Add `syncing` field to response returned by `/status`. Is `true` while in fast-sync mode.
IMPROVEMENTS:
- various improvements to documentation and code comments
BUG FIXES:
- mempool: pass height into constructor so it doesn't always start at 0
## 0.10.2 (July 10, 2017)
FEATURES:
- Enable lower latency block commits by adding consensus reactor sleep durations and p2p flush throttle timeout to the config
IMPROVEMENTS:
- More detailed logging in the consensus reactor and state machine
- More in-code documentation for many exposed functions, especially in consensus/reactor.go and p2p/switch.go
- Improved readability for some function definitions and code blocks with long lines
## 0.10.1 (June 28, 2017)
FEATURES:
- Use `--trace` to get stack traces for logged errors
- types: GenesisDoc.ValidatorHash returns the hash of the genesis validator set
- types: GenesisDocFromFile parses a GenesiDoc from a JSON file
IMPROVEMENTS:
- Add a Code of Conduct
- Variety of improvements as suggested by `megacheck` tool
- rpc: deduplicate tests between rpc/client and rpc/tests
- rpc: addresses without a protocol prefix default to `tcp://`. `http://` is also accepted as an alias for `tcp://`
- cmd: commands are more easily reuseable from other tools
- DOCKER: automate build/push
BUG FIXES:
- Fix log statements using keys with spaces (logger does not currently support spaces)
- rpc: set logger on websocket connection
- rpc: fix ws connection stability by setting write deadline on pings
## 0.10.0 (June 2, 2017)
Includes major updates to configuration, logging, and json serialization.
Also includes the Grand Repo-Merge of 2017.
BREAKING CHANGES:
- Config and Flags:
- The `config` map is replaced with a [`Config` struct](https://github.com/tendermint/tendermint/blob/master/config/config.go#L11),
containing substructs: `BaseConfig`, `P2PConfig`, `MempoolConfig`, `ConsensusConfig`, `RPCConfig`
- This affects the following flags:
- `--seeds` is now `--p2p.seeds`
- `--node_laddr` is now `--p2p.laddr`
- `--pex` is now `--p2p.pex`
- `--skip_upnp` is now `--p2p.skip_upnp`
- `--rpc_laddr` is now `--rpc.laddr`
- `--grpc_laddr` is now `--rpc.grpc_laddr`
- Any configuration option now within a substract must come under that heading in the `config.toml`, for instance:
```
[p2p]
laddr="tcp://1.2.3.4:46656"
[consensus]
timeout_propose=1000
```
- Use viper and `DefaultConfig() / TestConfig()` functions to handle defaults, and remove `config/tendermint` and `config/tendermint_test`
- Change some function and method signatures to
- Change some [function and method signatures](https://gist.github.com/ebuchman/640d5fc6c2605f73497992fe107ebe0b) accomodate new config
- Logger
- Replace static `log15` logger with a simple interface, and provide a new implementation using `go-kit`.
See our new [logging library](https://github.com/tendermint/tmlibs/log) and [blog post](https://tendermint.com/blog/abstracting-the-logger-interface-in-go) for more details
- Levels `warn` and `notice` are removed (you may need to change them in your `config.toml`!)
- Change some [function and method signatures](https://gist.github.com/ebuchman/640d5fc6c2605f73497992fe107ebe0b) to accept a logger
- JSON serialization:
- Replace `[TypeByte, Xxx]` with `{"type": "some-type", "data": Xxx}` in RPC and all `.json` files by using `go-wire/data`. For instance, a public key is now:
```
"pub_key": {
"type": "ed25519",
"data": "83DDF8775937A4A12A2704269E2729FCFCD491B933C4B0A7FFE37FE41D7760D0"
}
```
- Remove type information about RPC responses, so `[TypeByte, {"jsonrpc": "2.0", ... }]` is now just `{"jsonrpc": "2.0", ... }`
- Change `[]byte` to `data.Bytes` in all serialized types (for hex encoding)
- Lowercase the JSON tags in `ValidatorSet` fields
- Introduce `EventDataInner` for serializing events
- Other:
- Send InitChain message in handshake if `appBlockHeight == 0`
- Do not include the `Accum` field when computing the validator hash. This makes the ValidatorSetHash unique for a given validator set, rather than changing with every block (as the Accum changes)
- Unsafe RPC calls are not enabled by default. This includes `/dial_seeds`, and all calls prefixed with `unsafe`. Use the `--rpc.unsafe` flag to enable.
FEATURES:
- Per-module log levels. For instance, the new default is `state:info,*:error`, which means the `state` package logs at `info` level, and everything else logs at `error` level
- Log if a node is validator or not in every consensus round
- Use ldflags to set git hash as part of the version
- Ignore `address` and `pub_key` fields in `priv_validator.json` and overwrite them with the values derrived from the `priv_key`
IMPROVEMENTS:
- Merge `tendermint/go-p2p -> tendermint/tendermint/p2p` and `tendermint/go-rpc -> tendermint/tendermint/rpc/lib`
- Update paths for grand repo merge:
- `go-common -> tmlibs/common`
- `go-data -> go-wire/data`
- All other `go-` libs, except `go-crypto` and `go-wire`, are merged under `tmlibs`
- No global loggers (loggers are passed into constructors, or preferably set with a SetLogger method)
- Return HTTP status codes with errors for RPC responses
- Limit `/blockchain_info` call to return a maximum of 20 blocks
- Use `.Wrap()` and `.Unwrap()` instead of eg. `PubKeyS` for `go-crypto` types
- RPC JSON responses use pretty printing (via `json.MarshalIndent`)
- Color code different instances of the consensus for tests
- Isolate viper to `cmd/tendermint/commands` and do not read config from file for tests
## 0.9.2 (April 26, 2017)
BUG FIXES:
- Fix bug in `ResetPrivValidator` where we were using the global config and log (causing external consumers, eg. basecoin, to fail).
## 0.9.1 (April 21, 2017)
FEATURES:
- Transaction indexing - txs are indexed by their hash using a simple key-value store; easily extended to more advanced indexers
- New `/tx?hash=X` endpoint to query for transactions and their DeliverTx result by hash. Optionally returns a proof of the tx's inclusion in the block
- `tendermint testnet` command initializes files for a testnet
IMPROVEMENTS:
- CLI now uses Cobra framework
- TMROOT is now TMHOME (TMROOT will stop working in 0.10.0)
- `/broadcast_tx_XXX` also returns the Hash (can be used to query for the tx)
- `/broadcast_tx_commit` also returns the height the block was committed in
- ABCIResponses struct persisted to disk before calling Commit; makes handshake replay much cleaner
- WAL uses #ENDHEIGHT instead of #HEIGHT (#HEIGHT will stop working in 0.10.0)
- Peers included via `--seeds`, under `seeds` in the config, or in `/dial_seeds` are now persistent, and will be reconnected to if the connection breaks
BUG FIXES:
- Fix bug in fast-sync where we stop syncing after a peer is removed, even if they're re-added later
- Fix handshake replay to handle validator set changes and results of DeliverTx when we crash after app.Commit but before state.Save()
## 0.9.0 (March 6, 2017)
BREAKING CHANGES:
- Update ABCI to v0.4.0, where Query is now `Query(RequestQuery) ResponseQuery`, enabling precise proofs at particular heights:
```
message RequestQuery{
bytes data = 1;
string path = 2;
uint64 height = 3;
bool prove = 4;
}
message ResponseQuery{
CodeType code = 1;
int64 index = 2;
bytes key = 3;
bytes value = 4;
bytes proof = 5;
uint64 height = 6;
string log = 7;
}
```
- `BlockMeta` data type unifies its Hash and PartSetHash under a `BlockID`:
```
type BlockMeta struct {
BlockID BlockID `json:"block_id"` // the block hash and partsethash
Header *Header `json:"header"` // The block's Header
}
```
- `ValidatorSet.Proposer` is exposed as a field and persisted with the `State`. Use `GetProposer()` to initialize or update after validator-set changes.
- `tendermint gen_validator` command output is now pure JSON
FEATURES:
- New RPC endpoint `/commit?height=X` returns header and commit for block at height `X`
- Client API for each endpoint, including mocks for testing
IMPROVEMENTS:
- `Node` is now a `BaseService`
- Simplified starting Tendermint in-process from another application
- Better organized Makefile
- Scripts for auto-building binaries across platforms
- Docker image improved, slimmed down (using Alpine), and changed from tendermint/tmbase to tendermint/tendermint
- New repo files: `CONTRIBUTING.md`, Github `ISSUE_TEMPLATE`, `CHANGELOG.md`
- Improvements on CircleCI for managing build/test artifacts
- Handshake replay is doen through the consensus package, possibly using a mockApp
- Graceful shutdown of RPC listeners
- Tests for the PEX reactor and DialSeeds
BUG FIXES:
- Check peer.Send for failure before updating PeerState in consensus
- Fix panic in `/dial_seeds` with invalid addresses
- Fix proposer selection logic in ValidatorSet by taking the address into account in the `accumComparable`
- Fix inconcistencies with `ValidatorSet.Proposer` across restarts by persisting it in the `State`
## 0.8.0 (January 13, 2017)
BREAKING CHANGES:
- New data type `BlockID` to represent blocks:
```
type BlockID struct {
Hash []byte `json:"hash"`
PartsHeader PartSetHeader `json:"parts"`
}
```
- `Vote` data type now includes validator address and index:
```
type Vote struct {
ValidatorAddress []byte `json:"validator_address"`
ValidatorIndex int `json:"validator_index"`
Height int `json:"height"`
Round int `json:"round"`
Type byte `json:"type"`
BlockID BlockID `json:"block_id"` // zero if vote is nil.
Signature crypto.Signature `json:"signature"`
}
```
- Update TMSP to v0.3.0, where it is now called ABCI and AppendTx is DeliverTx
- Hex strings in the RPC are now "0x" prefixed
FEATURES:
- New message type on the ConsensusReactor, `Maj23Msg`, for peers to alert others they've seen a Maj23,
in order to track and handle conflicting votes intelligently to prevent Byzantine faults from causing halts:
```
type VoteSetMaj23Message struct {
Height int
Round int
Type byte
BlockID types.BlockID
}
```
- Configurable block part set size
- Validator set changes
- Optionally skip TimeoutCommit if we have all the votes
- Handshake between Tendermint and App on startup to sync latest state and ensure consistent recovery from crashes
- GRPC server for BroadcastTx endpoint
IMPROVEMENTS:
- Less verbose logging
- Better test coverage (37% -> 49%)
- Canonical SignBytes for signable types
- Write-Ahead Log for Mempool and Consensus via tmlibs/autofile
- Better in-process testing for the consensus reactor and byzantine faults
- Better crash/restart testing for individual nodes at preset failure points, and of networks at arbitrary points
- Better abstraction over timeout mechanics
BUG FIXES:
- Fix memory leak in mempool peer
- Fix panic on POLRound=-1
- Actually set the CommitTime
- Actually send BeginBlock message
- Fix a liveness issues caused by Byzantine proposals/votes. Uses the new `Maj23Msg`.
## 0.7.4 (December 14, 2016)
FEATURES:
- Enable the Peer Exchange reactor with the `--pex` flag for more resilient gossip network (feature still in development, beware dragons)
IMPROVEMENTS:
- Remove restrictions on RPC endpoint `/dial_seeds` to enable manual network configuration
## 0.7.3 (October 20, 2016)
IMPROVEMENTS:
- Type safe FireEvent
- More WAL/replay tests
- Cleanup some docs
BUG FIXES:
- Fix deadlock in mempool for synchronous apps
- Replay handles non-empty blocks
- Fix race condition in HeightVoteSet
## 0.7.2 (September 11, 2016)
BUG FIXES:
- Set mustConnect=false so tendermint will retry connecting to the app
## 0.7.1 (September 10, 2016)
FEATURES:
- New TMSP connection for Query/Info
- New RPC endpoints:
- `tmsp_query`
- `tmsp_info`
- Allow application to filter peers through Query (off by default)
IMPROVEMENTS:
- TMSP connection type enforced at compile time
- All listen/client urls use a "tcp://" or "unix://" prefix
BUG FIXES:
- Save LastSignature/LastSignBytes to `priv_validator.json` for recovery
- Fix event unsubscribe
- Fix fastsync/blockchain reactor
## 0.7.0 (August 7, 2016)
BREAKING CHANGES:
- Strict SemVer starting now!
- Update to ABCI v0.2.0
- Validation types now called Commit
- NewBlock event only returns the block header
FEATURES:
- TMSP and RPC support TCP and UNIX sockets
- Addition config options including block size and consensus parameters
- New WAL mode `cswal_light`; logs only the validator's own votes
- New RPC endpoints:
- for starting/stopping profilers, and for updating config
- `/broadcast_tx_commit`, returns when tx is included in a block, else an error
- `/unsafe_flush_mempool`, empties the mempool
IMPROVEMENTS:
- Various optimizations
- Remove bad or invalidated transactions from the mempool cache (allows later duplicates)
- More elaborate testing using CircleCI including benchmarking throughput on 4 digitalocean droplets
BUG FIXES:
- Various fixes to WAL and replay logic
- Various race conditions
## PreHistory
Strict versioning only began with the release of v0.7.0, in late summer 2016.
The project itself began in early summer 2014 and was workable decentralized cryptocurrency software by the end of that year.
Through the course of 2015, in collaboration with Eris Industries (now Monax Indsutries),
many additional features were integrated, including an implementation from scratch of the Ethereum Virtual Machine.
That implementation now forms the heart of [Burrow](https://github.com/hyperledger/burrow).
In the later half of 2015, the consensus algorithm was upgraded with a more asynchronous design and a more deterministic and robust implementation.
By late 2015, frustration with the difficulty of forking a large monolithic stack to create alternative cryptocurrency designs led to the
invention of the Application Blockchain Interface (ABCI), then called the Tendermint Socket Protocol (TMSP).
The Ethereum Virtual Machine and various other transaction features were removed, and Tendermint was whittled down to a core consensus engine
driving an application running in another process.
The ABCI interface and implementation were iterated on and improved over the course of 2016,
until versioned history kicked in with v0.7.0.

56
CODE_OF_CONDUCT.md Normal file
View File

@@ -0,0 +1,56 @@
# The Tendermint Code of Conduct
This code of conduct applies to all projects run by the Tendermint/COSMOS team and hence to tendermint.
----
# Conduct
## Contact: adrian@tendermint.com
* We are committed to providing a friendly, safe and welcoming environment for all, regardless of level of experience, gender, gender identity and expression, sexual orientation, disability, personal appearance, body size, race, ethnicity, age, religion, nationality, or other similar characteristic.
* On Slack, please avoid using overtly sexual nicknames or other nicknames that might detract from a friendly, safe and welcoming environment for all.
* Please be kind and courteous. Theres no need to be mean or rude.
* Respect that people have differences of opinion and that every design or implementation choice carries a trade-off and numerous costs. There is seldom a right answer.
* Please keep unstructured critique to a minimum. If you have solid ideas you want to experiment with, make a fork and see how it works.
* We will exclude you from interaction if you insult, demean or harass anyone. That is not welcome behaviour. We interpret the term “harassment” as including the definition in the [Citizen Code of Conduct](http://citizencodeofconduct.org/); if you have any lack of clarity about what might be included in that concept, please read their definition. In particular, we dont tolerate behavior that excludes people in socially marginalized groups.
* Private harassment is also unacceptable. No matter who you are, if you feel you have been or are being harassed or made uncomfortable by a community member, please contact one of the channel admins or the person mentioned above immediately. Whether youre a regular contributor or a newcomer, we care about making this community a safe place for you and weve got your back.
* Likewise any spamming, trolling, flaming, baiting or other attention-stealing behaviour is not welcome.
----
# Moderation
These are the policies for upholding our communitys standards of conduct. If you feel that a thread needs moderation, please contact the above mentioned person.
1. Remarks that violate the Tendermint/COSMOS standards of conduct, including hateful, hurtful, oppressive, or exclusionary remarks, are not allowed. (Cursing is allowed, but never targeting another user, and never in a hateful manner.)
2. Remarks that moderators find inappropriate, whether listed in the code of conduct or not, are also not allowed.
3. Moderators will first respond to such remarks with a warning.
4. If the warning is unheeded, the user will be “kicked,” i.e., kicked out of the communication channel to cool off.
5. If the user comes back and continues to make trouble, they will be banned, i.e., indefinitely excluded.
6. Moderators may choose at their discretion to un-ban the user if it was a first offense and they offer the offended party a genuine apology.
7. If a moderator bans someone and you think it was unjustified, please take it up with that moderator, or with a different moderator, in private. Complaints about bans in-channel are not allowed.
8. Moderators are held to a higher standard than other community members. If a moderator creates an inappropriate situation, they should expect less leeway than others.
In the Tendermint/COSMOS community we strive to go the extra step to look out for each other. Dont just aim to be technically unimpeachable, try to be your best self. In particular, avoid flirting with offensive or sensitive issues, particularly if theyre off-topic; this all too often leads to unnecessary fights, hurt feelings, and damaged trust; worse, it can drive people away from the community entirely.
And if someone takes issue with something you said or did, resist the urge to be defensive. Just stop doing what it was they complained about and apologize. Even if you feel you were misinterpreted or unfairly accused, chances are good there was something you couldve communicated better — remember that its your responsibility to make your fellow Cosmonauts comfortable. Everyone wants to get along and we are all here first and foremost because we want to talk about cool technology. You will find that people will be eager to assume good intent and forgive as long as you earn their trust.
The enforcement policies listed above apply to all official Tendermint/COSMOS venues.For other projects adopting the Tendermint/COSMOS Code of Conduct, please contact the maintainers of those projects for enforcement. If you wish to use this code of conduct for your own project, consider explicitly mentioning your moderation policy or making a copy with your own moderation policy so as to avoid confusion.
*Adapted from the [Node.js Policy on Trolling](http://blog.izs.me/post/30036893703/policy-on-trolling), the [Contributor Covenant v1.3.0](http://contributor-covenant.org/version/1/3/0/) and the [Rust Code of Conduct](https://www.rust-lang.org/en-US/conduct.html).

100
CONTRIBUTING.md Normal file
View File

@@ -0,0 +1,100 @@
# Contributing
Thank you for considering making contributions to Tendermint and related repositories! Start by taking a look at the [coding repo](https://github.com/tendermint/coding) for overall information on repository workflow and standards.
Please follow standard github best practices: fork the repo, branch from the tip of develop, make some commits, and submit a pull request to develop. See the [open issues](https://github.com/tendermint/tendermint/issues) for things we need help with!
Please make sure to use `gofmt` before every commit - the easiest way to do this is have your editor run it for you upon saving a file.
## Forking
Please note that Go requires code to live under absolute paths, which complicates forking.
While my fork lives at `https://github.com/ebuchman/tendermint`,
the code should never exist at `$GOPATH/src/github.com/ebuchman/tendermint`.
Instead, we use `git remote` to add the fork as a new remote for the original repo,
`$GOPATH/src/github.com/tendermint/tendermint `, and do all the work there.
For instance, to create a fork and work on a branch of it, I would:
* Create the fork on github, using the fork button.
* Go to the original repo checked out locally (ie. `$GOPATH/src/github.com/tendermint/tendermint`)
* `git remote rename origin upstream`
* `git remote add origin git@github.com:ebuchman/basecoin.git`
Now `origin` refers to my fork and `upstream` refers to the tendermint version.
So I can `git push -u origin master` to update my fork, and make pull requests to tendermint from there.
Of course, replace `ebuchman` with your git handle.
To pull in updates from the origin repo, run
* `git fetch upstream`
* `git rebase upstream/master` (or whatever branch you want)
Please don't make Pull Requests to `master`.
## Dependencies
We use [glide](https://github.com/masterminds/glide) to manage dependencies.
That said, the master branch of every Tendermint repository should just build with `go get`, which means they should be kept up-to-date with their dependencies so we can get away with telling people they can just `go get` our software.
Since some dependencies are not under our control, a third party may break our build, in which case we can fall back on `glide install`. Even for dependencies under our control, glide helps us keeps multiple repos in sync as they evolve. Anything with an executable, such as apps, tools, and the core, should use glide.
Run `bash scripts/glide/status.sh` to get a list of vendored dependencies that may not be up-to-date.
## Vagrant
If you are a [Vagrant](https://www.vagrantup.com/) user, all you have to do to get started hacking Tendermint is:
```
vagrant up
vagrant ssh
cd ~/go/src/github.com/tendermint/tendermint
make test
```
## Testing
All repos should be hooked up to circle.
If they have `.go` files in the root directory, they will be automatically tested by circle using `go test -v -race ./...`. If not, they will need a `circle.yml`. Ideally, every repo has a `Makefile` that defines `make test` and includes its continuous integration status using a badge in the `README.md`.
## Branching Model and Release
User-facing repos should adhere to the branching model: http://nvie.com/posts/a-successful-git-branching-model/.
That is, these repos should be well versioned, and any merge to master requires a version bump and tagged release.
Libraries need not follow the model strictly, but would be wise to,
especially `go-p2p` and `go-rpc`, as their versions are referenced in tendermint core.
### Development Procedure:
- the latest state of development is on `develop`
- `develop` must never fail `make test`
- no --force onto `develop` (except when reverting a broken commit, which should seldom happen)
- create a development branch either on github.com/tendermint/tendermint, or your fork (using `git add origin`)
- before submitting a pull request, begin `git rebase` on top of `develop`
### Pull Merge Procedure:
- ensure pull branch is rebased on develop
- run `make test` to ensure that all tests pass
- merge pull request
- the `unstable` branch may be used to aggregate pull merges before testing once
- push master may request that pull requests be rebased on top of `unstable`
### Release Procedure:
- start on `develop`
- run integration tests (see `test_integrations` in Makefile)
- prepare changelog/release issue
- bump versions
- push to release-vX.X.X to run the extended integration tests on the CI
- merge to master
- merge master back to develop
### Hotfix Procedure:
- start on `master`
- checkout a new branch named hotfix-vX.X.X
- make the required changes
- these changes should be small and an absolute necessity
- add a note to CHANGELOG.md
- bumb versions
- push to hotfix-vX.X.X to run the extended integration tests on the CI
- merge hotfix-vX.X.X to master
- merge hotfix-vX.X.X to develop
- delete the hotfix-vX.X.X branch

View File

@@ -1,41 +1,45 @@
# Pull base image.
FROM golang:1.4
FROM alpine:3.6
ENV user tendermint
ENV data_root /data/tendermint
# This is the release of tendermint to pull in.
ENV TM_VERSION 0.13.0
ENV TM_SHA256SUM 36d773d4c2890addc61cc87a72c1e9c21c89516921b0defb0edfebde719b4b85
# set user right away for determinism
RUN groupadd -r $user \
&& useradd -r -s /bin/false -g $user $user
# Tendermint will be looking for genesis file in /tendermint (unless you change
# `genesis_file` in config.toml). You can put your config.toml and private
# validator file into /tendermint.
#
# The /tendermint/data dir is used by tendermint to store state.
ENV DATA_ROOT /tendermint
ENV TMHOME $DATA_ROOT
# create directory for persistence and give our user ownership
RUN mkdir -p $data_root \
&& chown -R $user:$user $data_root
# Set user right away for determinism
RUN addgroup tmuser && \
adduser -S -G tmuser tmuser
# Set the env variables to non-interactive
ENV DEBIAN_FRONTEND noninteractive
ENV DEBIAN_PRIORITY critical
ENV DEBCONF_NOWARNINGS yes
ENV TERM linux
RUN echo 'debconf debconf/frontend select Noninteractive' | debconf-set-selections
# Create directory for persistence and give our user ownership
RUN mkdir -p $DATA_ROOT && \
chown -R tmuser:tmuser $DATA_ROOT
# grab deps (gmp)
RUN apt-get update && \
apt-get install -y --no-install-recommends \
libgmp3-dev && \
rm -rf /var/lib/apt/lists/*
# jq and curl used for extracting `pub_key` from private validator while
# deploying tendermint with Kubernetes. It is nice to have bash so the users
# could execute bash commands.
RUN apk add --no-cache bash curl jq
# set the repo and install tendermint
ENV repo /go/src/github.com/tendermint/tendermint
ADD . $repo
WORKDIR $repo
RUN make
RUN apk add --no-cache openssl && \
wget https://s3-us-west-2.amazonaws.com/tendermint/binaries/tendermint/v${TM_VERSION}/tendermint_${TM_VERSION}_linux_amd64.zip && \
echo "${TM_SHA256SUM} tendermint_${TM_VERSION}_linux_amd64.zip" | sha256sum -c && \
unzip -d /bin tendermint_${TM_VERSION}_linux_amd64.zip && \
apk del openssl && \
rm -f tendermint_${TM_VERSION}_linux_amd64.zip
# persist data, set user
VOLUME $data_root
USER tendermint
ENV TMROOT $data_root
# Expose the data directory as a volume since there's mutable state in there
VOLUME $DATA_ROOT
# run tendermint
CMD ["./DOCKER/run.sh"]
# p2p port
EXPOSE 46656
# rpc port
EXPOSE 46657
ENTRYPOINT ["tendermint"]
CMD ["node", "--moniker=`hostname`"]

35
DOCKER/Dockerfile.develop Normal file
View File

@@ -0,0 +1,35 @@
FROM alpine:3.6
ENV DATA_ROOT /tendermint
ENV TMHOME $DATA_ROOT
RUN addgroup tmuser && \
adduser -S -G tmuser tmuser
RUN mkdir -p $DATA_ROOT && \
chown -R tmuser:tmuser $DATA_ROOT
RUN apk add --no-cache bash curl jq
ENV GOPATH /go
ENV PATH "$PATH:/go/bin"
RUN mkdir -p /go/src/github.com/tendermint/tendermint && \
apk add --no-cache go build-base git && \
cd /go/src/github.com/tendermint/tendermint && \
git clone https://github.com/tendermint/tendermint . && \
git checkout develop && \
make get_vendor_deps && \
make install && \
glide cc && \
cd - && \
rm -rf /go/src/github.com/tendermint/tendermint && \
apk del go build-base git
VOLUME $DATA_ROOT
EXPOSE 46656
EXPOSE 46657
ENTRYPOINT ["tendermint"]
CMD ["node", "--moniker=`hostname`", "--proxy_app=dummy"]

13
DOCKER/Makefile Normal file
View File

@@ -0,0 +1,13 @@
build:
@sh -c "'$(CURDIR)/build.sh'"
push:
@sh -c "'$(CURDIR)/push.sh'"
build_develop:
docker build -t "tendermint/tendermint:develop" -f Dockerfile.develop .
push_develop:
docker push "tendermint/tendermint:develop"
.PHONY: build build_develop push push_develop

View File

@@ -1,33 +1,59 @@
# Supported tags and respective `Dockerfile` links
# Persistence
- `0.13.0`, `latest` [(Dockerfile)](https://github.com/tendermint/tendermint/blob/a28b3fff49dce2fb31f90abb2fc693834e0029c2/DOCKER/Dockerfile)
- `0.12.1` [(Dockerfile)](https://github.com/tendermint/tendermint/blob/457c688346b565e90735431619ca3ca597ef9007/DOCKER/Dockerfile)
- `0.12.0` [(Dockerfile)](https://github.com/tendermint/tendermint/blob/70d8afa6e952e24c573ece345560a5971bf2cc0e/DOCKER/Dockerfile)
- `0.11.0` [(Dockerfile)](https://github.com/tendermint/tendermint/blob/9177cc1f64ca88a4a0243c5d1773d10fba67e201/DOCKER/Dockerfile)
- `0.10.0` [(Dockerfile)](https://github.com/tendermint/tendermint/blob/e5342f4054ab784b2cd6150e14f01053d7c8deb2/DOCKER/Dockerfile)
- `0.9.1`, `0.9`, [(Dockerfile)](https://github.com/tendermint/tendermint/blob/809e0e8c5933604ba8b2d096803ada7c5ec4dfd3/DOCKER/Dockerfile)
- `0.9.0` [(Dockerfile)](https://github.com/tendermint/tendermint/blob/d474baeeea6c22b289e7402449572f7c89ee21da/DOCKER/Dockerfile)
- `0.8.0`, `0.8` [(Dockerfile)](https://github.com/tendermint/tendermint/blob/bf64dd21fdb193e54d8addaaaa2ecf7ac371de8c/DOCKER/Dockerfile)
- `develop` [(Dockerfile)](https://github.com/tendermint/tendermint/blob/master/DOCKER/Dockerfile.develop)
It's good practice to use a data-only container, alongside the main application.
The `docker.sh` script sets it all up for you, and provides the
same functionality as `-v host_dir:image_dir` but by copying the data rather than
mounting it.
`develop` tag points to the [develop](https://github.com/tendermint/tendermint/tree/develop) branch.
# To Play
# Quick reference
The commands should work from tendermint/tendermint or tendermint/tendermint/DOCKER,
save the removal of DOCKER from the path.
* **Where to get help:**
https://tendermint.com/community
Get quickly caught up with the testnet: `FAST_SYNC=true ./DOCKER/docker.sh`
* **Where to file issues:**
https://github.com/tendermint/tendermint/issues
Use a pre-existing `~/.tendermint`: `VC=~/.tendermint NO_BUILD=true ./DOCKER/docker.sh`
* **Supported Docker versions:**
[the latest release](https://github.com/moby/moby/releases) (down to 1.6 on a best-effort basis)
This is like doing `-v ~/.tendermint:/data/tendermint`, but better.
# Tendermint
Use `NO_BUILD` to avoid waiting if the image is already built.
Tendermint Core is Byzantine Fault Tolerant (BFT) middleware that takes a state transition machine, written in any programming language, and securely replicates it on many machines.
Rerunning `docker.sh` will require you to delete the old containers:
For more background, see the [introduction](https://tendermint.readthedocs.io/en/master/introduction.html).
`docker rm mint mintdata`
To get started developing applications, see the [application developers guide](https://tendermint.readthedocs.io/en/master/getting-started.html).
However, if you remove the `mintdata` container, you delete the data (the blockchain).
If you don't use the `VC` option, your key will be deleted too
# How to use this image
To avoid deleting and recreating the data container, use
## Start one instance of the Tendermint core with the `dummy` app
`VD=true NO_BUILD=true ./DOCKER/docker.sh`
A very simple example of a built-in app and Tendermint core in one container.
Of course, once running, you can just control the main container with `docker stop mint` and `docker start mint`
```
docker run -it --rm -v "/tmp:/tendermint" tendermint/tendermint init
docker run -it --rm -v "/tmp:/tendermint" tendermint/tendermint node --proxy_app=dummy
```
## mintnet-kubernetes
If you want to see many containers talking to each other, consider using [mintnet-kubernetes](https://github.com/tendermint/tools/tree/master/mintnet-kubernetes), which is a tool for running Tendermint-based applications on a Kubernetes cluster.
# License
View [license information](https://raw.githubusercontent.com/tendermint/tendermint/master/LICENSE) for the software contained in this image.
# User Feedback
## Contributing
You are invited to contribute new features, fixes, or updates, large or small; we are always thrilled to receive pull requests, and do our best to process them as fast as we can.
Before you start to code, we recommend discussing your plans through a [GitHub](https://github.com/tendermint/tendermint/issues) issue, especially for more ambitious contributions. This gives other contributors a chance to point you in the right direction, give you feedback on your design, and help you find out if someone else is working on the same thing.

20
DOCKER/build.sh Executable file
View File

@@ -0,0 +1,20 @@
#!/usr/bin/env bash
set -e
# Get the tag from the version, or try to figure it out.
if [ -z "$TAG" ]; then
TAG=$(awk -F\" '/Version =/ { print $2; exit }' < ../version/version.go)
fi
if [ -z "$TAG" ]; then
echo "Please specify a tag."
exit 1
fi
TAG_NO_PATCH=${TAG%.*}
read -p "==> Build 3 docker images with the following tags (latest, $TAG, $TAG_NO_PATCH)? y/n" -n 1 -r
echo
if [[ $REPLY =~ ^[Yy]$ ]]
then
docker build -t "tendermint/tendermint" -t "tendermint/tendermint:$TAG" -t "tendermint/tendermint:$TAG_NO_PATCH" .
fi

View File

@@ -1,21 +0,0 @@
#! /bin/bash
# don't build if you're impatient
if [[ ! $NO_BUILD ]]; then
cd $GOPATH/src/github.com/tendermint/tendermint
docker build -t mint -f DOCKER/Dockerfile .
fi
# create the data-only container
if [[ ! $VD ]]; then
docker run --name mintdata --entrypoint /bin/echo mint Data-only container for mint
fi
# copy a directory from host to data-only volume
if [[ $VC ]]; then
cd $VC
tar cf - . | docker run -i --rm --volumes-from mintdata mint tar xvf - -C /data/tendermint
fi
# run tendermint
docker run --name mint --volumes-from mintdata -d -p 46656:46656 -p 46657:46657 -e FAST_SYNC=$FAST_SYNC mint

22
DOCKER/push.sh Executable file
View File

@@ -0,0 +1,22 @@
#!/usr/bin/env bash
set -e
# Get the tag from the version, or try to figure it out.
if [ -z "$TAG" ]; then
TAG=$(awk -F\" '/Version =/ { print $2; exit }' < ../version/version.go)
fi
if [ -z "$TAG" ]; then
echo "Please specify a tag."
exit 1
fi
TAG_NO_PATCH=${TAG%.*}
read -p "==> Push 3 docker images with the following tags (latest, $TAG, $TAG_NO_PATCH)? y/n" -n 1 -r
echo
if [[ $REPLY =~ ^[Yy]$ ]]
then
docker push "tendermint/tendermint:latest"
docker push "tendermint/tendermint:$TAG"
docker push "tendermint/tendermint:$TAG_NO_PATCH"
fi

View File

@@ -1,12 +0,0 @@
#! /bin/bash
if [[ $BARAK_SEED ]]; then
cat ./cmd/barak/$BARAK_SEED | ./build/barak &
fi
if [ "$FAST_SYNC" = "true" ]; then
tendermint node --fast_sync
else
tendermint node
fi

108
Godeps/Godeps.json generated
View File

@@ -1,108 +0,0 @@
{
"ImportPath": "github.com/tendermint/tendermint",
"GoVersion": "go1.4.2",
"Packages": [
"./..."
],
"Deps": [
{
"ImportPath": "code.google.com/p/go.crypto/ripemd160",
"Comment": "null-236",
"Rev": "69e2a90ed92d03812364aeb947b7068dc42e561e"
},
{
"ImportPath": "code.google.com/p/mxk/go1/flowcontrol",
"Comment": "null-12",
"Rev": "5ff2502e25566863e8a0136c7aae8838e4c7de39"
},
{
"ImportPath": "github.com/agl/ed25519/edwards25519",
"Rev": "d2b94fd789ea21d12fac1a4443dd3a3f79cda72c"
},
{
"ImportPath": "github.com/codegangsta/cli",
"Comment": "1.2.0-106-ga889873",
"Rev": "a889873af50a499d060097216dcdbcc26ed09e7c"
},
{
"ImportPath": "github.com/gorilla/websocket",
"Rev": "1f87405cd9755fc388e111c4003caca4a2f52fa6"
},
{
"ImportPath": "github.com/inconshreveable/log15/stack",
"Comment": "v2.3-38-g352fceb",
"Rev": "352fceb48e895bd1dd0b9f5d3ae8f8516c49af0f"
},
{
"ImportPath": "github.com/inconshreveable/log15/term",
"Comment": "v2.3-38-g352fceb",
"Rev": "352fceb48e895bd1dd0b9f5d3ae8f8516c49af0f"
},
{
"ImportPath": "github.com/mattn/go-colorable",
"Rev": "043ae16291351db8465272edf465c9f388161627"
},
{
"ImportPath": "github.com/naoina/go-stringutil",
"Rev": "360db0db4b01d34e12a2ec042c09e7d37fece761"
},
{
"ImportPath": "github.com/naoina/toml",
"Rev": "7b2dffbeaee47506726f29e36d19cf4ee90d361b"
},
{
"ImportPath": "github.com/sfreiberg/gotwilio",
"Rev": "b7230c284bd0c1614c94d00b9998c49f9a2737d8"
},
{
"ImportPath": "github.com/spf13/pflag",
"Rev": "5644820622454e71517561946e3d94b9f9db6842"
},
{
"ImportPath": "github.com/syndtr/goleveldb/leveldb",
"Rev": "63c9e642efad852f49e20a6f90194cae112fd2ac"
},
{
"ImportPath": "github.com/syndtr/gosnappy/snappy",
"Rev": "ce8acff4829e0c2458a67ead32390ac0a381c862"
},
{
"ImportPath": "github.com/tendermint/ed25519",
"Rev": "533fb6548e2071076888eda3c38749d707ba49bc"
},
{
"ImportPath": "github.com/tendermint/log15",
"Comment": "v2.3-34-gbec7415",
"Rev": "bec7415fb62f05ac62298c2bc1a080d45ac3065c"
},
{
"ImportPath": "golang.org/x/crypto/curve25519",
"Rev": "02a186af8b62cb007f392270669b91be5527d39c"
},
{
"ImportPath": "golang.org/x/crypto/nacl/box",
"Rev": "02a186af8b62cb007f392270669b91be5527d39c"
},
{
"ImportPath": "golang.org/x/crypto/nacl/secretbox",
"Rev": "02a186af8b62cb007f392270669b91be5527d39c"
},
{
"ImportPath": "golang.org/x/crypto/poly1305",
"Rev": "02a186af8b62cb007f392270669b91be5527d39c"
},
{
"ImportPath": "golang.org/x/crypto/ripemd160",
"Rev": "02a186af8b62cb007f392270669b91be5527d39c"
},
{
"ImportPath": "golang.org/x/crypto/salsa20/salsa",
"Rev": "02a186af8b62cb007f392270669b91be5527d39c"
},
{
"ImportPath": "gopkg.in/fatih/set.v0",
"Comment": "v0.1.0-3-g27c4092",
"Rev": "27c40922c40b43fe04554d8223a402af3ea333f3"
}
]
}

5
Godeps/Readme generated
View File

@@ -1,5 +0,0 @@
This directory tree is generated automatically by godep.
Please do not edit.
See https://github.com/tools/godep for more information.

2
Godeps/_workspace/.gitignore generated vendored
View File

@@ -1,2 +0,0 @@
/pkg
/bin

View File

@@ -1,120 +0,0 @@
// Copyright 2010 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// Package ripemd160 implements the RIPEMD-160 hash algorithm.
package ripemd160
// RIPEMD-160 is designed by by Hans Dobbertin, Antoon Bosselaers, and Bart
// Preneel with specifications available at:
// http://homes.esat.kuleuven.be/~cosicart/pdf/AB-9601/AB-9601.pdf.
import (
"crypto"
"hash"
)
func init() {
crypto.RegisterHash(crypto.RIPEMD160, New)
}
// The size of the checksum in bytes.
const Size = 20
// The block size of the hash algorithm in bytes.
const BlockSize = 64
const (
_s0 = 0x67452301
_s1 = 0xefcdab89
_s2 = 0x98badcfe
_s3 = 0x10325476
_s4 = 0xc3d2e1f0
)
// digest represents the partial evaluation of a checksum.
type digest struct {
s [5]uint32 // running context
x [BlockSize]byte // temporary buffer
nx int // index into x
tc uint64 // total count of bytes processed
}
func (d *digest) Reset() {
d.s[0], d.s[1], d.s[2], d.s[3], d.s[4] = _s0, _s1, _s2, _s3, _s4
d.nx = 0
d.tc = 0
}
// New returns a new hash.Hash computing the checksum.
func New() hash.Hash {
result := new(digest)
result.Reset()
return result
}
func (d *digest) Size() int { return Size }
func (d *digest) BlockSize() int { return BlockSize }
func (d *digest) Write(p []byte) (nn int, err error) {
nn = len(p)
d.tc += uint64(nn)
if d.nx > 0 {
n := len(p)
if n > BlockSize-d.nx {
n = BlockSize - d.nx
}
for i := 0; i < n; i++ {
d.x[d.nx+i] = p[i]
}
d.nx += n
if d.nx == BlockSize {
_Block(d, d.x[0:])
d.nx = 0
}
p = p[n:]
}
n := _Block(d, p)
p = p[n:]
if len(p) > 0 {
d.nx = copy(d.x[:], p)
}
return
}
func (d0 *digest) Sum(in []byte) []byte {
// Make a copy of d0 so that caller can keep writing and summing.
d := *d0
// Padding. Add a 1 bit and 0 bits until 56 bytes mod 64.
tc := d.tc
var tmp [64]byte
tmp[0] = 0x80
if tc%64 < 56 {
d.Write(tmp[0 : 56-tc%64])
} else {
d.Write(tmp[0 : 64+56-tc%64])
}
// Length in bits.
tc <<= 3
for i := uint(0); i < 8; i++ {
tmp[i] = byte(tc >> (8 * i))
}
d.Write(tmp[0:8])
if d.nx != 0 {
panic("d.nx != 0")
}
var digest [Size]byte
for i, s := range d.s {
digest[i*4] = byte(s)
digest[i*4+1] = byte(s >> 8)
digest[i*4+2] = byte(s >> 16)
digest[i*4+3] = byte(s >> 24)
}
return append(in, digest[:]...)
}

View File

@@ -1,64 +0,0 @@
// Copyright 2010 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package ripemd160
// Test vectors are from:
// http://homes.esat.kuleuven.be/~bosselae/ripemd160.html
import (
"fmt"
"io"
"testing"
)
type mdTest struct {
out string
in string
}
var vectors = [...]mdTest{
{"9c1185a5c5e9fc54612808977ee8f548b2258d31", ""},
{"0bdc9d2d256b3ee9daae347be6f4dc835a467ffe", "a"},
{"8eb208f7e05d987a9b044a8e98c6b087f15a0bfc", "abc"},
{"5d0689ef49d2fae572b881b123a85ffa21595f36", "message digest"},
{"f71c27109c692c1b56bbdceb5b9d2865b3708dbc", "abcdefghijklmnopqrstuvwxyz"},
{"12a053384a9c0c88e405a06c27dcf49ada62eb2b", "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq"},
{"b0e20b6e3116640286ed3a87a5713079b21f5189", "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789"},
{"9b752e45573d4b39f4dbd3323cab82bf63326bfb", "12345678901234567890123456789012345678901234567890123456789012345678901234567890"},
}
func TestVectors(t *testing.T) {
for i := 0; i < len(vectors); i++ {
tv := vectors[i]
md := New()
for j := 0; j < 3; j++ {
if j < 2 {
io.WriteString(md, tv.in)
} else {
io.WriteString(md, tv.in[0:len(tv.in)/2])
md.Sum(nil)
io.WriteString(md, tv.in[len(tv.in)/2:])
}
s := fmt.Sprintf("%x", md.Sum(nil))
if s != tv.out {
t.Fatalf("RIPEMD-160[%d](%s) = %s, expected %s", j, tv.in, s, tv.out)
}
md.Reset()
}
}
}
func TestMillionA(t *testing.T) {
md := New()
for i := 0; i < 100000; i++ {
io.WriteString(md, "aaaaaaaaaa")
}
out := "52783243c1697bdbe16d37f97f68f08325dc1528"
s := fmt.Sprintf("%x", md.Sum(nil))
if s != out {
t.Fatalf("RIPEMD-160 (1 million 'a') = %s, expected %s", s, out)
}
md.Reset()
}

View File

@@ -1,161 +0,0 @@
// Copyright 2010 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// RIPEMD-160 block step.
// In its own file so that a faster assembly or C version
// can be substituted easily.
package ripemd160
// work buffer indices and roll amounts for one line
var _n = [80]uint{
0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15,
7, 4, 13, 1, 10, 6, 15, 3, 12, 0, 9, 5, 2, 14, 11, 8,
3, 10, 14, 4, 9, 15, 8, 1, 2, 7, 0, 6, 13, 11, 5, 12,
1, 9, 11, 10, 0, 8, 12, 4, 13, 3, 7, 15, 14, 5, 6, 2,
4, 0, 5, 9, 7, 12, 2, 10, 14, 1, 3, 8, 11, 6, 15, 13,
}
var _r = [80]uint{
11, 14, 15, 12, 5, 8, 7, 9, 11, 13, 14, 15, 6, 7, 9, 8,
7, 6, 8, 13, 11, 9, 7, 15, 7, 12, 15, 9, 11, 7, 13, 12,
11, 13, 6, 7, 14, 9, 13, 15, 14, 8, 13, 6, 5, 12, 7, 5,
11, 12, 14, 15, 14, 15, 9, 8, 9, 14, 5, 6, 8, 6, 5, 12,
9, 15, 5, 11, 6, 8, 13, 12, 5, 12, 13, 14, 11, 8, 5, 6,
}
// same for the other parallel one
var n_ = [80]uint{
5, 14, 7, 0, 9, 2, 11, 4, 13, 6, 15, 8, 1, 10, 3, 12,
6, 11, 3, 7, 0, 13, 5, 10, 14, 15, 8, 12, 4, 9, 1, 2,
15, 5, 1, 3, 7, 14, 6, 9, 11, 8, 12, 2, 10, 0, 4, 13,
8, 6, 4, 1, 3, 11, 15, 0, 5, 12, 2, 13, 9, 7, 10, 14,
12, 15, 10, 4, 1, 5, 8, 7, 6, 2, 13, 14, 0, 3, 9, 11,
}
var r_ = [80]uint{
8, 9, 9, 11, 13, 15, 15, 5, 7, 7, 8, 11, 14, 14, 12, 6,
9, 13, 15, 7, 12, 8, 9, 11, 7, 7, 12, 7, 6, 15, 13, 11,
9, 7, 15, 11, 8, 6, 6, 14, 12, 13, 5, 14, 13, 13, 7, 5,
15, 5, 8, 11, 14, 14, 6, 14, 6, 9, 12, 9, 12, 5, 15, 8,
8, 5, 12, 9, 12, 5, 14, 6, 8, 13, 6, 5, 15, 13, 11, 11,
}
func _Block(md *digest, p []byte) int {
n := 0
var x [16]uint32
var alpha, beta uint32
for len(p) >= BlockSize {
a, b, c, d, e := md.s[0], md.s[1], md.s[2], md.s[3], md.s[4]
aa, bb, cc, dd, ee := a, b, c, d, e
j := 0
for i := 0; i < 16; i++ {
x[i] = uint32(p[j]) | uint32(p[j+1])<<8 | uint32(p[j+2])<<16 | uint32(p[j+3])<<24
j += 4
}
// round 1
i := 0
for i < 16 {
alpha = a + (b ^ c ^ d) + x[_n[i]]
s := _r[i]
alpha = (alpha<<s | alpha>>(32-s)) + e
beta = c<<10 | c>>22
a, b, c, d, e = e, alpha, b, beta, d
// parallel line
alpha = aa + (bb ^ (cc | ^dd)) + x[n_[i]] + 0x50a28be6
s = r_[i]
alpha = (alpha<<s | alpha>>(32-s)) + ee
beta = cc<<10 | cc>>22
aa, bb, cc, dd, ee = ee, alpha, bb, beta, dd
i++
}
// round 2
for i < 32 {
alpha = a + (b&c | ^b&d) + x[_n[i]] + 0x5a827999
s := _r[i]
alpha = (alpha<<s | alpha>>(32-s)) + e
beta = c<<10 | c>>22
a, b, c, d, e = e, alpha, b, beta, d
// parallel line
alpha = aa + (bb&dd | cc&^dd) + x[n_[i]] + 0x5c4dd124
s = r_[i]
alpha = (alpha<<s | alpha>>(32-s)) + ee
beta = cc<<10 | cc>>22
aa, bb, cc, dd, ee = ee, alpha, bb, beta, dd
i++
}
// round 3
for i < 48 {
alpha = a + (b | ^c ^ d) + x[_n[i]] + 0x6ed9eba1
s := _r[i]
alpha = (alpha<<s | alpha>>(32-s)) + e
beta = c<<10 | c>>22
a, b, c, d, e = e, alpha, b, beta, d
// parallel line
alpha = aa + (bb | ^cc ^ dd) + x[n_[i]] + 0x6d703ef3
s = r_[i]
alpha = (alpha<<s | alpha>>(32-s)) + ee
beta = cc<<10 | cc>>22
aa, bb, cc, dd, ee = ee, alpha, bb, beta, dd
i++
}
// round 4
for i < 64 {
alpha = a + (b&d | c&^d) + x[_n[i]] + 0x8f1bbcdc
s := _r[i]
alpha = (alpha<<s | alpha>>(32-s)) + e
beta = c<<10 | c>>22
a, b, c, d, e = e, alpha, b, beta, d
// parallel line
alpha = aa + (bb&cc | ^bb&dd) + x[n_[i]] + 0x7a6d76e9
s = r_[i]
alpha = (alpha<<s | alpha>>(32-s)) + ee
beta = cc<<10 | cc>>22
aa, bb, cc, dd, ee = ee, alpha, bb, beta, dd
i++
}
// round 5
for i < 80 {
alpha = a + (b ^ (c | ^d)) + x[_n[i]] + 0xa953fd4e
s := _r[i]
alpha = (alpha<<s | alpha>>(32-s)) + e
beta = c<<10 | c>>22
a, b, c, d, e = e, alpha, b, beta, d
// parallel line
alpha = aa + (bb ^ cc ^ dd) + x[n_[i]]
s = r_[i]
alpha = (alpha<<s | alpha>>(32-s)) + ee
beta = cc<<10 | cc>>22
aa, bb, cc, dd, ee = ee, alpha, bb, beta, dd
i++
}
// combine results
dd += c + md.s[1]
md.s[1] = md.s[2] + d + ee
md.s[2] = md.s[3] + e + aa
md.s[3] = md.s[4] + a + bb
md.s[4] = md.s[0] + b + cc
md.s[0] = dd
p = p[BlockSize:]
n += BlockSize
}
return n
}

View File

@@ -1,267 +0,0 @@
//
// Written by Maxim Khitrov (November 2012)
//
// Package flowcontrol provides the tools for monitoring and limiting the
// transfer rate of an arbitrary data stream.
package flowcontrol
import (
"math"
"sync"
"time"
)
// Monitor monitors and limits the transfer rate of a data stream.
type Monitor struct {
mu sync.Mutex // Mutex guarding access to all internal fields
active bool // Flag indicating an active transfer
start time.Duration // Transfer start time (clock() value)
bytes int64 // Total number of bytes transferred
samples int64 // Total number of samples taken
rSample float64 // Most recent transfer rate sample (bytes per second)
rEMA float64 // Exponential moving average of rSample
rPeak float64 // Peak transfer rate (max of all rSamples)
rWindow float64 // rEMA window (seconds)
sBytes int64 // Number of bytes transferred since sLast
sLast time.Duration // Most recent sample time (stop time when inactive)
sRate time.Duration // Sampling rate
tBytes int64 // Number of bytes expected in the current transfer
tLast time.Duration // Time of the most recent transfer of at least 1 byte
}
// New creates a new flow control monitor. Instantaneous transfer rate is
// measured and updated for each sampleRate interval. windowSize determines the
// weight of each sample in the exponential moving average (EMA) calculation.
// The exact formulas are:
//
// sampleTime = currentTime - prevSampleTime
// sampleRate = byteCount / sampleTime
// weight = 1 - exp(-sampleTime/windowSize)
// newRate = weight*sampleRate + (1-weight)*oldRate
//
// The default values for sampleRate and windowSize (if <= 0) are 100ms and 1s,
// respectively.
func New(sampleRate, windowSize time.Duration) *Monitor {
if sampleRate = clockRound(sampleRate); sampleRate <= 0 {
sampleRate = 5 * clockRate
}
if windowSize <= 0 {
windowSize = 1 * time.Second
}
now := clock()
return &Monitor{
active: true,
start: now,
rWindow: windowSize.Seconds(),
sLast: now,
sRate: sampleRate,
tLast: now,
}
}
// Update records the transfer of n bytes and returns n. It should be called
// after each Read/Write operation, even if n is 0.
func (m *Monitor) Update(n int) int {
m.mu.Lock()
m.update(n)
m.mu.Unlock()
return n
}
// IO is a convenience method intended to wrap io.Reader and io.Writer method
// execution. It calls m.Update(n) and then returns (n, err) unmodified.
func (m *Monitor) IO(n int, err error) (int, error) {
return m.Update(n), err
}
// Done marks the transfer as finished and prevents any further updates or
// limiting. Instantaneous and current transfer rates drop to 0. Update, IO, and
// Limit methods become NOOPs. It returns the total number of bytes transferred.
func (m *Monitor) Done() int64 {
m.mu.Lock()
if now := m.update(0); m.sBytes > 0 {
m.reset(now)
}
m.active = false
m.tLast = 0
n := m.bytes
m.mu.Unlock()
return n
}
// timeRemLimit is the maximum Status.TimeRem value.
const timeRemLimit = 999*time.Hour + 59*time.Minute + 59*time.Second
// Status represents the current Monitor status. All transfer rates are in bytes
// per second rounded to the nearest byte.
type Status struct {
Active bool // Flag indicating an active transfer
Start time.Time // Transfer start time
Duration time.Duration // Time period covered by the statistics
Idle time.Duration // Time since the last transfer of at least 1 byte
Bytes int64 // Total number of bytes transferred
Samples int64 // Total number of samples taken
InstRate int64 // Instantaneous transfer rate
CurRate int64 // Current transfer rate (EMA of InstRate)
AvgRate int64 // Average transfer rate (Bytes / Duration)
PeakRate int64 // Maximum instantaneous transfer rate
BytesRem int64 // Number of bytes remaining in the transfer
TimeRem time.Duration // Estimated time to completion
Progress Percent // Overall transfer progress
}
// Status returns current transfer status information. The returned value
// becomes static after a call to Done.
func (m *Monitor) Status() Status {
m.mu.Lock()
now := m.update(0)
s := Status{
Active: m.active,
Start: clockToTime(m.start),
Duration: m.sLast - m.start,
Idle: now - m.tLast,
Bytes: m.bytes,
Samples: m.samples,
PeakRate: round(m.rPeak),
BytesRem: m.tBytes - m.bytes,
Progress: percentOf(float64(m.bytes), float64(m.tBytes)),
}
if s.BytesRem < 0 {
s.BytesRem = 0
}
if s.Duration > 0 {
rAvg := float64(s.Bytes) / s.Duration.Seconds()
s.AvgRate = round(rAvg)
if s.Active {
s.InstRate = round(m.rSample)
s.CurRate = round(m.rEMA)
if s.BytesRem > 0 {
if tRate := 0.8*m.rEMA + 0.2*rAvg; tRate > 0 {
ns := float64(s.BytesRem) / tRate * 1e9
if ns > float64(timeRemLimit) {
ns = float64(timeRemLimit)
}
s.TimeRem = clockRound(time.Duration(ns))
}
}
}
}
m.mu.Unlock()
return s
}
// Limit restricts the instantaneous (per-sample) data flow to rate bytes per
// second. It returns the maximum number of bytes (0 <= n <= want) that may be
// transferred immediately without exceeding the limit. If block == true, the
// call blocks until n > 0. want is returned unmodified if want < 1, rate < 1,
// or the transfer is inactive (after a call to Done).
//
// At least one byte is always allowed to be transferred in any given sampling
// period. Thus, if the sampling rate is 100ms, the lowest achievable flow rate
// is 10 bytes per second.
//
// For usage examples, see the implementation of Reader and Writer in io.go.
func (m *Monitor) Limit(want int, rate int64, block bool) (n int) {
if want < 1 || rate < 1 {
return want
}
m.mu.Lock()
// Determine the maximum number of bytes that can be sent in one sample
limit := round(float64(rate) * m.sRate.Seconds())
if limit <= 0 {
limit = 1
}
// If block == true, wait until m.sBytes < limit
if now := m.update(0); block {
for m.sBytes >= limit && m.active {
now = m.waitNextSample(now)
}
}
// Make limit <= want (unlimited if the transfer is no longer active)
if limit -= m.sBytes; limit > int64(want) || !m.active {
limit = int64(want)
}
m.mu.Unlock()
if limit < 0 {
limit = 0
}
return int(limit)
}
// SetTransferSize specifies the total size of the data transfer, which allows
// the Monitor to calculate the overall progress and time to completion.
func (m *Monitor) SetTransferSize(bytes int64) {
if bytes < 0 {
bytes = 0
}
m.mu.Lock()
m.tBytes = bytes
m.mu.Unlock()
}
// update accumulates the transferred byte count for the current sample until
// clock() - m.sLast >= m.sRate. The monitor status is updated once the current
// sample is done.
func (m *Monitor) update(n int) (now time.Duration) {
if !m.active {
return
}
if now = clock(); n > 0 {
m.tLast = now
}
m.sBytes += int64(n)
if sTime := now - m.sLast; sTime >= m.sRate {
t := sTime.Seconds()
if m.rSample = float64(m.sBytes) / t; m.rSample > m.rPeak {
m.rPeak = m.rSample
}
// Exponential moving average using a method similar to *nix load
// average calculation. Longer sampling periods carry greater weight.
if m.samples > 0 {
w := math.Exp(-t / m.rWindow)
m.rEMA = m.rSample + w*(m.rEMA-m.rSample)
} else {
m.rEMA = m.rSample
}
m.reset(now)
}
return
}
// reset clears the current sample state in preparation for the next sample.
func (m *Monitor) reset(sampleTime time.Duration) {
m.bytes += m.sBytes
m.samples++
m.sBytes = 0
m.sLast = sampleTime
}
// waitNextSample sleeps for the remainder of the current sample. The lock is
// released and reacquired during the actual sleep period, so it's possible for
// the transfer to be inactive when this method returns.
func (m *Monitor) waitNextSample(now time.Duration) time.Duration {
const minWait = 5 * time.Millisecond
current := m.sLast
// sleep until the last sample time changes (ideally, just one iteration)
for m.sLast == current && m.active {
d := current + m.sRate - now
m.mu.Unlock()
if d < minWait {
d = minWait
}
time.Sleep(d)
m.mu.Lock()
now = m.update(0)
}
return now
}

View File

@@ -1,133 +0,0 @@
//
// Written by Maxim Khitrov (November 2012)
//
package flowcontrol
import (
"errors"
"io"
)
// ErrLimit is returned by the Writer when a non-blocking write is short due to
// the transfer rate limit.
var ErrLimit = errors.New("flowcontrol: transfer rate limit exceeded")
// Limiter is implemented by the Reader and Writer to provide a consistent
// interface for monitoring and controlling data transfer.
type Limiter interface {
Done() int64
Status() Status
SetTransferSize(bytes int64)
SetLimit(new int64) (old int64)
SetBlocking(new bool) (old bool)
}
// Reader implements io.ReadCloser with a restriction on the rate of data
// transfer.
type Reader struct {
io.Reader // Data source
*Monitor // Flow control monitor
limit int64 // Rate limit in bytes per second (unlimited when <= 0)
block bool // What to do when no new bytes can be read due to the limit
}
// NewReader restricts all Read operations on r to limit bytes per second.
func NewReader(r io.Reader, limit int64) *Reader {
return &Reader{r, New(0, 0), limit, true}
}
// Read reads up to len(p) bytes into p without exceeding the current transfer
// rate limit. It returns (0, nil) immediately if r is non-blocking and no new
// bytes can be read at this time.
func (r *Reader) Read(p []byte) (n int, err error) {
p = p[:r.Limit(len(p), r.limit, r.block)]
if len(p) > 0 {
n, err = r.IO(r.Reader.Read(p))
}
return
}
// SetLimit changes the transfer rate limit to new bytes per second and returns
// the previous setting.
func (r *Reader) SetLimit(new int64) (old int64) {
old, r.limit = r.limit, new
return
}
// SetBlocking changes the blocking behavior and returns the previous setting. A
// Read call on a non-blocking reader returns immediately if no additional bytes
// may be read at this time due to the rate limit.
func (r *Reader) SetBlocking(new bool) (old bool) {
old, r.block = r.block, new
return
}
// Close closes the underlying reader if it implements the io.Closer interface.
func (r *Reader) Close() error {
defer r.Done()
if c, ok := r.Reader.(io.Closer); ok {
return c.Close()
}
return nil
}
// Writer implements io.WriteCloser with a restriction on the rate of data
// transfer.
type Writer struct {
io.Writer // Data destination
*Monitor // Flow control monitor
limit int64 // Rate limit in bytes per second (unlimited when <= 0)
block bool // What to do when no new bytes can be written due to the limit
}
// NewWriter restricts all Write operations on w to limit bytes per second. The
// transfer rate and the default blocking behavior (true) can be changed
// directly on the returned *Writer.
func NewWriter(w io.Writer, limit int64) *Writer {
return &Writer{w, New(0, 0), limit, true}
}
// Write writes len(p) bytes from p to the underlying data stream without
// exceeding the current transfer rate limit. It returns (n, ErrLimit) if w is
// non-blocking and no additional bytes can be written at this time.
func (w *Writer) Write(p []byte) (n int, err error) {
var c int
for len(p) > 0 && err == nil {
s := p[:w.Limit(len(p), w.limit, w.block)]
if len(s) > 0 {
c, err = w.IO(w.Writer.Write(s))
} else {
return n, ErrLimit
}
p = p[c:]
n += c
}
return
}
// SetLimit changes the transfer rate limit to new bytes per second and returns
// the previous setting.
func (w *Writer) SetLimit(new int64) (old int64) {
old, w.limit = w.limit, new
return
}
// SetBlocking changes the blocking behavior and returns the previous setting. A
// Write call on a non-blocking writer returns as soon as no additional bytes
// may be written at this time due to the rate limit.
func (w *Writer) SetBlocking(new bool) (old bool) {
old, w.block = w.block, new
return
}
// Close closes the underlying writer if it implements the io.Closer interface.
func (w *Writer) Close() error {
defer w.Done()
if c, ok := w.Writer.(io.Closer); ok {
return c.Close()
}
return nil
}

View File

@@ -1,146 +0,0 @@
//
// Written by Maxim Khitrov (November 2012)
//
package flowcontrol
import (
"bytes"
"reflect"
"testing"
"time"
)
const (
_50ms = 50 * time.Millisecond
_100ms = 100 * time.Millisecond
_200ms = 200 * time.Millisecond
_300ms = 300 * time.Millisecond
_400ms = 400 * time.Millisecond
_500ms = 500 * time.Millisecond
)
func nextStatus(m *Monitor) Status {
samples := m.samples
for i := 0; i < 30; i++ {
if s := m.Status(); s.Samples != samples {
return s
}
time.Sleep(5 * time.Millisecond)
}
return m.Status()
}
func TestReader(t *testing.T) {
in := make([]byte, 100)
for i := range in {
in[i] = byte(i)
}
b := make([]byte, 100)
r := NewReader(bytes.NewReader(in), 100)
start := time.Now()
// Make sure r implements Limiter
_ = Limiter(r)
// 1st read of 10 bytes is performed immediately
if n, err := r.Read(b); n != 10 || err != nil {
t.Fatalf("r.Read(b) expected 10 (<nil>); got %v (%v)", n, err)
} else if rt := time.Since(start); rt > _50ms {
t.Fatalf("r.Read(b) took too long (%v)", rt)
}
// No new Reads allowed in the current sample
r.SetBlocking(false)
if n, err := r.Read(b); n != 0 || err != nil {
t.Fatalf("r.Read(b) expected 0 (<nil>); got %v (%v)", n, err)
} else if rt := time.Since(start); rt > _50ms {
t.Fatalf("r.Read(b) took too long (%v)", rt)
}
status := [6]Status{0: r.Status()} // No samples in the first status
// 2nd read of 10 bytes blocks until the next sample
r.SetBlocking(true)
if n, err := r.Read(b[10:]); n != 10 || err != nil {
t.Fatalf("r.Read(b[10:]) expected 10 (<nil>); got %v (%v)", n, err)
} else if rt := time.Since(start); rt < _100ms {
t.Fatalf("r.Read(b[10:]) returned ahead of time (%v)", rt)
}
status[1] = r.Status() // 1st sample
status[2] = nextStatus(r.Monitor) // 2nd sample
status[3] = nextStatus(r.Monitor) // No activity for the 3rd sample
if n := r.Done(); n != 20 {
t.Fatalf("r.Done() expected 20; got %v", n)
}
status[4] = r.Status()
status[5] = nextStatus(r.Monitor) // Timeout
start = status[0].Start
// Active, Start, Duration, Idle, Bytes, Samples, InstRate, CurRate, AvgRate, PeakRate, BytesRem, TimeRem, Progress
want := []Status{
Status{true, start, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
Status{true, start, _100ms, 0, 10, 1, 100, 100, 100, 100, 0, 0, 0},
Status{true, start, _200ms, _100ms, 20, 2, 100, 100, 100, 100, 0, 0, 0},
Status{true, start, _300ms, _200ms, 20, 3, 0, 90, 67, 100, 0, 0, 0},
Status{false, start, _300ms, 0, 20, 3, 0, 0, 67, 100, 0, 0, 0},
Status{false, start, _300ms, 0, 20, 3, 0, 0, 67, 100, 0, 0, 0},
}
for i, s := range status {
if !reflect.DeepEqual(&s, &want[i]) {
t.Errorf("r.Status(%v) expected %v; got %v", i, want[i], s)
}
}
if !bytes.Equal(b[:20], in[:20]) {
t.Errorf("r.Read() input doesn't match output")
}
}
func TestWriter(t *testing.T) {
b := make([]byte, 100)
for i := range b {
b[i] = byte(i)
}
w := NewWriter(&bytes.Buffer{}, 200)
start := time.Now()
// Make sure w implements Limiter
_ = Limiter(w)
// Non-blocking 20-byte write for the first sample returns ErrLimit
w.SetBlocking(false)
if n, err := w.Write(b); n != 20 || err != ErrLimit {
t.Fatalf("w.Write(b) expected 20 (ErrLimit); got %v (%v)", n, err)
} else if rt := time.Since(start); rt > _50ms {
t.Fatalf("w.Write(b) took too long (%v)", rt)
}
// Blocking 80-byte write
w.SetBlocking(true)
if n, err := w.Write(b[20:]); n != 80 || err != nil {
t.Fatalf("w.Write(b[20:]) expected 80 (<nil>); got %v (%v)", n, err)
} else if rt := time.Since(start); rt < _400ms {
t.Fatalf("w.Write(b[20:]) returned ahead of time (%v)", rt)
}
w.SetTransferSize(100)
status := []Status{w.Status(), nextStatus(w.Monitor)}
start = status[0].Start
// Active, Start, Duration, Idle, Bytes, Samples, InstRate, CurRate, AvgRate, PeakRate, BytesRem, TimeRem, Progress
want := []Status{
Status{true, start, _400ms, 0, 80, 4, 200, 200, 200, 200, 20, _100ms, 80000},
Status{true, start, _500ms, _100ms, 100, 5, 200, 200, 200, 200, 0, 0, 100000},
}
for i, s := range status {
if !reflect.DeepEqual(&s, &want[i]) {
t.Errorf("w.Status(%v) expected %v; got %v", i, want[i], s)
}
}
if !bytes.Equal(b, w.Writer.(*bytes.Buffer).Bytes()) {
t.Errorf("w.Write() input doesn't match output")
}
}

View File

@@ -1,67 +0,0 @@
//
// Written by Maxim Khitrov (November 2012)
//
package flowcontrol
import (
"math"
"strconv"
"time"
)
// clockRate is the resolution and precision of clock().
const clockRate = 20 * time.Millisecond
// czero is the process start time rounded down to the nearest clockRate
// increment.
var czero = time.Duration(time.Now().UnixNano()) / clockRate * clockRate
// clock returns a low resolution timestamp relative to the process start time.
func clock() time.Duration {
return time.Duration(time.Now().UnixNano())/clockRate*clockRate - czero
}
// clockToTime converts a clock() timestamp to an absolute time.Time value.
func clockToTime(c time.Duration) time.Time {
return time.Unix(0, int64(czero+c))
}
// clockRound returns d rounded to the nearest clockRate increment.
func clockRound(d time.Duration) time.Duration {
return (d + clockRate>>1) / clockRate * clockRate
}
// round returns x rounded to the nearest int64 (non-negative values only).
func round(x float64) int64 {
if _, frac := math.Modf(x); frac >= 0.5 {
return int64(math.Ceil(x))
}
return int64(math.Floor(x))
}
// Percent represents a percentage in increments of 1/1000th of a percent.
type Percent uint32
// percentOf calculates what percent of the total is x.
func percentOf(x, total float64) Percent {
if x < 0 || total <= 0 {
return 0
} else if p := round(x / total * 1e5); p <= math.MaxUint32 {
return Percent(p)
}
return Percent(math.MaxUint32)
}
func (p Percent) Float() float64 {
return float64(p) * 1e-3
}
func (p Percent) String() string {
var buf [12]byte
b := strconv.AppendUint(buf[:0], uint64(p)/1000, 10)
n := len(b)
b = strconv.AppendUint(b, 1000+uint64(p)%1000, 10)
b[n] = '.'
return string(append(b, '%'))
}

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -1,6 +0,0 @@
language: go
go: 1.1
script:
- go vet ./...
- go test -v ./...

View File

@@ -1,21 +0,0 @@
Copyright (C) 2013 Jeremy Saenz
All Rights Reserved.
MIT LICENSE
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software is furnished to do so,
subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

View File

@@ -1,298 +0,0 @@
[![Build Status](https://travis-ci.org/codegangsta/cli.png?branch=master)](https://travis-ci.org/codegangsta/cli)
# cli.go
cli.go is simple, fast, and fun package for building command line apps in Go. The goal is to enable developers to write fast and distributable command line applications in an expressive way.
You can view the API docs here:
http://godoc.org/github.com/codegangsta/cli
## Overview
Command line apps are usually so tiny that there is absolutely no reason why your code should *not* be self-documenting. Things like generating help text and parsing command flags/options should not hinder productivity when writing a command line app.
**This is where cli.go comes into play.** cli.go makes command line programming fun, organized, and expressive!
## Installation
Make sure you have a working Go environment (go 1.1+ is *required*). [See the install instructions](http://golang.org/doc/install.html).
To install `cli.go`, simply run:
```
$ go get github.com/codegangsta/cli
```
Make sure your `PATH` includes to the `$GOPATH/bin` directory so your commands can be easily used:
```
export PATH=$PATH:$GOPATH/bin
```
## Getting Started
One of the philosophies behind cli.go is that an API should be playful and full of discovery. So a cli.go app can be as little as one line of code in `main()`.
``` go
package main
import (
"os"
"github.com/codegangsta/cli"
)
func main() {
cli.NewApp().Run(os.Args)
}
```
This app will run and show help text, but is not very useful. Let's give an action to execute and some help documentation:
``` go
package main
import (
"os"
"github.com/codegangsta/cli"
)
func main() {
app := cli.NewApp()
app.Name = "boom"
app.Usage = "make an explosive entrance"
app.Action = func(c *cli.Context) {
println("boom! I say!")
}
app.Run(os.Args)
}
```
Running this already gives you a ton of functionality, plus support for things like subcommands and flags, which are covered below.
## Example
Being a programmer can be a lonely job. Thankfully by the power of automation that is not the case! Let's create a greeter app to fend off our demons of loneliness!
Start by creating a directory named `greet`, and within it, add a file, `greet.go` with the following code in it:
``` go
package main
import (
"os"
"github.com/codegangsta/cli"
)
func main() {
app := cli.NewApp()
app.Name = "greet"
app.Usage = "fight the loneliness!"
app.Action = func(c *cli.Context) {
println("Hello friend!")
}
app.Run(os.Args)
}
```
Install our command to the `$GOPATH/bin` directory:
```
$ go install
```
Finally run our new command:
```
$ greet
Hello friend!
```
cli.go also generates some bitchass help text:
```
$ greet help
NAME:
greet - fight the loneliness!
USAGE:
greet [global options] command [command options] [arguments...]
VERSION:
0.0.0
COMMANDS:
help, h Shows a list of commands or help for one command
GLOBAL OPTIONS
--version Shows version information
```
### Arguments
You can lookup arguments by calling the `Args` function on `cli.Context`.
``` go
...
app.Action = func(c *cli.Context) {
println("Hello", c.Args()[0])
}
...
```
### Flags
Setting and querying flags is simple.
``` go
...
app.Flags = []cli.Flag {
cli.StringFlag{
Name: "lang",
Value: "english",
Usage: "language for the greeting",
},
}
app.Action = func(c *cli.Context) {
name := "someone"
if len(c.Args()) > 0 {
name = c.Args()[0]
}
if c.String("lang") == "spanish" {
println("Hola", name)
} else {
println("Hello", name)
}
}
...
```
#### Alternate Names
You can set alternate (or short) names for flags by providing a comma-delimited list for the `Name`. e.g.
``` go
app.Flags = []cli.Flag {
cli.StringFlag{
Name: "lang, l",
Value: "english",
Usage: "language for the greeting",
},
}
```
That flag can then be set with `--lang spanish` or `-l spanish`. Note that giving two different forms of the same flag in the same command invocation is an error.
#### Values from the Environment
You can also have the default value set from the environment via `EnvVar`. e.g.
``` go
app.Flags = []cli.Flag {
cli.StringFlag{
Name: "lang, l",
Value: "english",
Usage: "language for the greeting",
EnvVar: "APP_LANG",
},
}
```
The `EnvVar` may also be given as a comma-delimited "cascade", where the first environment variable that resolves is used as the default.
``` go
app.Flags = []cli.Flag {
cli.StringFlag{
Name: "lang, l",
Value: "english",
Usage: "language for the greeting",
EnvVar: "LEGACY_COMPAT_LANG,APP_LANG,LANG",
},
}
```
### Subcommands
Subcommands can be defined for a more git-like command line app.
```go
...
app.Commands = []cli.Command{
{
Name: "add",
Aliases: []string{"a"},
Usage: "add a task to the list",
Action: func(c *cli.Context) {
println("added task: ", c.Args().First())
},
},
{
Name: "complete",
Aliases: []string{"c"},
Usage: "complete a task on the list",
Action: func(c *cli.Context) {
println("completed task: ", c.Args().First())
},
},
{
Name: "template",
Aliases: []string{"r"},
Usage: "options for task templates",
Subcommands: []cli.Command{
{
Name: "add",
Usage: "add a new template",
Action: func(c *cli.Context) {
println("new task template: ", c.Args().First())
},
},
{
Name: "remove",
Usage: "remove an existing template",
Action: func(c *cli.Context) {
println("removed task template: ", c.Args().First())
},
},
},
},
}
...
```
### Bash Completion
You can enable completion commands by setting the `EnableBashCompletion`
flag on the `App` object. By default, this setting will only auto-complete to
show an app's subcommands, but you can write your own completion methods for
the App or its subcommands.
```go
...
var tasks = []string{"cook", "clean", "laundry", "eat", "sleep", "code"}
app := cli.NewApp()
app.EnableBashCompletion = true
app.Commands = []cli.Command{
{
Name: "complete",
Aliases: []string{"c"},
Usage: "complete a task on the list",
Action: func(c *cli.Context) {
println("completed task: ", c.Args().First())
},
BashComplete: func(c *cli.Context) {
// This will complete if no args are passed
if len(c.Args()) > 0 {
return
}
for _, t := range tasks {
fmt.Println(t)
}
},
}
}
...
```
#### To Enable
Source the `autocomplete/bash_autocomplete` file in your `.bashrc` file while
setting the `PROG` variable to the name of your program:
`PROG=myprogram source /.../cli/autocomplete/bash_autocomplete`
## Contribution Guidelines
Feel free to put up a pull request to fix a bug or maybe add a feature. I will give it a code review and make sure that it does not break backwards compatibility. If I or any other collaborators agree that it is in line with the vision of the project, we will work with you to get the code into a mergeable state and merge it into the master branch.
If you have contributed something significant to the project, I will most likely add you as a collaborator. As a collaborator you are given the ability to merge others pull requests. It is very important that new code does not break existing code, so be careful about what code you do choose to merge. If you have any questions feel free to link @codegangsta to the issue in question and we can review it together.
If you feel like you have contributed to the project but have not yet been added as a collaborator, I probably forgot to add you. Hit @codegangsta up over email and we will get it figured out.

View File

@@ -1,298 +0,0 @@
package cli
import (
"fmt"
"io"
"io/ioutil"
"os"
"time"
)
// App is the main structure of a cli application. It is recomended that
// and app be created with the cli.NewApp() function
type App struct {
// The name of the program. Defaults to os.Args[0]
Name string
// Description of the program.
Usage string
// Version of the program
Version string
// List of commands to execute
Commands []Command
// List of flags to parse
Flags []Flag
// Boolean to enable bash completion commands
EnableBashCompletion bool
// Boolean to hide built-in help command
HideHelp bool
// Boolean to hide built-in version flag
HideVersion bool
// An action to execute when the bash-completion flag is set
BashComplete func(context *Context)
// An action to execute before any subcommands are run, but after the context is ready
// If a non-nil error is returned, no subcommands are run
Before func(context *Context) error
// An action to execute after any subcommands are run, but after the subcommand has finished
// It is run even if Action() panics
After func(context *Context) error
// The action to execute when no subcommands are specified
Action func(context *Context)
// Execute this function if the proper command cannot be found
CommandNotFound func(context *Context, command string)
// Compilation date
Compiled time.Time
// List of all authors who contributed
Authors []Author
// Name of Author (Note: Use App.Authors, this is deprecated)
Author string
// Email of Author (Note: Use App.Authors, this is deprecated)
Email string
// Writer writer to write output to
Writer io.Writer
}
// Tries to find out when this binary was compiled.
// Returns the current time if it fails to find it.
func compileTime() time.Time {
info, err := os.Stat(os.Args[0])
if err != nil {
return time.Now()
}
return info.ModTime()
}
// Creates a new cli Application with some reasonable defaults for Name, Usage, Version and Action.
func NewApp() *App {
return &App{
Name: os.Args[0],
Usage: "A new cli application",
Version: "0.0.0",
BashComplete: DefaultAppComplete,
Action: helpCommand.Action,
Compiled: compileTime(),
Writer: os.Stdout,
}
}
// Entry point to the cli app. Parses the arguments slice and routes to the proper flag/args combination
func (a *App) Run(arguments []string) (err error) {
if a.Author != "" || a.Email != "" {
a.Authors = append(a.Authors, Author{Name: a.Author, Email: a.Email})
}
// append help to commands
if a.Command(helpCommand.Name) == nil && !a.HideHelp {
a.Commands = append(a.Commands, helpCommand)
if (HelpFlag != BoolFlag{}) {
a.appendFlag(HelpFlag)
}
}
//append version/help flags
if a.EnableBashCompletion {
a.appendFlag(BashCompletionFlag)
}
if !a.HideVersion {
a.appendFlag(VersionFlag)
}
// parse flags
set := flagSet(a.Name, a.Flags)
set.SetOutput(ioutil.Discard)
err = set.Parse(arguments[1:])
nerr := normalizeFlags(a.Flags, set)
if nerr != nil {
fmt.Fprintln(a.Writer, nerr)
context := NewContext(a, set, set)
ShowAppHelp(context)
fmt.Fprintln(a.Writer)
return nerr
}
context := NewContext(a, set, set)
if err != nil {
fmt.Fprintf(a.Writer, "Incorrect Usage.\n\n")
ShowAppHelp(context)
fmt.Fprintln(a.Writer)
return err
}
if checkCompletions(context) {
return nil
}
if checkHelp(context) {
return nil
}
if checkVersion(context) {
return nil
}
if a.After != nil {
defer func() {
// err is always nil here.
// There is a check to see if it is non-nil
// just few lines before.
err = a.After(context)
}()
}
if a.Before != nil {
err := a.Before(context)
if err != nil {
return err
}
}
args := context.Args()
if args.Present() {
name := args.First()
c := a.Command(name)
if c != nil {
return c.Run(context)
}
}
// Run default Action
a.Action(context)
return nil
}
// Another entry point to the cli app, takes care of passing arguments and error handling
func (a *App) RunAndExitOnError() {
if err := a.Run(os.Args); err != nil {
fmt.Fprintln(os.Stderr, err)
os.Exit(1)
}
}
// Invokes the subcommand given the context, parses ctx.Args() to generate command-specific flags
func (a *App) RunAsSubcommand(ctx *Context) (err error) {
// append help to commands
if len(a.Commands) > 0 {
if a.Command(helpCommand.Name) == nil && !a.HideHelp {
a.Commands = append(a.Commands, helpCommand)
if (HelpFlag != BoolFlag{}) {
a.appendFlag(HelpFlag)
}
}
}
// append flags
if a.EnableBashCompletion {
a.appendFlag(BashCompletionFlag)
}
// parse flags
set := flagSet(a.Name, a.Flags)
set.SetOutput(ioutil.Discard)
err = set.Parse(ctx.Args().Tail())
nerr := normalizeFlags(a.Flags, set)
context := NewContext(a, set, ctx.globalSet)
if nerr != nil {
fmt.Fprintln(a.Writer, nerr)
if len(a.Commands) > 0 {
ShowSubcommandHelp(context)
} else {
ShowCommandHelp(ctx, context.Args().First())
}
fmt.Fprintln(a.Writer)
return nerr
}
if err != nil {
fmt.Fprintf(a.Writer, "Incorrect Usage.\n\n")
ShowSubcommandHelp(context)
return err
}
if checkCompletions(context) {
return nil
}
if len(a.Commands) > 0 {
if checkSubcommandHelp(context) {
return nil
}
} else {
if checkCommandHelp(ctx, context.Args().First()) {
return nil
}
}
if a.After != nil {
defer func() {
// err is always nil here.
// There is a check to see if it is non-nil
// just few lines before.
err = a.After(context)
}()
}
if a.Before != nil {
err := a.Before(context)
if err != nil {
return err
}
}
args := context.Args()
if args.Present() {
name := args.First()
c := a.Command(name)
if c != nil {
return c.Run(context)
}
}
// Run default Action
a.Action(context)
return nil
}
// Returns the named command on App. Returns nil if the command does not exist
func (a *App) Command(name string) *Command {
for _, c := range a.Commands {
if c.HasName(name) {
return &c
}
}
return nil
}
func (a *App) hasFlag(flag Flag) bool {
for _, f := range a.Flags {
if flag == f {
return true
}
}
return false
}
func (a *App) appendFlag(flag Flag) {
if !a.hasFlag(flag) {
a.Flags = append(a.Flags, flag)
}
}
// Author represents someone who has contributed to a cli project.
type Author struct {
Name string // The Authors name
Email string // The Authors email
}
// String makes Author comply to the Stringer interface, to allow an easy print in the templating process
func (a Author) String() string {
e := ""
if a.Email != "" {
e = "<" + a.Email + "> "
}
return fmt.Sprintf("%v %v", a.Name, e)
}

View File

@@ -1,679 +0,0 @@
package cli_test
import (
"bytes"
"flag"
"fmt"
"io"
"os"
"strings"
"testing"
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/codegangsta/cli"
)
func ExampleApp() {
// set args for examples sake
os.Args = []string{"greet", "--name", "Jeremy"}
app := cli.NewApp()
app.Name = "greet"
app.Flags = []cli.Flag{
cli.StringFlag{Name: "name", Value: "bob", Usage: "a name to say"},
}
app.Action = func(c *cli.Context) {
fmt.Printf("Hello %v\n", c.String("name"))
}
app.Author = "Harrison"
app.Email = "harrison@lolwut.com"
app.Authors = []cli.Author{cli.Author{Name: "Oliver Allen", Email: "oliver@toyshop.com"}}
app.Run(os.Args)
// Output:
// Hello Jeremy
}
func ExampleAppSubcommand() {
// set args for examples sake
os.Args = []string{"say", "hi", "english", "--name", "Jeremy"}
app := cli.NewApp()
app.Name = "say"
app.Commands = []cli.Command{
{
Name: "hello",
Aliases: []string{"hi"},
Usage: "use it to see a description",
Description: "This is how we describe hello the function",
Subcommands: []cli.Command{
{
Name: "english",
Aliases: []string{"en"},
Usage: "sends a greeting in english",
Description: "greets someone in english",
Flags: []cli.Flag{
cli.StringFlag{
Name: "name",
Value: "Bob",
Usage: "Name of the person to greet",
},
},
Action: func(c *cli.Context) {
fmt.Println("Hello,", c.String("name"))
},
},
},
},
}
app.Run(os.Args)
// Output:
// Hello, Jeremy
}
func ExampleAppHelp() {
// set args for examples sake
os.Args = []string{"greet", "h", "describeit"}
app := cli.NewApp()
app.Name = "greet"
app.Flags = []cli.Flag{
cli.StringFlag{Name: "name", Value: "bob", Usage: "a name to say"},
}
app.Commands = []cli.Command{
{
Name: "describeit",
Aliases: []string{"d"},
Usage: "use it to see a description",
Description: "This is how we describe describeit the function",
Action: func(c *cli.Context) {
fmt.Printf("i like to describe things")
},
},
}
app.Run(os.Args)
// Output:
// NAME:
// describeit - use it to see a description
//
// USAGE:
// command describeit [arguments...]
//
// DESCRIPTION:
// This is how we describe describeit the function
}
func ExampleAppBashComplete() {
// set args for examples sake
os.Args = []string{"greet", "--generate-bash-completion"}
app := cli.NewApp()
app.Name = "greet"
app.EnableBashCompletion = true
app.Commands = []cli.Command{
{
Name: "describeit",
Aliases: []string{"d"},
Usage: "use it to see a description",
Description: "This is how we describe describeit the function",
Action: func(c *cli.Context) {
fmt.Printf("i like to describe things")
},
}, {
Name: "next",
Usage: "next example",
Description: "more stuff to see when generating bash completion",
Action: func(c *cli.Context) {
fmt.Printf("the next example")
},
},
}
app.Run(os.Args)
// Output:
// describeit
// d
// next
// help
// h
}
func TestApp_Run(t *testing.T) {
s := ""
app := cli.NewApp()
app.Action = func(c *cli.Context) {
s = s + c.Args().First()
}
err := app.Run([]string{"command", "foo"})
expect(t, err, nil)
err = app.Run([]string{"command", "bar"})
expect(t, err, nil)
expect(t, s, "foobar")
}
var commandAppTests = []struct {
name string
expected bool
}{
{"foobar", true},
{"batbaz", true},
{"b", true},
{"f", true},
{"bat", false},
{"nothing", false},
}
func TestApp_Command(t *testing.T) {
app := cli.NewApp()
fooCommand := cli.Command{Name: "foobar", Aliases: []string{"f"}}
batCommand := cli.Command{Name: "batbaz", Aliases: []string{"b"}}
app.Commands = []cli.Command{
fooCommand,
batCommand,
}
for _, test := range commandAppTests {
expect(t, app.Command(test.name) != nil, test.expected)
}
}
func TestApp_CommandWithArgBeforeFlags(t *testing.T) {
var parsedOption, firstArg string
app := cli.NewApp()
command := cli.Command{
Name: "cmd",
Flags: []cli.Flag{
cli.StringFlag{Name: "option", Value: "", Usage: "some option"},
},
Action: func(c *cli.Context) {
parsedOption = c.String("option")
firstArg = c.Args().First()
},
}
app.Commands = []cli.Command{command}
app.Run([]string{"", "cmd", "my-arg", "--option", "my-option"})
expect(t, parsedOption, "my-option")
expect(t, firstArg, "my-arg")
}
func TestApp_RunAsSubcommandParseFlags(t *testing.T) {
var context *cli.Context
a := cli.NewApp()
a.Commands = []cli.Command{
{
Name: "foo",
Action: func(c *cli.Context) {
context = c
},
Flags: []cli.Flag{
cli.StringFlag{
Name: "lang",
Value: "english",
Usage: "language for the greeting",
},
},
Before: func(_ *cli.Context) error { return nil },
},
}
a.Run([]string{"", "foo", "--lang", "spanish", "abcd"})
expect(t, context.Args().Get(0), "abcd")
expect(t, context.String("lang"), "spanish")
}
func TestApp_CommandWithFlagBeforeTerminator(t *testing.T) {
var parsedOption string
var args []string
app := cli.NewApp()
command := cli.Command{
Name: "cmd",
Flags: []cli.Flag{
cli.StringFlag{Name: "option", Value: "", Usage: "some option"},
},
Action: func(c *cli.Context) {
parsedOption = c.String("option")
args = c.Args()
},
}
app.Commands = []cli.Command{command}
app.Run([]string{"", "cmd", "my-arg", "--option", "my-option", "--", "--notARealFlag"})
expect(t, parsedOption, "my-option")
expect(t, args[0], "my-arg")
expect(t, args[1], "--")
expect(t, args[2], "--notARealFlag")
}
func TestApp_CommandWithNoFlagBeforeTerminator(t *testing.T) {
var args []string
app := cli.NewApp()
command := cli.Command{
Name: "cmd",
Action: func(c *cli.Context) {
args = c.Args()
},
}
app.Commands = []cli.Command{command}
app.Run([]string{"", "cmd", "my-arg", "--", "notAFlagAtAll"})
expect(t, args[0], "my-arg")
expect(t, args[1], "--")
expect(t, args[2], "notAFlagAtAll")
}
func TestApp_Float64Flag(t *testing.T) {
var meters float64
app := cli.NewApp()
app.Flags = []cli.Flag{
cli.Float64Flag{Name: "height", Value: 1.5, Usage: "Set the height, in meters"},
}
app.Action = func(c *cli.Context) {
meters = c.Float64("height")
}
app.Run([]string{"", "--height", "1.93"})
expect(t, meters, 1.93)
}
func TestApp_ParseSliceFlags(t *testing.T) {
var parsedOption, firstArg string
var parsedIntSlice []int
var parsedStringSlice []string
app := cli.NewApp()
command := cli.Command{
Name: "cmd",
Flags: []cli.Flag{
cli.IntSliceFlag{Name: "p", Value: &cli.IntSlice{}, Usage: "set one or more ip addr"},
cli.StringSliceFlag{Name: "ip", Value: &cli.StringSlice{}, Usage: "set one or more ports to open"},
},
Action: func(c *cli.Context) {
parsedIntSlice = c.IntSlice("p")
parsedStringSlice = c.StringSlice("ip")
parsedOption = c.String("option")
firstArg = c.Args().First()
},
}
app.Commands = []cli.Command{command}
app.Run([]string{"", "cmd", "my-arg", "-p", "22", "-p", "80", "-ip", "8.8.8.8", "-ip", "8.8.4.4"})
IntsEquals := func(a, b []int) bool {
if len(a) != len(b) {
return false
}
for i, v := range a {
if v != b[i] {
return false
}
}
return true
}
StrsEquals := func(a, b []string) bool {
if len(a) != len(b) {
return false
}
for i, v := range a {
if v != b[i] {
return false
}
}
return true
}
var expectedIntSlice = []int{22, 80}
var expectedStringSlice = []string{"8.8.8.8", "8.8.4.4"}
if !IntsEquals(parsedIntSlice, expectedIntSlice) {
t.Errorf("%v does not match %v", parsedIntSlice, expectedIntSlice)
}
if !StrsEquals(parsedStringSlice, expectedStringSlice) {
t.Errorf("%v does not match %v", parsedStringSlice, expectedStringSlice)
}
}
func TestApp_DefaultStdout(t *testing.T) {
app := cli.NewApp()
if app.Writer != os.Stdout {
t.Error("Default output writer not set.")
}
}
type mockWriter struct {
written []byte
}
func (fw *mockWriter) Write(p []byte) (n int, err error) {
if fw.written == nil {
fw.written = p
} else {
fw.written = append(fw.written, p...)
}
return len(p), nil
}
func (fw *mockWriter) GetWritten() (b []byte) {
return fw.written
}
func TestApp_SetStdout(t *testing.T) {
w := &mockWriter{}
app := cli.NewApp()
app.Name = "test"
app.Writer = w
err := app.Run([]string{"help"})
if err != nil {
t.Fatalf("Run error: %s", err)
}
if len(w.written) == 0 {
t.Error("App did not write output to desired writer.")
}
}
func TestApp_BeforeFunc(t *testing.T) {
beforeRun, subcommandRun := false, false
beforeError := fmt.Errorf("fail")
var err error
app := cli.NewApp()
app.Before = func(c *cli.Context) error {
beforeRun = true
s := c.String("opt")
if s == "fail" {
return beforeError
}
return nil
}
app.Commands = []cli.Command{
cli.Command{
Name: "sub",
Action: func(c *cli.Context) {
subcommandRun = true
},
},
}
app.Flags = []cli.Flag{
cli.StringFlag{Name: "opt"},
}
// run with the Before() func succeeding
err = app.Run([]string{"command", "--opt", "succeed", "sub"})
if err != nil {
t.Fatalf("Run error: %s", err)
}
if beforeRun == false {
t.Errorf("Before() not executed when expected")
}
if subcommandRun == false {
t.Errorf("Subcommand not executed when expected")
}
// reset
beforeRun, subcommandRun = false, false
// run with the Before() func failing
err = app.Run([]string{"command", "--opt", "fail", "sub"})
// should be the same error produced by the Before func
if err != beforeError {
t.Errorf("Run error expected, but not received")
}
if beforeRun == false {
t.Errorf("Before() not executed when expected")
}
if subcommandRun == true {
t.Errorf("Subcommand executed when NOT expected")
}
}
func TestApp_AfterFunc(t *testing.T) {
afterRun, subcommandRun := false, false
afterError := fmt.Errorf("fail")
var err error
app := cli.NewApp()
app.After = func(c *cli.Context) error {
afterRun = true
s := c.String("opt")
if s == "fail" {
return afterError
}
return nil
}
app.Commands = []cli.Command{
cli.Command{
Name: "sub",
Action: func(c *cli.Context) {
subcommandRun = true
},
},
}
app.Flags = []cli.Flag{
cli.StringFlag{Name: "opt"},
}
// run with the After() func succeeding
err = app.Run([]string{"command", "--opt", "succeed", "sub"})
if err != nil {
t.Fatalf("Run error: %s", err)
}
if afterRun == false {
t.Errorf("After() not executed when expected")
}
if subcommandRun == false {
t.Errorf("Subcommand not executed when expected")
}
// reset
afterRun, subcommandRun = false, false
// run with the Before() func failing
err = app.Run([]string{"command", "--opt", "fail", "sub"})
// should be the same error produced by the Before func
if err != afterError {
t.Errorf("Run error expected, but not received")
}
if afterRun == false {
t.Errorf("After() not executed when expected")
}
if subcommandRun == false {
t.Errorf("Subcommand not executed when expected")
}
}
func TestAppNoHelpFlag(t *testing.T) {
oldFlag := cli.HelpFlag
defer func() {
cli.HelpFlag = oldFlag
}()
cli.HelpFlag = cli.BoolFlag{}
app := cli.NewApp()
err := app.Run([]string{"test", "-h"})
if err != flag.ErrHelp {
t.Errorf("expected error about missing help flag, but got: %s (%T)", err, err)
}
}
func TestAppHelpPrinter(t *testing.T) {
oldPrinter := cli.HelpPrinter
defer func() {
cli.HelpPrinter = oldPrinter
}()
var wasCalled = false
cli.HelpPrinter = func(w io.Writer, template string, data interface{}) {
wasCalled = true
}
app := cli.NewApp()
app.Run([]string{"-h"})
if wasCalled == false {
t.Errorf("Help printer expected to be called, but was not")
}
}
func TestAppVersionPrinter(t *testing.T) {
oldPrinter := cli.VersionPrinter
defer func() {
cli.VersionPrinter = oldPrinter
}()
var wasCalled = false
cli.VersionPrinter = func(c *cli.Context) {
wasCalled = true
}
app := cli.NewApp()
ctx := cli.NewContext(app, nil, nil)
cli.ShowVersion(ctx)
if wasCalled == false {
t.Errorf("Version printer expected to be called, but was not")
}
}
func TestAppCommandNotFound(t *testing.T) {
beforeRun, subcommandRun := false, false
app := cli.NewApp()
app.CommandNotFound = func(c *cli.Context, command string) {
beforeRun = true
}
app.Commands = []cli.Command{
cli.Command{
Name: "bar",
Action: func(c *cli.Context) {
subcommandRun = true
},
},
}
app.Run([]string{"command", "foo"})
expect(t, beforeRun, true)
expect(t, subcommandRun, false)
}
func TestGlobalFlagsInSubcommands(t *testing.T) {
subcommandRun := false
app := cli.NewApp()
app.Flags = []cli.Flag{
cli.BoolFlag{Name: "debug, d", Usage: "Enable debugging"},
}
app.Commands = []cli.Command{
cli.Command{
Name: "foo",
Subcommands: []cli.Command{
{
Name: "bar",
Action: func(c *cli.Context) {
if c.GlobalBool("debug") {
subcommandRun = true
}
},
},
},
},
}
app.Run([]string{"command", "-d", "foo", "bar"})
expect(t, subcommandRun, true)
}
func TestApp_Run_CommandWithSubcommandHasHelpTopic(t *testing.T) {
var subcommandHelpTopics = [][]string{
{"command", "foo", "--help"},
{"command", "foo", "-h"},
{"command", "foo", "help"},
}
for _, flagSet := range subcommandHelpTopics {
t.Logf("==> checking with flags %v", flagSet)
app := cli.NewApp()
buf := new(bytes.Buffer)
app.Writer = buf
subCmdBar := cli.Command{
Name: "bar",
Usage: "does bar things",
}
subCmdBaz := cli.Command{
Name: "baz",
Usage: "does baz things",
}
cmd := cli.Command{
Name: "foo",
Description: "descriptive wall of text about how it does foo things",
Subcommands: []cli.Command{subCmdBar, subCmdBaz},
}
app.Commands = []cli.Command{cmd}
err := app.Run(flagSet)
if err != nil {
t.Error(err)
}
output := buf.String()
t.Logf("output: %q\n", buf.Bytes())
if strings.Contains(output, "No help topic for") {
t.Errorf("expect a help topic, got none: \n%q", output)
}
for _, shouldContain := range []string{
cmd.Name, cmd.Description,
subCmdBar.Name, subCmdBar.Usage,
subCmdBaz.Name, subCmdBaz.Usage,
} {
if !strings.Contains(output, shouldContain) {
t.Errorf("want help to contain %q, did not: \n%q", shouldContain, output)
}
}
}
}

View File

@@ -1,13 +0,0 @@
#! /bin/bash
_cli_bash_autocomplete() {
local cur prev opts base
COMPREPLY=()
cur="${COMP_WORDS[COMP_CWORD]}"
prev="${COMP_WORDS[COMP_CWORD-1]}"
opts=$( ${COMP_WORDS[@]:0:$COMP_CWORD} --generate-bash-completion )
COMPREPLY=( $(compgen -W "${opts}" -- ${cur}) )
return 0
}
complete -F _cli_bash_autocomplete $PROG

View File

@@ -1,5 +0,0 @@
autoload -U compinit && compinit
autoload -U bashcompinit && bashcompinit
script_dir=$(dirname $0)
source ${script_dir}/bash_autocomplete

View File

@@ -1,19 +0,0 @@
// Package cli provides a minimal framework for creating and organizing command line
// Go applications. cli is designed to be easy to understand and write, the most simple
// cli application can be written as follows:
// func main() {
// cli.NewApp().Run(os.Args)
// }
//
// Of course this application does not do much, so let's make this an actual application:
// func main() {
// app := cli.NewApp()
// app.Name = "greet"
// app.Usage = "say a greeting"
// app.Action = func(c *cli.Context) {
// println("Greetings")
// }
//
// app.Run(os.Args)
// }
package cli

View File

@@ -1,100 +0,0 @@
package cli_test
import (
"os"
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/codegangsta/cli"
)
func Example() {
app := cli.NewApp()
app.Name = "todo"
app.Usage = "task list on the command line"
app.Commands = []cli.Command{
{
Name: "add",
Aliases: []string{"a"},
Usage: "add a task to the list",
Action: func(c *cli.Context) {
println("added task: ", c.Args().First())
},
},
{
Name: "complete",
Aliases: []string{"c"},
Usage: "complete a task on the list",
Action: func(c *cli.Context) {
println("completed task: ", c.Args().First())
},
},
}
app.Run(os.Args)
}
func ExampleSubcommand() {
app := cli.NewApp()
app.Name = "say"
app.Commands = []cli.Command{
{
Name: "hello",
Aliases: []string{"hi"},
Usage: "use it to see a description",
Description: "This is how we describe hello the function",
Subcommands: []cli.Command{
{
Name: "english",
Aliases: []string{"en"},
Usage: "sends a greeting in english",
Description: "greets someone in english",
Flags: []cli.Flag{
cli.StringFlag{
Name: "name",
Value: "Bob",
Usage: "Name of the person to greet",
},
},
Action: func(c *cli.Context) {
println("Hello, ", c.String("name"))
},
}, {
Name: "spanish",
Aliases: []string{"sp"},
Usage: "sends a greeting in spanish",
Flags: []cli.Flag{
cli.StringFlag{
Name: "surname",
Value: "Jones",
Usage: "Surname of the person to greet",
},
},
Action: func(c *cli.Context) {
println("Hola, ", c.String("surname"))
},
}, {
Name: "french",
Aliases: []string{"fr"},
Usage: "sends a greeting in french",
Flags: []cli.Flag{
cli.StringFlag{
Name: "nickname",
Value: "Stevie",
Usage: "Nickname of the person to greet",
},
},
Action: func(c *cli.Context) {
println("Bonjour, ", c.String("nickname"))
},
},
},
}, {
Name: "bye",
Usage: "says goodbye",
Action: func(c *cli.Context) {
println("bye")
},
},
}
app.Run(os.Args)
}

View File

@@ -1,184 +0,0 @@
package cli
import (
"fmt"
"io/ioutil"
"strings"
)
// Command is a subcommand for a cli.App.
type Command struct {
// The name of the command
Name string
// short name of the command. Typically one character (deprecated, use `Aliases`)
ShortName string
// A list of aliases for the command
Aliases []string
// A short description of the usage of this command
Usage string
// A longer explanation of how the command works
Description string
// The function to call when checking for bash command completions
BashComplete func(context *Context)
// An action to execute before any sub-subcommands are run, but after the context is ready
// If a non-nil error is returned, no sub-subcommands are run
Before func(context *Context) error
// An action to execute after any subcommands are run, but after the subcommand has finished
// It is run even if Action() panics
After func(context *Context) error
// The function to call when this command is invoked
Action func(context *Context)
// List of child commands
Subcommands []Command
// List of flags to parse
Flags []Flag
// Treat all flags as normal arguments if true
SkipFlagParsing bool
// Boolean to hide built-in help command
HideHelp bool
}
// Invokes the command given the context, parses ctx.Args() to generate command-specific flags
func (c Command) Run(ctx *Context) error {
if len(c.Subcommands) > 0 || c.Before != nil || c.After != nil {
return c.startApp(ctx)
}
if !c.HideHelp && (HelpFlag != BoolFlag{}) {
// append help to flags
c.Flags = append(
c.Flags,
HelpFlag,
)
}
if ctx.App.EnableBashCompletion {
c.Flags = append(c.Flags, BashCompletionFlag)
}
set := flagSet(c.Name, c.Flags)
set.SetOutput(ioutil.Discard)
firstFlagIndex := -1
terminatorIndex := -1
for index, arg := range ctx.Args() {
if arg == "--" {
terminatorIndex = index
break
} else if strings.HasPrefix(arg, "-") && firstFlagIndex == -1 {
firstFlagIndex = index
}
}
var err error
if firstFlagIndex > -1 && !c.SkipFlagParsing {
args := ctx.Args()
regularArgs := make([]string, len(args[1:firstFlagIndex]))
copy(regularArgs, args[1:firstFlagIndex])
var flagArgs []string
if terminatorIndex > -1 {
flagArgs = args[firstFlagIndex:terminatorIndex]
regularArgs = append(regularArgs, args[terminatorIndex:]...)
} else {
flagArgs = args[firstFlagIndex:]
}
err = set.Parse(append(flagArgs, regularArgs...))
} else {
err = set.Parse(ctx.Args().Tail())
}
if err != nil {
fmt.Fprint(ctx.App.Writer, "Incorrect Usage.\n\n")
ShowCommandHelp(ctx, c.Name)
fmt.Fprintln(ctx.App.Writer)
return err
}
nerr := normalizeFlags(c.Flags, set)
if nerr != nil {
fmt.Fprintln(ctx.App.Writer, nerr)
fmt.Fprintln(ctx.App.Writer)
ShowCommandHelp(ctx, c.Name)
fmt.Fprintln(ctx.App.Writer)
return nerr
}
context := NewContext(ctx.App, set, ctx.globalSet)
if checkCommandCompletions(context, c.Name) {
return nil
}
if checkCommandHelp(context, c.Name) {
return nil
}
context.Command = c
c.Action(context)
return nil
}
func (c Command) Names() []string {
names := []string{c.Name}
if c.ShortName != "" {
names = append(names, c.ShortName)
}
return append(names, c.Aliases...)
}
// Returns true if Command.Name or Command.ShortName matches given name
func (c Command) HasName(name string) bool {
for _, n := range c.Names() {
if n == name {
return true
}
}
return false
}
func (c Command) startApp(ctx *Context) error {
app := NewApp()
// set the name and usage
app.Name = fmt.Sprintf("%s %s", ctx.App.Name, c.Name)
if c.Description != "" {
app.Usage = c.Description
} else {
app.Usage = c.Usage
}
// set CommandNotFound
app.CommandNotFound = ctx.App.CommandNotFound
// set the flags and commands
app.Commands = c.Subcommands
app.Flags = c.Flags
app.HideHelp = c.HideHelp
app.Version = ctx.App.Version
app.HideVersion = ctx.App.HideVersion
app.Compiled = ctx.App.Compiled
app.Author = ctx.App.Author
app.Email = ctx.App.Email
app.Writer = ctx.App.Writer
// bash completion
app.EnableBashCompletion = ctx.App.EnableBashCompletion
if c.BashComplete != nil {
app.BashComplete = c.BashComplete
}
// set the actions
app.Before = c.Before
app.After = c.After
if c.Action != nil {
app.Action = c.Action
} else {
app.Action = helpSubcommand.Action
}
return app.RunAsSubcommand(ctx)
}

View File

@@ -1,49 +0,0 @@
package cli_test
import (
"flag"
"testing"
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/codegangsta/cli"
)
func TestCommandDoNotIgnoreFlags(t *testing.T) {
app := cli.NewApp()
set := flag.NewFlagSet("test", 0)
test := []string{"blah", "blah", "-break"}
set.Parse(test)
c := cli.NewContext(app, set, set)
command := cli.Command{
Name: "test-cmd",
Aliases: []string{"tc"},
Usage: "this is for testing",
Description: "testing",
Action: func(_ *cli.Context) {},
}
err := command.Run(c)
expect(t, err.Error(), "flag provided but not defined: -break")
}
func TestCommandIgnoreFlags(t *testing.T) {
app := cli.NewApp()
set := flag.NewFlagSet("test", 0)
test := []string{"blah", "blah"}
set.Parse(test)
c := cli.NewContext(app, set, set)
command := cli.Command{
Name: "test-cmd",
Aliases: []string{"tc"},
Usage: "this is for testing",
Description: "testing",
Action: func(_ *cli.Context) {},
SkipFlagParsing: true,
}
err := command.Run(c)
expect(t, err, nil)
}

View File

@@ -1,344 +0,0 @@
package cli
import (
"errors"
"flag"
"strconv"
"strings"
"time"
)
// Context is a type that is passed through to
// each Handler action in a cli application. Context
// can be used to retrieve context-specific Args and
// parsed command-line options.
type Context struct {
App *App
Command Command
flagSet *flag.FlagSet
globalSet *flag.FlagSet
setFlags map[string]bool
globalSetFlags map[string]bool
}
// Creates a new context. For use in when invoking an App or Command action.
func NewContext(app *App, set *flag.FlagSet, globalSet *flag.FlagSet) *Context {
return &Context{App: app, flagSet: set, globalSet: globalSet}
}
// Looks up the value of a local int flag, returns 0 if no int flag exists
func (c *Context) Int(name string) int {
return lookupInt(name, c.flagSet)
}
// Looks up the value of a local time.Duration flag, returns 0 if no time.Duration flag exists
func (c *Context) Duration(name string) time.Duration {
return lookupDuration(name, c.flagSet)
}
// Looks up the value of a local float64 flag, returns 0 if no float64 flag exists
func (c *Context) Float64(name string) float64 {
return lookupFloat64(name, c.flagSet)
}
// Looks up the value of a local bool flag, returns false if no bool flag exists
func (c *Context) Bool(name string) bool {
return lookupBool(name, c.flagSet)
}
// Looks up the value of a local boolT flag, returns false if no bool flag exists
func (c *Context) BoolT(name string) bool {
return lookupBoolT(name, c.flagSet)
}
// Looks up the value of a local string flag, returns "" if no string flag exists
func (c *Context) String(name string) string {
return lookupString(name, c.flagSet)
}
// Looks up the value of a local string slice flag, returns nil if no string slice flag exists
func (c *Context) StringSlice(name string) []string {
return lookupStringSlice(name, c.flagSet)
}
// Looks up the value of a local int slice flag, returns nil if no int slice flag exists
func (c *Context) IntSlice(name string) []int {
return lookupIntSlice(name, c.flagSet)
}
// Looks up the value of a local generic flag, returns nil if no generic flag exists
func (c *Context) Generic(name string) interface{} {
return lookupGeneric(name, c.flagSet)
}
// Looks up the value of a global int flag, returns 0 if no int flag exists
func (c *Context) GlobalInt(name string) int {
return lookupInt(name, c.globalSet)
}
// Looks up the value of a global time.Duration flag, returns 0 if no time.Duration flag exists
func (c *Context) GlobalDuration(name string) time.Duration {
return lookupDuration(name, c.globalSet)
}
// Looks up the value of a global bool flag, returns false if no bool flag exists
func (c *Context) GlobalBool(name string) bool {
return lookupBool(name, c.globalSet)
}
// Looks up the value of a global string flag, returns "" if no string flag exists
func (c *Context) GlobalString(name string) string {
return lookupString(name, c.globalSet)
}
// Looks up the value of a global string slice flag, returns nil if no string slice flag exists
func (c *Context) GlobalStringSlice(name string) []string {
return lookupStringSlice(name, c.globalSet)
}
// Looks up the value of a global int slice flag, returns nil if no int slice flag exists
func (c *Context) GlobalIntSlice(name string) []int {
return lookupIntSlice(name, c.globalSet)
}
// Looks up the value of a global generic flag, returns nil if no generic flag exists
func (c *Context) GlobalGeneric(name string) interface{} {
return lookupGeneric(name, c.globalSet)
}
// Returns the number of flags set
func (c *Context) NumFlags() int {
return c.flagSet.NFlag()
}
// Determines if the flag was actually set
func (c *Context) IsSet(name string) bool {
if c.setFlags == nil {
c.setFlags = make(map[string]bool)
c.flagSet.Visit(func(f *flag.Flag) {
c.setFlags[f.Name] = true
})
}
return c.setFlags[name] == true
}
// Determines if the global flag was actually set
func (c *Context) GlobalIsSet(name string) bool {
if c.globalSetFlags == nil {
c.globalSetFlags = make(map[string]bool)
c.globalSet.Visit(func(f *flag.Flag) {
c.globalSetFlags[f.Name] = true
})
}
return c.globalSetFlags[name] == true
}
// Returns a slice of flag names used in this context.
func (c *Context) FlagNames() (names []string) {
for _, flag := range c.Command.Flags {
name := strings.Split(flag.getName(), ",")[0]
if name == "help" {
continue
}
names = append(names, name)
}
return
}
// Returns a slice of global flag names used by the app.
func (c *Context) GlobalFlagNames() (names []string) {
for _, flag := range c.App.Flags {
name := strings.Split(flag.getName(), ",")[0]
if name == "help" || name == "version" {
continue
}
names = append(names, name)
}
return
}
type Args []string
// Returns the command line arguments associated with the context.
func (c *Context) Args() Args {
args := Args(c.flagSet.Args())
return args
}
// Returns the nth argument, or else a blank string
func (a Args) Get(n int) string {
if len(a) > n {
return a[n]
}
return ""
}
// Returns the first argument, or else a blank string
func (a Args) First() string {
return a.Get(0)
}
// Return the rest of the arguments (not the first one)
// or else an empty string slice
func (a Args) Tail() []string {
if len(a) >= 2 {
return []string(a)[1:]
}
return []string{}
}
// Checks if there are any arguments present
func (a Args) Present() bool {
return len(a) != 0
}
// Swaps arguments at the given indexes
func (a Args) Swap(from, to int) error {
if from >= len(a) || to >= len(a) {
return errors.New("index out of range")
}
a[from], a[to] = a[to], a[from]
return nil
}
func lookupInt(name string, set *flag.FlagSet) int {
f := set.Lookup(name)
if f != nil {
val, err := strconv.Atoi(f.Value.String())
if err != nil {
return 0
}
return val
}
return 0
}
func lookupDuration(name string, set *flag.FlagSet) time.Duration {
f := set.Lookup(name)
if f != nil {
val, err := time.ParseDuration(f.Value.String())
if err == nil {
return val
}
}
return 0
}
func lookupFloat64(name string, set *flag.FlagSet) float64 {
f := set.Lookup(name)
if f != nil {
val, err := strconv.ParseFloat(f.Value.String(), 64)
if err != nil {
return 0
}
return val
}
return 0
}
func lookupString(name string, set *flag.FlagSet) string {
f := set.Lookup(name)
if f != nil {
return f.Value.String()
}
return ""
}
func lookupStringSlice(name string, set *flag.FlagSet) []string {
f := set.Lookup(name)
if f != nil {
return (f.Value.(*StringSlice)).Value()
}
return nil
}
func lookupIntSlice(name string, set *flag.FlagSet) []int {
f := set.Lookup(name)
if f != nil {
return (f.Value.(*IntSlice)).Value()
}
return nil
}
func lookupGeneric(name string, set *flag.FlagSet) interface{} {
f := set.Lookup(name)
if f != nil {
return f.Value
}
return nil
}
func lookupBool(name string, set *flag.FlagSet) bool {
f := set.Lookup(name)
if f != nil {
val, err := strconv.ParseBool(f.Value.String())
if err != nil {
return false
}
return val
}
return false
}
func lookupBoolT(name string, set *flag.FlagSet) bool {
f := set.Lookup(name)
if f != nil {
val, err := strconv.ParseBool(f.Value.String())
if err != nil {
return true
}
return val
}
return false
}
func copyFlag(name string, ff *flag.Flag, set *flag.FlagSet) {
switch ff.Value.(type) {
case *StringSlice:
default:
set.Set(name, ff.Value.String())
}
}
func normalizeFlags(flags []Flag, set *flag.FlagSet) error {
visited := make(map[string]bool)
set.Visit(func(f *flag.Flag) {
visited[f.Name] = true
})
for _, f := range flags {
parts := strings.Split(f.getName(), ",")
if len(parts) == 1 {
continue
}
var ff *flag.Flag
for _, name := range parts {
name = strings.Trim(name, " ")
if visited[name] {
if ff != nil {
return errors.New("Cannot use two forms of the same flag: " + name + " " + ff.Name)
}
ff = set.Lookup(name)
}
}
if ff == nil {
continue
}
for _, name := range parts {
name = strings.Trim(name, " ")
if !visited[name] {
copyFlag(name, ff, set)
}
}
}
return nil
}

View File

@@ -1,111 +0,0 @@
package cli_test
import (
"flag"
"testing"
"time"
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/codegangsta/cli"
)
func TestNewContext(t *testing.T) {
set := flag.NewFlagSet("test", 0)
set.Int("myflag", 12, "doc")
globalSet := flag.NewFlagSet("test", 0)
globalSet.Int("myflag", 42, "doc")
command := cli.Command{Name: "mycommand"}
c := cli.NewContext(nil, set, globalSet)
c.Command = command
expect(t, c.Int("myflag"), 12)
expect(t, c.GlobalInt("myflag"), 42)
expect(t, c.Command.Name, "mycommand")
}
func TestContext_Int(t *testing.T) {
set := flag.NewFlagSet("test", 0)
set.Int("myflag", 12, "doc")
c := cli.NewContext(nil, set, set)
expect(t, c.Int("myflag"), 12)
}
func TestContext_Duration(t *testing.T) {
set := flag.NewFlagSet("test", 0)
set.Duration("myflag", time.Duration(12*time.Second), "doc")
c := cli.NewContext(nil, set, set)
expect(t, c.Duration("myflag"), time.Duration(12*time.Second))
}
func TestContext_String(t *testing.T) {
set := flag.NewFlagSet("test", 0)
set.String("myflag", "hello world", "doc")
c := cli.NewContext(nil, set, set)
expect(t, c.String("myflag"), "hello world")
}
func TestContext_Bool(t *testing.T) {
set := flag.NewFlagSet("test", 0)
set.Bool("myflag", false, "doc")
c := cli.NewContext(nil, set, set)
expect(t, c.Bool("myflag"), false)
}
func TestContext_BoolT(t *testing.T) {
set := flag.NewFlagSet("test", 0)
set.Bool("myflag", true, "doc")
c := cli.NewContext(nil, set, set)
expect(t, c.BoolT("myflag"), true)
}
func TestContext_Args(t *testing.T) {
set := flag.NewFlagSet("test", 0)
set.Bool("myflag", false, "doc")
c := cli.NewContext(nil, set, set)
set.Parse([]string{"--myflag", "bat", "baz"})
expect(t, len(c.Args()), 2)
expect(t, c.Bool("myflag"), true)
}
func TestContext_IsSet(t *testing.T) {
set := flag.NewFlagSet("test", 0)
set.Bool("myflag", false, "doc")
set.String("otherflag", "hello world", "doc")
globalSet := flag.NewFlagSet("test", 0)
globalSet.Bool("myflagGlobal", true, "doc")
c := cli.NewContext(nil, set, globalSet)
set.Parse([]string{"--myflag", "bat", "baz"})
globalSet.Parse([]string{"--myflagGlobal", "bat", "baz"})
expect(t, c.IsSet("myflag"), true)
expect(t, c.IsSet("otherflag"), false)
expect(t, c.IsSet("bogusflag"), false)
expect(t, c.IsSet("myflagGlobal"), false)
}
func TestContext_GlobalIsSet(t *testing.T) {
set := flag.NewFlagSet("test", 0)
set.Bool("myflag", false, "doc")
set.String("otherflag", "hello world", "doc")
globalSet := flag.NewFlagSet("test", 0)
globalSet.Bool("myflagGlobal", true, "doc")
globalSet.Bool("myflagGlobalUnset", true, "doc")
c := cli.NewContext(nil, set, globalSet)
set.Parse([]string{"--myflag", "bat", "baz"})
globalSet.Parse([]string{"--myflagGlobal", "bat", "baz"})
expect(t, c.GlobalIsSet("myflag"), false)
expect(t, c.GlobalIsSet("otherflag"), false)
expect(t, c.GlobalIsSet("bogusflag"), false)
expect(t, c.GlobalIsSet("myflagGlobal"), true)
expect(t, c.GlobalIsSet("myflagGlobalUnset"), false)
expect(t, c.GlobalIsSet("bogusGlobal"), false)
}
func TestContext_NumFlags(t *testing.T) {
set := flag.NewFlagSet("test", 0)
set.Bool("myflag", false, "doc")
set.String("otherflag", "hello world", "doc")
globalSet := flag.NewFlagSet("test", 0)
globalSet.Bool("myflagGlobal", true, "doc")
c := cli.NewContext(nil, set, globalSet)
set.Parse([]string{"--myflag", "--otherflag=foo"})
globalSet.Parse([]string{"--myflagGlobal"})
expect(t, c.NumFlags(), 2)
}

View File

@@ -1,454 +0,0 @@
package cli
import (
"flag"
"fmt"
"os"
"strconv"
"strings"
"time"
)
// This flag enables bash-completion for all commands and subcommands
var BashCompletionFlag = BoolFlag{
Name: "generate-bash-completion",
}
// This flag prints the version for the application
var VersionFlag = BoolFlag{
Name: "version, v",
Usage: "print the version",
}
// This flag prints the help for all commands and subcommands
// Set to the zero value (BoolFlag{}) to disable flag -- keeps subcommand
// unless HideHelp is set to true)
var HelpFlag = BoolFlag{
Name: "help, h",
Usage: "show help",
}
// Flag is a common interface related to parsing flags in cli.
// For more advanced flag parsing techniques, it is recomended that
// this interface be implemented.
type Flag interface {
fmt.Stringer
// Apply Flag settings to the given flag set
Apply(*flag.FlagSet)
getName() string
}
func flagSet(name string, flags []Flag) *flag.FlagSet {
set := flag.NewFlagSet(name, flag.ContinueOnError)
for _, f := range flags {
f.Apply(set)
}
return set
}
func eachName(longName string, fn func(string)) {
parts := strings.Split(longName, ",")
for _, name := range parts {
name = strings.Trim(name, " ")
fn(name)
}
}
// Generic is a generic parseable type identified by a specific flag
type Generic interface {
Set(value string) error
String() string
}
// GenericFlag is the flag type for types implementing Generic
type GenericFlag struct {
Name string
Value Generic
Usage string
EnvVar string
}
// String returns the string representation of the generic flag to display the
// help text to the user (uses the String() method of the generic flag to show
// the value)
func (f GenericFlag) String() string {
return withEnvHint(f.EnvVar, fmt.Sprintf("%s%s \"%v\"\t%v", prefixFor(f.Name), f.Name, f.Value, f.Usage))
}
// Apply takes the flagset and calls Set on the generic flag with the value
// provided by the user for parsing by the flag
func (f GenericFlag) Apply(set *flag.FlagSet) {
val := f.Value
if f.EnvVar != "" {
for _, envVar := range strings.Split(f.EnvVar, ",") {
envVar = strings.TrimSpace(envVar)
if envVal := os.Getenv(envVar); envVal != "" {
val.Set(envVal)
break
}
}
}
eachName(f.Name, func(name string) {
set.Var(f.Value, name, f.Usage)
})
}
func (f GenericFlag) getName() string {
return f.Name
}
type StringSlice []string
func (f *StringSlice) Set(value string) error {
*f = append(*f, value)
return nil
}
func (f *StringSlice) String() string {
return fmt.Sprintf("%s", *f)
}
func (f *StringSlice) Value() []string {
return *f
}
type StringSliceFlag struct {
Name string
Value *StringSlice
Usage string
EnvVar string
}
func (f StringSliceFlag) String() string {
firstName := strings.Trim(strings.Split(f.Name, ",")[0], " ")
pref := prefixFor(firstName)
return withEnvHint(f.EnvVar, fmt.Sprintf("%s [%v]\t%v", prefixedNames(f.Name), pref+firstName+" option "+pref+firstName+" option", f.Usage))
}
func (f StringSliceFlag) Apply(set *flag.FlagSet) {
if f.EnvVar != "" {
for _, envVar := range strings.Split(f.EnvVar, ",") {
envVar = strings.TrimSpace(envVar)
if envVal := os.Getenv(envVar); envVal != "" {
newVal := &StringSlice{}
for _, s := range strings.Split(envVal, ",") {
s = strings.TrimSpace(s)
newVal.Set(s)
}
f.Value = newVal
break
}
}
}
eachName(f.Name, func(name string) {
set.Var(f.Value, name, f.Usage)
})
}
func (f StringSliceFlag) getName() string {
return f.Name
}
type IntSlice []int
func (f *IntSlice) Set(value string) error {
tmp, err := strconv.Atoi(value)
if err != nil {
return err
} else {
*f = append(*f, tmp)
}
return nil
}
func (f *IntSlice) String() string {
return fmt.Sprintf("%d", *f)
}
func (f *IntSlice) Value() []int {
return *f
}
type IntSliceFlag struct {
Name string
Value *IntSlice
Usage string
EnvVar string
}
func (f IntSliceFlag) String() string {
firstName := strings.Trim(strings.Split(f.Name, ",")[0], " ")
pref := prefixFor(firstName)
return withEnvHint(f.EnvVar, fmt.Sprintf("%s [%v]\t%v", prefixedNames(f.Name), pref+firstName+" option "+pref+firstName+" option", f.Usage))
}
func (f IntSliceFlag) Apply(set *flag.FlagSet) {
if f.EnvVar != "" {
for _, envVar := range strings.Split(f.EnvVar, ",") {
envVar = strings.TrimSpace(envVar)
if envVal := os.Getenv(envVar); envVal != "" {
newVal := &IntSlice{}
for _, s := range strings.Split(envVal, ",") {
s = strings.TrimSpace(s)
err := newVal.Set(s)
if err != nil {
fmt.Fprintf(os.Stderr, err.Error())
}
}
f.Value = newVal
break
}
}
}
eachName(f.Name, func(name string) {
set.Var(f.Value, name, f.Usage)
})
}
func (f IntSliceFlag) getName() string {
return f.Name
}
type BoolFlag struct {
Name string
Usage string
EnvVar string
}
func (f BoolFlag) String() string {
return withEnvHint(f.EnvVar, fmt.Sprintf("%s\t%v", prefixedNames(f.Name), f.Usage))
}
func (f BoolFlag) Apply(set *flag.FlagSet) {
val := false
if f.EnvVar != "" {
for _, envVar := range strings.Split(f.EnvVar, ",") {
envVar = strings.TrimSpace(envVar)
if envVal := os.Getenv(envVar); envVal != "" {
envValBool, err := strconv.ParseBool(envVal)
if err == nil {
val = envValBool
}
break
}
}
}
eachName(f.Name, func(name string) {
set.Bool(name, val, f.Usage)
})
}
func (f BoolFlag) getName() string {
return f.Name
}
type BoolTFlag struct {
Name string
Usage string
EnvVar string
}
func (f BoolTFlag) String() string {
return withEnvHint(f.EnvVar, fmt.Sprintf("%s\t%v", prefixedNames(f.Name), f.Usage))
}
func (f BoolTFlag) Apply(set *flag.FlagSet) {
val := true
if f.EnvVar != "" {
for _, envVar := range strings.Split(f.EnvVar, ",") {
envVar = strings.TrimSpace(envVar)
if envVal := os.Getenv(envVar); envVal != "" {
envValBool, err := strconv.ParseBool(envVal)
if err == nil {
val = envValBool
break
}
}
}
}
eachName(f.Name, func(name string) {
set.Bool(name, val, f.Usage)
})
}
func (f BoolTFlag) getName() string {
return f.Name
}
type StringFlag struct {
Name string
Value string
Usage string
EnvVar string
}
func (f StringFlag) String() string {
var fmtString string
fmtString = "%s %v\t%v"
if len(f.Value) > 0 {
fmtString = "%s \"%v\"\t%v"
} else {
fmtString = "%s %v\t%v"
}
return withEnvHint(f.EnvVar, fmt.Sprintf(fmtString, prefixedNames(f.Name), f.Value, f.Usage))
}
func (f StringFlag) Apply(set *flag.FlagSet) {
if f.EnvVar != "" {
for _, envVar := range strings.Split(f.EnvVar, ",") {
envVar = strings.TrimSpace(envVar)
if envVal := os.Getenv(envVar); envVal != "" {
f.Value = envVal
break
}
}
}
eachName(f.Name, func(name string) {
set.String(name, f.Value, f.Usage)
})
}
func (f StringFlag) getName() string {
return f.Name
}
type IntFlag struct {
Name string
Value int
Usage string
EnvVar string
}
func (f IntFlag) String() string {
return withEnvHint(f.EnvVar, fmt.Sprintf("%s \"%v\"\t%v", prefixedNames(f.Name), f.Value, f.Usage))
}
func (f IntFlag) Apply(set *flag.FlagSet) {
if f.EnvVar != "" {
for _, envVar := range strings.Split(f.EnvVar, ",") {
envVar = strings.TrimSpace(envVar)
if envVal := os.Getenv(envVar); envVal != "" {
envValInt, err := strconv.ParseInt(envVal, 0, 64)
if err == nil {
f.Value = int(envValInt)
break
}
}
}
}
eachName(f.Name, func(name string) {
set.Int(name, f.Value, f.Usage)
})
}
func (f IntFlag) getName() string {
return f.Name
}
type DurationFlag struct {
Name string
Value time.Duration
Usage string
EnvVar string
}
func (f DurationFlag) String() string {
return withEnvHint(f.EnvVar, fmt.Sprintf("%s \"%v\"\t%v", prefixedNames(f.Name), f.Value, f.Usage))
}
func (f DurationFlag) Apply(set *flag.FlagSet) {
if f.EnvVar != "" {
for _, envVar := range strings.Split(f.EnvVar, ",") {
envVar = strings.TrimSpace(envVar)
if envVal := os.Getenv(envVar); envVal != "" {
envValDuration, err := time.ParseDuration(envVal)
if err == nil {
f.Value = envValDuration
break
}
}
}
}
eachName(f.Name, func(name string) {
set.Duration(name, f.Value, f.Usage)
})
}
func (f DurationFlag) getName() string {
return f.Name
}
type Float64Flag struct {
Name string
Value float64
Usage string
EnvVar string
}
func (f Float64Flag) String() string {
return withEnvHint(f.EnvVar, fmt.Sprintf("%s \"%v\"\t%v", prefixedNames(f.Name), f.Value, f.Usage))
}
func (f Float64Flag) Apply(set *flag.FlagSet) {
if f.EnvVar != "" {
for _, envVar := range strings.Split(f.EnvVar, ",") {
envVar = strings.TrimSpace(envVar)
if envVal := os.Getenv(envVar); envVal != "" {
envValFloat, err := strconv.ParseFloat(envVal, 10)
if err == nil {
f.Value = float64(envValFloat)
}
}
}
}
eachName(f.Name, func(name string) {
set.Float64(name, f.Value, f.Usage)
})
}
func (f Float64Flag) getName() string {
return f.Name
}
func prefixFor(name string) (prefix string) {
if len(name) == 1 {
prefix = "-"
} else {
prefix = "--"
}
return
}
func prefixedNames(fullName string) (prefixed string) {
parts := strings.Split(fullName, ",")
for i, name := range parts {
name = strings.Trim(name, " ")
prefixed += prefixFor(name) + name
if i < len(parts)-1 {
prefixed += ", "
}
}
return
}
func withEnvHint(envVar, str string) string {
envText := ""
if envVar != "" {
envText = fmt.Sprintf(" [$%s]", strings.Join(strings.Split(envVar, ","), ", $"))
}
return str + envText
}

View File

@@ -1,742 +0,0 @@
package cli_test
import (
"fmt"
"os"
"reflect"
"strings"
"testing"
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/codegangsta/cli"
)
var boolFlagTests = []struct {
name string
expected string
}{
{"help", "--help\t"},
{"h", "-h\t"},
}
func TestBoolFlagHelpOutput(t *testing.T) {
for _, test := range boolFlagTests {
flag := cli.BoolFlag{Name: test.name}
output := flag.String()
if output != test.expected {
t.Errorf("%s does not match %s", output, test.expected)
}
}
}
var stringFlagTests = []struct {
name string
value string
expected string
}{
{"help", "", "--help \t"},
{"h", "", "-h \t"},
{"h", "", "-h \t"},
{"test", "Something", "--test \"Something\"\t"},
}
func TestStringFlagHelpOutput(t *testing.T) {
for _, test := range stringFlagTests {
flag := cli.StringFlag{Name: test.name, Value: test.value}
output := flag.String()
if output != test.expected {
t.Errorf("%s does not match %s", output, test.expected)
}
}
}
func TestStringFlagWithEnvVarHelpOutput(t *testing.T) {
os.Clearenv()
os.Setenv("APP_FOO", "derp")
for _, test := range stringFlagTests {
flag := cli.StringFlag{Name: test.name, Value: test.value, EnvVar: "APP_FOO"}
output := flag.String()
if !strings.HasSuffix(output, " [$APP_FOO]") {
t.Errorf("%s does not end with [$APP_FOO]", output)
}
}
}
var stringSliceFlagTests = []struct {
name string
value *cli.StringSlice
expected string
}{
{"help", func() *cli.StringSlice {
s := &cli.StringSlice{}
s.Set("")
return s
}(), "--help [--help option --help option]\t"},
{"h", func() *cli.StringSlice {
s := &cli.StringSlice{}
s.Set("")
return s
}(), "-h [-h option -h option]\t"},
{"h", func() *cli.StringSlice {
s := &cli.StringSlice{}
s.Set("")
return s
}(), "-h [-h option -h option]\t"},
{"test", func() *cli.StringSlice {
s := &cli.StringSlice{}
s.Set("Something")
return s
}(), "--test [--test option --test option]\t"},
}
func TestStringSliceFlagHelpOutput(t *testing.T) {
for _, test := range stringSliceFlagTests {
flag := cli.StringSliceFlag{Name: test.name, Value: test.value}
output := flag.String()
if output != test.expected {
t.Errorf("%q does not match %q", output, test.expected)
}
}
}
func TestStringSliceFlagWithEnvVarHelpOutput(t *testing.T) {
os.Clearenv()
os.Setenv("APP_QWWX", "11,4")
for _, test := range stringSliceFlagTests {
flag := cli.StringSliceFlag{Name: test.name, Value: test.value, EnvVar: "APP_QWWX"}
output := flag.String()
if !strings.HasSuffix(output, " [$APP_QWWX]") {
t.Errorf("%q does not end with [$APP_QWWX]", output)
}
}
}
var intFlagTests = []struct {
name string
expected string
}{
{"help", "--help \"0\"\t"},
{"h", "-h \"0\"\t"},
}
func TestIntFlagHelpOutput(t *testing.T) {
for _, test := range intFlagTests {
flag := cli.IntFlag{Name: test.name}
output := flag.String()
if output != test.expected {
t.Errorf("%s does not match %s", output, test.expected)
}
}
}
func TestIntFlagWithEnvVarHelpOutput(t *testing.T) {
os.Clearenv()
os.Setenv("APP_BAR", "2")
for _, test := range intFlagTests {
flag := cli.IntFlag{Name: test.name, EnvVar: "APP_BAR"}
output := flag.String()
if !strings.HasSuffix(output, " [$APP_BAR]") {
t.Errorf("%s does not end with [$APP_BAR]", output)
}
}
}
var durationFlagTests = []struct {
name string
expected string
}{
{"help", "--help \"0\"\t"},
{"h", "-h \"0\"\t"},
}
func TestDurationFlagHelpOutput(t *testing.T) {
for _, test := range durationFlagTests {
flag := cli.DurationFlag{Name: test.name}
output := flag.String()
if output != test.expected {
t.Errorf("%s does not match %s", output, test.expected)
}
}
}
func TestDurationFlagWithEnvVarHelpOutput(t *testing.T) {
os.Clearenv()
os.Setenv("APP_BAR", "2h3m6s")
for _, test := range durationFlagTests {
flag := cli.DurationFlag{Name: test.name, EnvVar: "APP_BAR"}
output := flag.String()
if !strings.HasSuffix(output, " [$APP_BAR]") {
t.Errorf("%s does not end with [$APP_BAR]", output)
}
}
}
var intSliceFlagTests = []struct {
name string
value *cli.IntSlice
expected string
}{
{"help", &cli.IntSlice{}, "--help [--help option --help option]\t"},
{"h", &cli.IntSlice{}, "-h [-h option -h option]\t"},
{"h", &cli.IntSlice{}, "-h [-h option -h option]\t"},
{"test", func() *cli.IntSlice {
i := &cli.IntSlice{}
i.Set("9")
return i
}(), "--test [--test option --test option]\t"},
}
func TestIntSliceFlagHelpOutput(t *testing.T) {
for _, test := range intSliceFlagTests {
flag := cli.IntSliceFlag{Name: test.name, Value: test.value}
output := flag.String()
if output != test.expected {
t.Errorf("%q does not match %q", output, test.expected)
}
}
}
func TestIntSliceFlagWithEnvVarHelpOutput(t *testing.T) {
os.Clearenv()
os.Setenv("APP_SMURF", "42,3")
for _, test := range intSliceFlagTests {
flag := cli.IntSliceFlag{Name: test.name, Value: test.value, EnvVar: "APP_SMURF"}
output := flag.String()
if !strings.HasSuffix(output, " [$APP_SMURF]") {
t.Errorf("%q does not end with [$APP_SMURF]", output)
}
}
}
var float64FlagTests = []struct {
name string
expected string
}{
{"help", "--help \"0\"\t"},
{"h", "-h \"0\"\t"},
}
func TestFloat64FlagHelpOutput(t *testing.T) {
for _, test := range float64FlagTests {
flag := cli.Float64Flag{Name: test.name}
output := flag.String()
if output != test.expected {
t.Errorf("%s does not match %s", output, test.expected)
}
}
}
func TestFloat64FlagWithEnvVarHelpOutput(t *testing.T) {
os.Clearenv()
os.Setenv("APP_BAZ", "99.4")
for _, test := range float64FlagTests {
flag := cli.Float64Flag{Name: test.name, EnvVar: "APP_BAZ"}
output := flag.String()
if !strings.HasSuffix(output, " [$APP_BAZ]") {
t.Errorf("%s does not end with [$APP_BAZ]", output)
}
}
}
var genericFlagTests = []struct {
name string
value cli.Generic
expected string
}{
{"test", &Parser{"abc", "def"}, "--test \"abc,def\"\ttest flag"},
{"t", &Parser{"abc", "def"}, "-t \"abc,def\"\ttest flag"},
}
func TestGenericFlagHelpOutput(t *testing.T) {
for _, test := range genericFlagTests {
flag := cli.GenericFlag{Name: test.name, Value: test.value, Usage: "test flag"}
output := flag.String()
if output != test.expected {
t.Errorf("%q does not match %q", output, test.expected)
}
}
}
func TestGenericFlagWithEnvVarHelpOutput(t *testing.T) {
os.Clearenv()
os.Setenv("APP_ZAP", "3")
for _, test := range genericFlagTests {
flag := cli.GenericFlag{Name: test.name, EnvVar: "APP_ZAP"}
output := flag.String()
if !strings.HasSuffix(output, " [$APP_ZAP]") {
t.Errorf("%s does not end with [$APP_ZAP]", output)
}
}
}
func TestParseMultiString(t *testing.T) {
(&cli.App{
Flags: []cli.Flag{
cli.StringFlag{Name: "serve, s"},
},
Action: func(ctx *cli.Context) {
if ctx.String("serve") != "10" {
t.Errorf("main name not set")
}
if ctx.String("s") != "10" {
t.Errorf("short name not set")
}
},
}).Run([]string{"run", "-s", "10"})
}
func TestParseMultiStringFromEnv(t *testing.T) {
os.Clearenv()
os.Setenv("APP_COUNT", "20")
(&cli.App{
Flags: []cli.Flag{
cli.StringFlag{Name: "count, c", EnvVar: "APP_COUNT"},
},
Action: func(ctx *cli.Context) {
if ctx.String("count") != "20" {
t.Errorf("main name not set")
}
if ctx.String("c") != "20" {
t.Errorf("short name not set")
}
},
}).Run([]string{"run"})
}
func TestParseMultiStringFromEnvCascade(t *testing.T) {
os.Clearenv()
os.Setenv("APP_COUNT", "20")
(&cli.App{
Flags: []cli.Flag{
cli.StringFlag{Name: "count, c", EnvVar: "COMPAT_COUNT,APP_COUNT"},
},
Action: func(ctx *cli.Context) {
if ctx.String("count") != "20" {
t.Errorf("main name not set")
}
if ctx.String("c") != "20" {
t.Errorf("short name not set")
}
},
}).Run([]string{"run"})
}
func TestParseMultiStringSlice(t *testing.T) {
(&cli.App{
Flags: []cli.Flag{
cli.StringSliceFlag{Name: "serve, s", Value: &cli.StringSlice{}},
},
Action: func(ctx *cli.Context) {
if !reflect.DeepEqual(ctx.StringSlice("serve"), []string{"10", "20"}) {
t.Errorf("main name not set")
}
if !reflect.DeepEqual(ctx.StringSlice("s"), []string{"10", "20"}) {
t.Errorf("short name not set")
}
},
}).Run([]string{"run", "-s", "10", "-s", "20"})
}
func TestParseMultiStringSliceFromEnv(t *testing.T) {
os.Clearenv()
os.Setenv("APP_INTERVALS", "20,30,40")
(&cli.App{
Flags: []cli.Flag{
cli.StringSliceFlag{Name: "intervals, i", Value: &cli.StringSlice{}, EnvVar: "APP_INTERVALS"},
},
Action: func(ctx *cli.Context) {
if !reflect.DeepEqual(ctx.StringSlice("intervals"), []string{"20", "30", "40"}) {
t.Errorf("main name not set from env")
}
if !reflect.DeepEqual(ctx.StringSlice("i"), []string{"20", "30", "40"}) {
t.Errorf("short name not set from env")
}
},
}).Run([]string{"run"})
}
func TestParseMultiStringSliceFromEnvCascade(t *testing.T) {
os.Clearenv()
os.Setenv("APP_INTERVALS", "20,30,40")
(&cli.App{
Flags: []cli.Flag{
cli.StringSliceFlag{Name: "intervals, i", Value: &cli.StringSlice{}, EnvVar: "COMPAT_INTERVALS,APP_INTERVALS"},
},
Action: func(ctx *cli.Context) {
if !reflect.DeepEqual(ctx.StringSlice("intervals"), []string{"20", "30", "40"}) {
t.Errorf("main name not set from env")
}
if !reflect.DeepEqual(ctx.StringSlice("i"), []string{"20", "30", "40"}) {
t.Errorf("short name not set from env")
}
},
}).Run([]string{"run"})
}
func TestParseMultiInt(t *testing.T) {
a := cli.App{
Flags: []cli.Flag{
cli.IntFlag{Name: "serve, s"},
},
Action: func(ctx *cli.Context) {
if ctx.Int("serve") != 10 {
t.Errorf("main name not set")
}
if ctx.Int("s") != 10 {
t.Errorf("short name not set")
}
},
}
a.Run([]string{"run", "-s", "10"})
}
func TestParseMultiIntFromEnv(t *testing.T) {
os.Clearenv()
os.Setenv("APP_TIMEOUT_SECONDS", "10")
a := cli.App{
Flags: []cli.Flag{
cli.IntFlag{Name: "timeout, t", EnvVar: "APP_TIMEOUT_SECONDS"},
},
Action: func(ctx *cli.Context) {
if ctx.Int("timeout") != 10 {
t.Errorf("main name not set")
}
if ctx.Int("t") != 10 {
t.Errorf("short name not set")
}
},
}
a.Run([]string{"run"})
}
func TestParseMultiIntFromEnvCascade(t *testing.T) {
os.Clearenv()
os.Setenv("APP_TIMEOUT_SECONDS", "10")
a := cli.App{
Flags: []cli.Flag{
cli.IntFlag{Name: "timeout, t", EnvVar: "COMPAT_TIMEOUT_SECONDS,APP_TIMEOUT_SECONDS"},
},
Action: func(ctx *cli.Context) {
if ctx.Int("timeout") != 10 {
t.Errorf("main name not set")
}
if ctx.Int("t") != 10 {
t.Errorf("short name not set")
}
},
}
a.Run([]string{"run"})
}
func TestParseMultiIntSlice(t *testing.T) {
(&cli.App{
Flags: []cli.Flag{
cli.IntSliceFlag{Name: "serve, s", Value: &cli.IntSlice{}},
},
Action: func(ctx *cli.Context) {
if !reflect.DeepEqual(ctx.IntSlice("serve"), []int{10, 20}) {
t.Errorf("main name not set")
}
if !reflect.DeepEqual(ctx.IntSlice("s"), []int{10, 20}) {
t.Errorf("short name not set")
}
},
}).Run([]string{"run", "-s", "10", "-s", "20"})
}
func TestParseMultiIntSliceFromEnv(t *testing.T) {
os.Clearenv()
os.Setenv("APP_INTERVALS", "20,30,40")
(&cli.App{
Flags: []cli.Flag{
cli.IntSliceFlag{Name: "intervals, i", Value: &cli.IntSlice{}, EnvVar: "APP_INTERVALS"},
},
Action: func(ctx *cli.Context) {
if !reflect.DeepEqual(ctx.IntSlice("intervals"), []int{20, 30, 40}) {
t.Errorf("main name not set from env")
}
if !reflect.DeepEqual(ctx.IntSlice("i"), []int{20, 30, 40}) {
t.Errorf("short name not set from env")
}
},
}).Run([]string{"run"})
}
func TestParseMultiIntSliceFromEnvCascade(t *testing.T) {
os.Clearenv()
os.Setenv("APP_INTERVALS", "20,30,40")
(&cli.App{
Flags: []cli.Flag{
cli.IntSliceFlag{Name: "intervals, i", Value: &cli.IntSlice{}, EnvVar: "COMPAT_INTERVALS,APP_INTERVALS"},
},
Action: func(ctx *cli.Context) {
if !reflect.DeepEqual(ctx.IntSlice("intervals"), []int{20, 30, 40}) {
t.Errorf("main name not set from env")
}
if !reflect.DeepEqual(ctx.IntSlice("i"), []int{20, 30, 40}) {
t.Errorf("short name not set from env")
}
},
}).Run([]string{"run"})
}
func TestParseMultiFloat64(t *testing.T) {
a := cli.App{
Flags: []cli.Flag{
cli.Float64Flag{Name: "serve, s"},
},
Action: func(ctx *cli.Context) {
if ctx.Float64("serve") != 10.2 {
t.Errorf("main name not set")
}
if ctx.Float64("s") != 10.2 {
t.Errorf("short name not set")
}
},
}
a.Run([]string{"run", "-s", "10.2"})
}
func TestParseMultiFloat64FromEnv(t *testing.T) {
os.Clearenv()
os.Setenv("APP_TIMEOUT_SECONDS", "15.5")
a := cli.App{
Flags: []cli.Flag{
cli.Float64Flag{Name: "timeout, t", EnvVar: "APP_TIMEOUT_SECONDS"},
},
Action: func(ctx *cli.Context) {
if ctx.Float64("timeout") != 15.5 {
t.Errorf("main name not set")
}
if ctx.Float64("t") != 15.5 {
t.Errorf("short name not set")
}
},
}
a.Run([]string{"run"})
}
func TestParseMultiFloat64FromEnvCascade(t *testing.T) {
os.Clearenv()
os.Setenv("APP_TIMEOUT_SECONDS", "15.5")
a := cli.App{
Flags: []cli.Flag{
cli.Float64Flag{Name: "timeout, t", EnvVar: "COMPAT_TIMEOUT_SECONDS,APP_TIMEOUT_SECONDS"},
},
Action: func(ctx *cli.Context) {
if ctx.Float64("timeout") != 15.5 {
t.Errorf("main name not set")
}
if ctx.Float64("t") != 15.5 {
t.Errorf("short name not set")
}
},
}
a.Run([]string{"run"})
}
func TestParseMultiBool(t *testing.T) {
a := cli.App{
Flags: []cli.Flag{
cli.BoolFlag{Name: "serve, s"},
},
Action: func(ctx *cli.Context) {
if ctx.Bool("serve") != true {
t.Errorf("main name not set")
}
if ctx.Bool("s") != true {
t.Errorf("short name not set")
}
},
}
a.Run([]string{"run", "--serve"})
}
func TestParseMultiBoolFromEnv(t *testing.T) {
os.Clearenv()
os.Setenv("APP_DEBUG", "1")
a := cli.App{
Flags: []cli.Flag{
cli.BoolFlag{Name: "debug, d", EnvVar: "APP_DEBUG"},
},
Action: func(ctx *cli.Context) {
if ctx.Bool("debug") != true {
t.Errorf("main name not set from env")
}
if ctx.Bool("d") != true {
t.Errorf("short name not set from env")
}
},
}
a.Run([]string{"run"})
}
func TestParseMultiBoolFromEnvCascade(t *testing.T) {
os.Clearenv()
os.Setenv("APP_DEBUG", "1")
a := cli.App{
Flags: []cli.Flag{
cli.BoolFlag{Name: "debug, d", EnvVar: "COMPAT_DEBUG,APP_DEBUG"},
},
Action: func(ctx *cli.Context) {
if ctx.Bool("debug") != true {
t.Errorf("main name not set from env")
}
if ctx.Bool("d") != true {
t.Errorf("short name not set from env")
}
},
}
a.Run([]string{"run"})
}
func TestParseMultiBoolT(t *testing.T) {
a := cli.App{
Flags: []cli.Flag{
cli.BoolTFlag{Name: "serve, s"},
},
Action: func(ctx *cli.Context) {
if ctx.BoolT("serve") != true {
t.Errorf("main name not set")
}
if ctx.BoolT("s") != true {
t.Errorf("short name not set")
}
},
}
a.Run([]string{"run", "--serve"})
}
func TestParseMultiBoolTFromEnv(t *testing.T) {
os.Clearenv()
os.Setenv("APP_DEBUG", "0")
a := cli.App{
Flags: []cli.Flag{
cli.BoolTFlag{Name: "debug, d", EnvVar: "APP_DEBUG"},
},
Action: func(ctx *cli.Context) {
if ctx.BoolT("debug") != false {
t.Errorf("main name not set from env")
}
if ctx.BoolT("d") != false {
t.Errorf("short name not set from env")
}
},
}
a.Run([]string{"run"})
}
func TestParseMultiBoolTFromEnvCascade(t *testing.T) {
os.Clearenv()
os.Setenv("APP_DEBUG", "0")
a := cli.App{
Flags: []cli.Flag{
cli.BoolTFlag{Name: "debug, d", EnvVar: "COMPAT_DEBUG,APP_DEBUG"},
},
Action: func(ctx *cli.Context) {
if ctx.BoolT("debug") != false {
t.Errorf("main name not set from env")
}
if ctx.BoolT("d") != false {
t.Errorf("short name not set from env")
}
},
}
a.Run([]string{"run"})
}
type Parser [2]string
func (p *Parser) Set(value string) error {
parts := strings.Split(value, ",")
if len(parts) != 2 {
return fmt.Errorf("invalid format")
}
(*p)[0] = parts[0]
(*p)[1] = parts[1]
return nil
}
func (p *Parser) String() string {
return fmt.Sprintf("%s,%s", p[0], p[1])
}
func TestParseGeneric(t *testing.T) {
a := cli.App{
Flags: []cli.Flag{
cli.GenericFlag{Name: "serve, s", Value: &Parser{}},
},
Action: func(ctx *cli.Context) {
if !reflect.DeepEqual(ctx.Generic("serve"), &Parser{"10", "20"}) {
t.Errorf("main name not set")
}
if !reflect.DeepEqual(ctx.Generic("s"), &Parser{"10", "20"}) {
t.Errorf("short name not set")
}
},
}
a.Run([]string{"run", "-s", "10,20"})
}
func TestParseGenericFromEnv(t *testing.T) {
os.Clearenv()
os.Setenv("APP_SERVE", "20,30")
a := cli.App{
Flags: []cli.Flag{
cli.GenericFlag{Name: "serve, s", Value: &Parser{}, EnvVar: "APP_SERVE"},
},
Action: func(ctx *cli.Context) {
if !reflect.DeepEqual(ctx.Generic("serve"), &Parser{"20", "30"}) {
t.Errorf("main name not set from env")
}
if !reflect.DeepEqual(ctx.Generic("s"), &Parser{"20", "30"}) {
t.Errorf("short name not set from env")
}
},
}
a.Run([]string{"run"})
}
func TestParseGenericFromEnvCascade(t *testing.T) {
os.Clearenv()
os.Setenv("APP_FOO", "99,2000")
a := cli.App{
Flags: []cli.Flag{
cli.GenericFlag{Name: "foos", Value: &Parser{}, EnvVar: "COMPAT_FOO,APP_FOO"},
},
Action: func(ctx *cli.Context) {
if !reflect.DeepEqual(ctx.Generic("foos"), &Parser{"99", "2000"}) {
t.Errorf("value not set from env")
}
},
}
a.Run([]string{"run"})
}

View File

@@ -1,235 +0,0 @@
package cli
import (
"fmt"
"io"
"strings"
"text/tabwriter"
"text/template"
)
// The text template for the Default help topic.
// cli.go uses text/template to render templates. You can
// render custom help text by setting this variable.
var AppHelpTemplate = `NAME:
{{.Name}} - {{.Usage}}
USAGE:
{{.Name}} {{if .Flags}}[global options] {{end}}command{{if .Flags}} [command options]{{end}} [arguments...]
VERSION:
{{.Version}}{{if len .Authors}}
AUTHOR(S):
{{range .Authors}}{{ . }}{{end}}{{end}}
COMMANDS:
{{range .Commands}}{{join .Names ", "}}{{ "\t" }}{{.Usage}}
{{end}}{{if .Flags}}
GLOBAL OPTIONS:
{{range .Flags}}{{.}}
{{end}}{{end}}
`
// The text template for the command help topic.
// cli.go uses text/template to render templates. You can
// render custom help text by setting this variable.
var CommandHelpTemplate = `NAME:
{{.Name}} - {{.Usage}}
USAGE:
command {{.Name}}{{if .Flags}} [command options]{{end}} [arguments...]{{if .Description}}
DESCRIPTION:
{{.Description}}{{end}}{{if .Flags}}
OPTIONS:
{{range .Flags}}{{.}}
{{end}}{{ end }}
`
// The text template for the subcommand help topic.
// cli.go uses text/template to render templates. You can
// render custom help text by setting this variable.
var SubcommandHelpTemplate = `NAME:
{{.Name}} - {{.Usage}}
USAGE:
{{.Name}} command{{if .Flags}} [command options]{{end}} [arguments...]
COMMANDS:
{{range .Commands}}{{join .Names ", "}}{{ "\t" }}{{.Usage}}
{{end}}{{if .Flags}}
OPTIONS:
{{range .Flags}}{{.}}
{{end}}{{end}}
`
var helpCommand = Command{
Name: "help",
Aliases: []string{"h"},
Usage: "Shows a list of commands or help for one command",
Action: func(c *Context) {
args := c.Args()
if args.Present() {
ShowCommandHelp(c, args.First())
} else {
ShowAppHelp(c)
}
},
}
var helpSubcommand = Command{
Name: "help",
Aliases: []string{"h"},
Usage: "Shows a list of commands or help for one command",
Action: func(c *Context) {
args := c.Args()
if args.Present() {
ShowCommandHelp(c, args.First())
} else {
ShowSubcommandHelp(c)
}
},
}
// Prints help for the App or Command
type helpPrinter func(w io.Writer, templ string, data interface{})
var HelpPrinter helpPrinter = printHelp
// Prints version for the App
var VersionPrinter = printVersion
func ShowAppHelp(c *Context) {
HelpPrinter(c.App.Writer, AppHelpTemplate, c.App)
}
// Prints the list of subcommands as the default app completion method
func DefaultAppComplete(c *Context) {
for _, command := range c.App.Commands {
for _, name := range command.Names() {
fmt.Fprintln(c.App.Writer, name)
}
}
}
// Prints help for the given command
func ShowCommandHelp(ctx *Context, command string) {
// show the subcommand help for a command with subcommands
if command == "" {
HelpPrinter(ctx.App.Writer, SubcommandHelpTemplate, ctx.App)
return
}
for _, c := range ctx.App.Commands {
if c.HasName(command) {
HelpPrinter(ctx.App.Writer, CommandHelpTemplate, c)
return
}
}
if ctx.App.CommandNotFound != nil {
ctx.App.CommandNotFound(ctx, command)
} else {
fmt.Fprintf(ctx.App.Writer, "No help topic for '%v'\n", command)
}
}
// Prints help for the given subcommand
func ShowSubcommandHelp(c *Context) {
ShowCommandHelp(c, c.Command.Name)
}
// Prints the version number of the App
func ShowVersion(c *Context) {
VersionPrinter(c)
}
func printVersion(c *Context) {
fmt.Fprintf(c.App.Writer, "%v version %v\n", c.App.Name, c.App.Version)
}
// Prints the lists of commands within a given context
func ShowCompletions(c *Context) {
a := c.App
if a != nil && a.BashComplete != nil {
a.BashComplete(c)
}
}
// Prints the custom completions for a given command
func ShowCommandCompletions(ctx *Context, command string) {
c := ctx.App.Command(command)
if c != nil && c.BashComplete != nil {
c.BashComplete(ctx)
}
}
func printHelp(out io.Writer, templ string, data interface{}) {
funcMap := template.FuncMap{
"join": strings.Join,
}
w := tabwriter.NewWriter(out, 0, 8, 1, '\t', 0)
t := template.Must(template.New("help").Funcs(funcMap).Parse(templ))
err := t.Execute(w, data)
if err != nil {
panic(err)
}
w.Flush()
}
func checkVersion(c *Context) bool {
if c.GlobalBool("version") {
ShowVersion(c)
return true
}
return false
}
func checkHelp(c *Context) bool {
if c.GlobalBool("h") || c.GlobalBool("help") {
ShowAppHelp(c)
return true
}
return false
}
func checkCommandHelp(c *Context, name string) bool {
if c.Bool("h") || c.Bool("help") {
ShowCommandHelp(c, name)
return true
}
return false
}
func checkSubcommandHelp(c *Context) bool {
if c.GlobalBool("h") || c.GlobalBool("help") {
ShowSubcommandHelp(c)
return true
}
return false
}
func checkCompletions(c *Context) bool {
if (c.GlobalBool(BashCompletionFlag.Name) || c.Bool(BashCompletionFlag.Name)) && c.App.EnableBashCompletion {
ShowCompletions(c)
return true
}
return false
}
func checkCommandCompletions(c *Context, name string) bool {
if c.Bool(BashCompletionFlag.Name) && c.App.EnableBashCompletion {
ShowCommandCompletions(c, name)
return true
}
return false
}

View File

@@ -1,22 +0,0 @@
package cli_test
import (
"bytes"
"testing"
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/codegangsta/cli"
)
func Test_ShowAppHelp_NoAuthor(t *testing.T) {
output := new(bytes.Buffer)
app := cli.NewApp()
app.Writer = output
c := cli.NewContext(app, nil, nil)
cli.ShowAppHelp(c)
if bytes.Index(output.Bytes(), []byte("AUTHOR(S):")) != -1 {
t.Errorf("expected\n%snot to include %s", output.String(), "AUTHOR(S):")
}
}

View File

@@ -1,19 +0,0 @@
package cli_test
import (
"reflect"
"testing"
)
/* Test Helpers */
func expect(t *testing.T, a interface{}, b interface{}) {
if a != b {
t.Errorf("Expected %v (type %v) - Got %v (type %v)", b, reflect.TypeOf(b), a, reflect.TypeOf(a))
}
}
func refute(t *testing.T, a interface{}, b interface{}) {
if a == b {
t.Errorf("Did not expect %v (type %v) - Got %v (type %v)", b, reflect.TypeOf(b), a, reflect.TypeOf(a))
}
}

View File

@@ -1,22 +0,0 @@
# Compiled Object files, Static and Dynamic libs (Shared Objects)
*.o
*.a
*.so
# Folders
_obj
_test
# Architecture specific extensions/prefixes
*.[568vq]
[568vq].out
*.cgo1.go
*.cgo2.c
_cgo_defun.c
_cgo_gotypes.go
_cgo_export.*
_testmain.go
*.exe

View File

@@ -1,6 +0,0 @@
language: go
go:
- 1.1
- 1.2
- tip

View File

@@ -1,8 +0,0 @@
# This is the official list of Gorilla WebSocket authors for copyright
# purposes.
#
# Please keep the list sorted.
Gary Burd <gary@beagledreams.com>
Joachim Bauch <mail@joachim-bauch.de>

View File

@@ -1,22 +0,0 @@
Copyright (c) 2013 The Gorilla WebSocket Authors. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:
Redistributions of source code must retain the above copyright notice, this
list of conditions and the following disclaimer.
Redistributions in binary form must reproduce the above copyright notice,
this list of conditions and the following disclaimer in the documentation
and/or other materials provided with the distribution.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

View File

@@ -1,59 +0,0 @@
# Gorilla WebSocket
Gorilla WebSocket is a [Go](http://golang.org/) implementation of the
[WebSocket](http://www.rfc-editor.org/rfc/rfc6455.txt) protocol.
### Documentation
* [API Reference](http://godoc.org/github.com/gorilla/websocket)
* [Chat example](https://github.com/gorilla/websocket/tree/master/examples/chat)
* [File watch example](https://github.com/gorilla/websocket/tree/master/examples/filewatch)
### Status
The Gorilla WebSocket package provides a complete and tested implementation of
the [WebSocket](http://www.rfc-editor.org/rfc/rfc6455.txt) protocol. The
package API is stable.
### Installation
go get github.com/gorilla/websocket
### Protocol Compliance
The Gorilla WebSocket package passes the server tests in the [Autobahn Test
Suite](http://autobahn.ws/testsuite) using the application in the [examples/autobahn
subdirectory](https://github.com/gorilla/websocket/tree/master/examples/autobahn).
### Gorilla WebSocket compared with other packages
<table>
<tr>
<th></th>
<th><a href="http://godoc.org/github.com/gorilla/websocket">github.com/gorilla</a></th>
<th><a href="http://godoc.org/golang.org/x/net/websocket">golang.org/x/net</a></th>
</tr>
<tr>
<tr><td colspan="3"><a href="http://tools.ietf.org/html/rfc6455">RFC 6455</a> Features</td></tr>
<tr><td>Passes <a href="http://autobahn.ws/testsuite/">Autobahn Test Suite</a></td><td><a href="https://github.com/gorilla/websocket/tree/master/examples/autobahn">Yes</a></td><td>No</td></tr>
<tr><td>Receive <a href="https://tools.ietf.org/html/rfc6455#section-5.4">fragmented</a> message<td>Yes</td><td><a href="https://code.google.com/p/go/issues/detail?id=7632">No</a>, see note 1</td></tr>
<tr><td>Send <a href="https://tools.ietf.org/html/rfc6455#section-5.5.1">close</a> message</td><td><a href="http://godoc.org/github.com/gorilla/websocket#hdr-Control_Messages">Yes</a></td><td><a href="https://code.google.com/p/go/issues/detail?id=4588">No</a></td></tr>
<tr><td>Send <a href="https://tools.ietf.org/html/rfc6455#section-5.5.2">pings</a> and receive <a href="https://tools.ietf.org/html/rfc6455#section-5.5.3">pongs</a></td><td><a href="http://godoc.org/github.com/gorilla/websocket#hdr-Control_Messages">Yes</a></td><td>No</td></tr>
<tr><td>Get the <a href="https://tools.ietf.org/html/rfc6455#section-5.6">type</a> of a received data message</td><td>Yes</td><td>Yes, see note 2</td></tr>
<tr><td colspan="3">Other Features</tr></td>
<tr><td>Limit size of received message</td><td><a href="http://godoc.org/github.com/gorilla/websocket#Conn.SetReadLimit">Yes</a></td><td><a href="https://code.google.com/p/go/issues/detail?id=5082">No</a></td></tr>
<tr><td>Read message using io.Reader</td><td><a href="http://godoc.org/github.com/gorilla/websocket#Conn.NextReader">Yes</a></td><td>No, see note 3</td></tr>
<tr><td>Write message using io.WriteCloser</td><td><a href="http://godoc.org/github.com/gorilla/websocket#Conn.NextWriter">Yes</a></td><td>No, see note 3</td></tr>
</table>
Notes:
1. Large messages are fragmented in [Chrome's new WebSocket implementation](http://www.ietf.org/mail-archive/web/hybi/current/msg10503.html).
2. The application can get the type of a received data message by implementing
a [Codec marshal](http://godoc.org/golang.org/x/net/websocket#Codec.Marshal)
function.
3. The go.net io.Reader and io.Writer operate across WebSocket frame boundaries.
Read returns when the input buffer is full or a frame boundary is
encountered. Each call to Write sends a single frame message. The Gorilla
io.Reader and io.WriteCloser operate on a single WebSocket message.

View File

@@ -1,19 +0,0 @@
// Copyright 2014 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package websocket
import (
"testing"
)
func BenchmarkMaskBytes(b *testing.B) {
var key [4]byte
data := make([]byte, 1024)
pos := 0
for i := 0; i < b.N; i++ {
pos = maskBytes(key, pos, data)
}
b.SetBytes(int64(len(data)))
}

View File

@@ -1,235 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package websocket
import (
"crypto/tls"
"errors"
"net"
"net/http"
"net/url"
"strings"
"time"
)
// ErrBadHandshake is returned when the server response to opening handshake is
// invalid.
var ErrBadHandshake = errors.New("websocket: bad handshake")
// NewClient creates a new client connection using the given net connection.
// The URL u specifies the host and request URI. Use requestHeader to specify
// the origin (Origin), subprotocols (Sec-WebSocket-Protocol) and cookies
// (Cookie). Use the response.Header to get the selected subprotocol
// (Sec-WebSocket-Protocol) and cookies (Set-Cookie).
//
// If the WebSocket handshake fails, ErrBadHandshake is returned along with a
// non-nil *http.Response so that callers can handle redirects, authentication,
// etc.
func NewClient(netConn net.Conn, u *url.URL, requestHeader http.Header, readBufSize, writeBufSize int) (c *Conn, response *http.Response, err error) {
challengeKey, err := generateChallengeKey()
if err != nil {
return nil, nil, err
}
acceptKey := computeAcceptKey(challengeKey)
c = newConn(netConn, false, readBufSize, writeBufSize)
p := c.writeBuf[:0]
p = append(p, "GET "...)
p = append(p, u.RequestURI()...)
p = append(p, " HTTP/1.1\r\nHost: "...)
p = append(p, u.Host...)
// "Upgrade" is capitalized for servers that do not use case insensitive
// comparisons on header tokens.
p = append(p, "\r\nUpgrade: websocket\r\nConnection: Upgrade\r\nSec-WebSocket-Version: 13\r\nSec-WebSocket-Key: "...)
p = append(p, challengeKey...)
p = append(p, "\r\n"...)
for k, vs := range requestHeader {
for _, v := range vs {
p = append(p, k...)
p = append(p, ": "...)
p = append(p, v...)
p = append(p, "\r\n"...)
}
}
p = append(p, "\r\n"...)
if _, err := netConn.Write(p); err != nil {
return nil, nil, err
}
resp, err := http.ReadResponse(c.br, &http.Request{Method: "GET", URL: u})
if err != nil {
return nil, nil, err
}
if resp.StatusCode != 101 ||
!strings.EqualFold(resp.Header.Get("Upgrade"), "websocket") ||
!strings.EqualFold(resp.Header.Get("Connection"), "upgrade") ||
resp.Header.Get("Sec-Websocket-Accept") != acceptKey {
return nil, resp, ErrBadHandshake
}
c.subprotocol = resp.Header.Get("Sec-Websocket-Protocol")
return c, resp, nil
}
// A Dialer contains options for connecting to WebSocket server.
type Dialer struct {
// NetDial specifies the dial function for creating TCP connections. If
// NetDial is nil, net.Dial is used.
NetDial func(network, addr string) (net.Conn, error)
// TLSClientConfig specifies the TLS configuration to use with tls.Client.
// If nil, the default configuration is used.
TLSClientConfig *tls.Config
// HandshakeTimeout specifies the duration for the handshake to complete.
HandshakeTimeout time.Duration
// Input and output buffer sizes. If the buffer size is zero, then a
// default value of 4096 is used.
ReadBufferSize, WriteBufferSize int
// Subprotocols specifies the client's requested subprotocols.
Subprotocols []string
}
var errMalformedURL = errors.New("malformed ws or wss URL")
// parseURL parses the URL. The url.Parse function is not used here because
// url.Parse mangles the path.
func parseURL(s string) (*url.URL, error) {
// From the RFC:
//
// ws-URI = "ws:" "//" host [ ":" port ] path [ "?" query ]
// wss-URI = "wss:" "//" host [ ":" port ] path [ "?" query ]
//
// We don't use the net/url parser here because the dialer interface does
// not provide a way for applications to work around percent deocding in
// the net/url parser.
var u url.URL
switch {
case strings.HasPrefix(s, "ws://"):
u.Scheme = "ws"
s = s[len("ws://"):]
case strings.HasPrefix(s, "wss://"):
u.Scheme = "wss"
s = s[len("wss://"):]
default:
return nil, errMalformedURL
}
u.Host = s
u.Opaque = "/"
if i := strings.Index(s, "/"); i >= 0 {
u.Host = s[:i]
u.Opaque = s[i:]
}
return &u, nil
}
func hostPortNoPort(u *url.URL) (hostPort, hostNoPort string) {
hostPort = u.Host
hostNoPort = u.Host
if i := strings.LastIndex(u.Host, ":"); i > strings.LastIndex(u.Host, "]") {
hostNoPort = hostNoPort[:i]
} else {
if u.Scheme == "wss" {
hostPort += ":443"
} else {
hostPort += ":80"
}
}
return hostPort, hostNoPort
}
// DefaultDialer is a dialer with all fields set to the default zero values.
var DefaultDialer *Dialer
// Dial creates a new client connection. Use requestHeader to specify the
// origin (Origin), subprotocols (Sec-WebSocket-Protocol) and cookies (Cookie).
// Use the response.Header to get the selected subprotocol
// (Sec-WebSocket-Protocol) and cookies (Set-Cookie).
//
// If the WebSocket handshake fails, ErrBadHandshake is returned along with a
// non-nil *http.Response so that callers can handle redirects, authentication,
// etc.
func (d *Dialer) Dial(urlStr string, requestHeader http.Header) (*Conn, *http.Response, error) {
u, err := parseURL(urlStr)
if err != nil {
return nil, nil, err
}
hostPort, hostNoPort := hostPortNoPort(u)
if d == nil {
d = &Dialer{}
}
var deadline time.Time
if d.HandshakeTimeout != 0 {
deadline = time.Now().Add(d.HandshakeTimeout)
}
netDial := d.NetDial
if netDial == nil {
netDialer := &net.Dialer{Deadline: deadline}
netDial = netDialer.Dial
}
netConn, err := netDial("tcp", hostPort)
if err != nil {
return nil, nil, err
}
defer func() {
if netConn != nil {
netConn.Close()
}
}()
if err := netConn.SetDeadline(deadline); err != nil {
return nil, nil, err
}
if u.Scheme == "wss" {
cfg := d.TLSClientConfig
if cfg == nil {
cfg = &tls.Config{ServerName: hostNoPort}
} else if cfg.ServerName == "" {
shallowCopy := *cfg
cfg = &shallowCopy
cfg.ServerName = hostNoPort
}
tlsConn := tls.Client(netConn, cfg)
netConn = tlsConn
if err := tlsConn.Handshake(); err != nil {
return nil, nil, err
}
if !cfg.InsecureSkipVerify {
if err := tlsConn.VerifyHostname(cfg.ServerName); err != nil {
return nil, nil, err
}
}
}
if len(d.Subprotocols) > 0 {
h := http.Header{}
for k, v := range requestHeader {
h[k] = v
}
h.Set("Sec-Websocket-Protocol", strings.Join(d.Subprotocols, ", "))
requestHeader = h
}
conn, resp, err := NewClient(netConn, u, requestHeader, d.ReadBufferSize, d.WriteBufferSize)
if err != nil {
return nil, resp, err
}
netConn.SetDeadline(time.Time{})
netConn = nil // to avoid close in defer.
return conn, resp, nil
}

View File

@@ -1,249 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package websocket
import (
"crypto/tls"
"crypto/x509"
"io"
"net"
"net/http"
"net/http/httptest"
"net/url"
"reflect"
"testing"
"time"
)
var cstUpgrader = Upgrader{
Subprotocols: []string{"p0", "p1"},
ReadBufferSize: 1024,
WriteBufferSize: 1024,
Error: func(w http.ResponseWriter, r *http.Request, status int, reason error) {
http.Error(w, reason.Error(), status)
},
}
var cstDialer = Dialer{
Subprotocols: []string{"p1", "p2"},
ReadBufferSize: 1024,
WriteBufferSize: 1024,
}
type cstHandler struct{ *testing.T }
type Server struct {
*httptest.Server
URL string
}
func newServer(t *testing.T) *Server {
var s Server
s.Server = httptest.NewServer(cstHandler{t})
s.URL = "ws" + s.Server.URL[len("http"):]
return &s
}
func newTLSServer(t *testing.T) *Server {
var s Server
s.Server = httptest.NewTLSServer(cstHandler{t})
s.URL = "ws" + s.Server.URL[len("http"):]
return &s
}
func (t cstHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
if r.Method != "GET" {
t.Logf("method %s not allowed", r.Method)
http.Error(w, "method not allowed", 405)
return
}
subprotos := Subprotocols(r)
if !reflect.DeepEqual(subprotos, cstDialer.Subprotocols) {
t.Logf("subprotols=%v, want %v", subprotos, cstDialer.Subprotocols)
http.Error(w, "bad protocol", 400)
return
}
ws, err := cstUpgrader.Upgrade(w, r, http.Header{"Set-Cookie": {"sessionID=1234"}})
if err != nil {
t.Logf("Upgrade: %v", err)
return
}
defer ws.Close()
if ws.Subprotocol() != "p1" {
t.Logf("Subprotocol() = %s, want p1", ws.Subprotocol())
ws.Close()
return
}
op, rd, err := ws.NextReader()
if err != nil {
t.Logf("NextReader: %v", err)
return
}
wr, err := ws.NextWriter(op)
if err != nil {
t.Logf("NextWriter: %v", err)
return
}
if _, err = io.Copy(wr, rd); err != nil {
t.Logf("NextWriter: %v", err)
return
}
if err := wr.Close(); err != nil {
t.Logf("Close: %v", err)
return
}
}
func sendRecv(t *testing.T, ws *Conn) {
const message = "Hello World!"
if err := ws.SetWriteDeadline(time.Now().Add(time.Second)); err != nil {
t.Fatalf("SetWriteDeadline: %v", err)
}
if err := ws.WriteMessage(TextMessage, []byte(message)); err != nil {
t.Fatalf("WriteMessage: %v", err)
}
if err := ws.SetReadDeadline(time.Now().Add(time.Second)); err != nil {
t.Fatalf("SetReadDeadline: %v", err)
}
_, p, err := ws.ReadMessage()
if err != nil {
t.Fatalf("ReadMessage: %v", err)
}
if string(p) != message {
t.Fatalf("message=%s, want %s", p, message)
}
}
func TestDial(t *testing.T) {
s := newServer(t)
defer s.Close()
ws, _, err := cstDialer.Dial(s.URL, nil)
if err != nil {
t.Fatalf("Dial: %v", err)
}
defer ws.Close()
sendRecv(t, ws)
}
func TestDialTLS(t *testing.T) {
s := newTLSServer(t)
defer s.Close()
certs := x509.NewCertPool()
for _, c := range s.TLS.Certificates {
roots, err := x509.ParseCertificates(c.Certificate[len(c.Certificate)-1])
if err != nil {
t.Fatalf("error parsing server's root cert: %v", err)
}
for _, root := range roots {
certs.AddCert(root)
}
}
u, _ := url.Parse(s.URL)
d := cstDialer
d.NetDial = func(network, addr string) (net.Conn, error) { return net.Dial(network, u.Host) }
d.TLSClientConfig = &tls.Config{RootCAs: certs}
ws, _, err := d.Dial("wss://example.com/", nil)
if err != nil {
t.Fatalf("Dial: %v", err)
}
defer ws.Close()
sendRecv(t, ws)
}
func xTestDialTLSBadCert(t *testing.T) {
s := newTLSServer(t)
defer s.Close()
ws, _, err := cstDialer.Dial(s.URL, nil)
if err == nil {
ws.Close()
t.Fatalf("Dial: nil")
}
}
func xTestDialTLSNoVerify(t *testing.T) {
s := newTLSServer(t)
defer s.Close()
d := cstDialer
d.TLSClientConfig = &tls.Config{InsecureSkipVerify: true}
ws, _, err := d.Dial(s.URL, nil)
if err != nil {
t.Fatalf("Dial: %v", err)
}
defer ws.Close()
sendRecv(t, ws)
}
func TestDialTimeout(t *testing.T) {
s := newServer(t)
defer s.Close()
d := cstDialer
d.HandshakeTimeout = -1
ws, _, err := d.Dial(s.URL, nil)
if err == nil {
ws.Close()
t.Fatalf("Dial: nil")
}
}
func TestDialBadScheme(t *testing.T) {
s := newServer(t)
defer s.Close()
ws, _, err := cstDialer.Dial(s.Server.URL, nil)
if err == nil {
ws.Close()
t.Fatalf("Dial: nil")
}
}
func TestDialBadOrigin(t *testing.T) {
s := newServer(t)
defer s.Close()
ws, resp, err := cstDialer.Dial(s.URL, http.Header{"Origin": {"bad"}})
if err == nil {
ws.Close()
t.Fatalf("Dial: nil")
}
if resp == nil {
t.Fatalf("resp=nil, err=%v", err)
}
if resp.StatusCode != http.StatusForbidden {
t.Fatalf("status=%d, want %d", resp.StatusCode, http.StatusForbidden)
}
}
func TestHandshake(t *testing.T) {
s := newServer(t)
defer s.Close()
ws, resp, err := cstDialer.Dial(s.URL, http.Header{"Origin": {s.URL}})
if err != nil {
t.Fatalf("Dial: %v", err)
}
defer ws.Close()
var sessionID string
for _, c := range resp.Cookies() {
if c.Name == "sessionID" {
sessionID = c.Value
}
}
if sessionID != "1234" {
t.Error("Set-Cookie not received from the server.")
}
if ws.Subprotocol() != "p1" {
t.Errorf("ws.Subprotocol() = %s, want p1", ws.Subprotocol())
}
sendRecv(t, ws)
}

View File

@@ -1,63 +0,0 @@
// Copyright 2014 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package websocket
import (
"net/url"
"reflect"
"testing"
)
var parseURLTests = []struct {
s string
u *url.URL
}{
{"ws://example.com/", &url.URL{Scheme: "ws", Host: "example.com", Opaque: "/"}},
{"ws://example.com", &url.URL{Scheme: "ws", Host: "example.com", Opaque: "/"}},
{"ws://example.com:7777/", &url.URL{Scheme: "ws", Host: "example.com:7777", Opaque: "/"}},
{"wss://example.com/", &url.URL{Scheme: "wss", Host: "example.com", Opaque: "/"}},
{"wss://example.com/a/b", &url.URL{Scheme: "wss", Host: "example.com", Opaque: "/a/b"}},
{"ss://example.com/a/b", nil},
}
func TestParseURL(t *testing.T) {
for _, tt := range parseURLTests {
u, err := parseURL(tt.s)
if tt.u != nil && err != nil {
t.Errorf("parseURL(%q) returned error %v", tt.s, err)
continue
}
if tt.u == nil && err == nil {
t.Errorf("parseURL(%q) did not return error", tt.s)
continue
}
if !reflect.DeepEqual(u, tt.u) {
t.Errorf("parseURL(%q) returned %v, want %v", tt.s, u, tt.u)
continue
}
}
}
var hostPortNoPortTests = []struct {
u *url.URL
hostPort, hostNoPort string
}{
{&url.URL{Scheme: "ws", Host: "example.com"}, "example.com:80", "example.com"},
{&url.URL{Scheme: "wss", Host: "example.com"}, "example.com:443", "example.com"},
{&url.URL{Scheme: "ws", Host: "example.com:7777"}, "example.com:7777", "example.com"},
{&url.URL{Scheme: "wss", Host: "example.com:7777"}, "example.com:7777", "example.com"},
}
func TestHostPortNoPort(t *testing.T) {
for _, tt := range hostPortNoPortTests {
hostPort, hostNoPort := hostPortNoPort(tt.u)
if hostPort != tt.hostPort {
t.Errorf("hostPortNoPort(%v) returned hostPort %q, want %q", tt.u, hostPort, tt.hostPort)
}
if hostNoPort != tt.hostNoPort {
t.Errorf("hostPortNoPort(%v) returned hostNoPort %q, want %q", tt.u, hostNoPort, tt.hostNoPort)
}
}
}

View File

@@ -1,825 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package websocket
import (
"bufio"
"encoding/binary"
"errors"
"io"
"io/ioutil"
"math/rand"
"net"
"strconv"
"time"
)
const (
maxFrameHeaderSize = 2 + 8 + 4 // Fixed header + length + mask
maxControlFramePayloadSize = 125
finalBit = 1 << 7
maskBit = 1 << 7
writeWait = time.Second
defaultReadBufferSize = 4096
defaultWriteBufferSize = 4096
continuationFrame = 0
noFrame = -1
)
// Close codes defined in RFC 6455, section 11.7.
const (
CloseNormalClosure = 1000
CloseGoingAway = 1001
CloseProtocolError = 1002
CloseUnsupportedData = 1003
CloseNoStatusReceived = 1005
CloseAbnormalClosure = 1006
CloseInvalidFramePayloadData = 1007
ClosePolicyViolation = 1008
CloseMessageTooBig = 1009
CloseMandatoryExtension = 1010
CloseInternalServerErr = 1011
CloseTLSHandshake = 1015
)
// The message types are defined in RFC 6455, section 11.8.
const (
// TextMessage denotes a text data message. The text message payload is
// interpreted as UTF-8 encoded text data.
TextMessage = 1
// BinaryMessage denotes a binary data message.
BinaryMessage = 2
// CloseMessage denotes a close control message. The optional message
// payload contains a numeric code and text. Use the FormatCloseMessage
// function to format a close message payload.
CloseMessage = 8
// PingMessage denotes a ping control message. The optional message payload
// is UTF-8 encoded text.
PingMessage = 9
// PongMessage denotes a ping control message. The optional message payload
// is UTF-8 encoded text.
PongMessage = 10
)
// ErrCloseSent is returned when the application writes a message to the
// connection after sending a close message.
var ErrCloseSent = errors.New("websocket: close sent")
// ErrReadLimit is returned when reading a message that is larger than the
// read limit set for the connection.
var ErrReadLimit = errors.New("websocket: read limit exceeded")
// netError satisfies the net Error interface.
type netError struct {
msg string
temporary bool
timeout bool
}
func (e *netError) Error() string { return e.msg }
func (e *netError) Temporary() bool { return e.temporary }
func (e *netError) Timeout() bool { return e.timeout }
// closeError represents close frame.
type closeError struct {
code int
text string
}
func (e *closeError) Error() string {
return "websocket: close " + strconv.Itoa(e.code) + " " + e.text
}
var (
errWriteTimeout = &netError{msg: "websocket: write timeout", timeout: true}
errUnexpectedEOF = &closeError{code: CloseAbnormalClosure, text: io.ErrUnexpectedEOF.Error()}
errBadWriteOpCode = errors.New("websocket: bad write message type")
errWriteClosed = errors.New("websocket: write closed")
errInvalidControlFrame = errors.New("websocket: invalid control frame")
)
func hideTempErr(err error) error {
if e, ok := err.(net.Error); ok && e.Temporary() {
err = &netError{msg: e.Error(), timeout: e.Timeout()}
}
return err
}
func isControl(frameType int) bool {
return frameType == CloseMessage || frameType == PingMessage || frameType == PongMessage
}
func isData(frameType int) bool {
return frameType == TextMessage || frameType == BinaryMessage
}
func maskBytes(key [4]byte, pos int, b []byte) int {
for i := range b {
b[i] ^= key[pos&3]
pos++
}
return pos & 3
}
func newMaskKey() [4]byte {
n := rand.Uint32()
return [4]byte{byte(n), byte(n >> 8), byte(n >> 16), byte(n >> 24)}
}
// Conn represents a WebSocket connection.
type Conn struct {
conn net.Conn
isServer bool
subprotocol string
// Write fields
mu chan bool // used as mutex to protect write to conn and closeSent
closeSent bool // true if close message was sent
// Message writer fields.
writeErr error
writeBuf []byte // frame is constructed in this buffer.
writePos int // end of data in writeBuf.
writeFrameType int // type of the current frame.
writeSeq int // incremented to invalidate message writers.
writeDeadline time.Time
// Read fields
readErr error
br *bufio.Reader
readRemaining int64 // bytes remaining in current frame.
readFinal bool // true the current message has more frames.
readSeq int // incremented to invalidate message readers.
readLength int64 // Message size.
readLimit int64 // Maximum message size.
readMaskPos int
readMaskKey [4]byte
handlePong func(string) error
handlePing func(string) error
}
func newConn(conn net.Conn, isServer bool, readBufferSize, writeBufferSize int) *Conn {
mu := make(chan bool, 1)
mu <- true
if readBufferSize == 0 {
readBufferSize = defaultReadBufferSize
}
if writeBufferSize == 0 {
writeBufferSize = defaultWriteBufferSize
}
c := &Conn{
isServer: isServer,
br: bufio.NewReaderSize(conn, readBufferSize),
conn: conn,
mu: mu,
readFinal: true,
writeBuf: make([]byte, writeBufferSize+maxFrameHeaderSize),
writeFrameType: noFrame,
writePos: maxFrameHeaderSize,
}
c.SetPingHandler(nil)
c.SetPongHandler(nil)
return c
}
// Subprotocol returns the negotiated protocol for the connection.
func (c *Conn) Subprotocol() string {
return c.subprotocol
}
// Close closes the underlying network connection without sending or waiting for a close frame.
func (c *Conn) Close() error {
return c.conn.Close()
}
// LocalAddr returns the local network address.
func (c *Conn) LocalAddr() net.Addr {
return c.conn.LocalAddr()
}
// RemoteAddr returns the remote network address.
func (c *Conn) RemoteAddr() net.Addr {
return c.conn.RemoteAddr()
}
// Write methods
func (c *Conn) write(frameType int, deadline time.Time, bufs ...[]byte) error {
<-c.mu
defer func() { c.mu <- true }()
if c.closeSent {
return ErrCloseSent
} else if frameType == CloseMessage {
c.closeSent = true
}
c.conn.SetWriteDeadline(deadline)
for _, buf := range bufs {
if len(buf) > 0 {
n, err := c.conn.Write(buf)
if n != len(buf) {
// Close on partial write.
c.conn.Close()
}
if err != nil {
return err
}
}
}
return nil
}
// WriteControl writes a control message with the given deadline. The allowed
// message types are CloseMessage, PingMessage and PongMessage.
func (c *Conn) WriteControl(messageType int, data []byte, deadline time.Time) error {
if !isControl(messageType) {
return errBadWriteOpCode
}
if len(data) > maxControlFramePayloadSize {
return errInvalidControlFrame
}
b0 := byte(messageType) | finalBit
b1 := byte(len(data))
if !c.isServer {
b1 |= maskBit
}
buf := make([]byte, 0, maxFrameHeaderSize+maxControlFramePayloadSize)
buf = append(buf, b0, b1)
if c.isServer {
buf = append(buf, data...)
} else {
key := newMaskKey()
buf = append(buf, key[:]...)
buf = append(buf, data...)
maskBytes(key, 0, buf[6:])
}
d := time.Hour * 1000
if !deadline.IsZero() {
d = deadline.Sub(time.Now())
if d < 0 {
return errWriteTimeout
}
}
timer := time.NewTimer(d)
select {
case <-c.mu:
timer.Stop()
case <-timer.C:
return errWriteTimeout
}
defer func() { c.mu <- true }()
if c.closeSent {
return ErrCloseSent
} else if messageType == CloseMessage {
c.closeSent = true
}
c.conn.SetWriteDeadline(deadline)
n, err := c.conn.Write(buf)
if n != 0 && n != len(buf) {
c.conn.Close()
}
return err
}
// NextWriter returns a writer for the next message to send. The writer's
// Close method flushes the complete message to the network.
//
// There can be at most one open writer on a connection. NextWriter closes the
// previous writer if the application has not already done so.
//
// The NextWriter method and the writers returned from the method cannot be
// accessed by more than one goroutine at a time.
func (c *Conn) NextWriter(messageType int) (io.WriteCloser, error) {
if c.writeErr != nil {
return nil, c.writeErr
}
if c.writeFrameType != noFrame {
if err := c.flushFrame(true, nil); err != nil {
return nil, err
}
}
if !isControl(messageType) && !isData(messageType) {
return nil, errBadWriteOpCode
}
c.writeFrameType = messageType
return messageWriter{c, c.writeSeq}, nil
}
func (c *Conn) flushFrame(final bool, extra []byte) error {
length := c.writePos - maxFrameHeaderSize + len(extra)
// Check for invalid control frames.
if isControl(c.writeFrameType) &&
(!final || length > maxControlFramePayloadSize) {
c.writeSeq++
c.writeFrameType = noFrame
c.writePos = maxFrameHeaderSize
return errInvalidControlFrame
}
b0 := byte(c.writeFrameType)
if final {
b0 |= finalBit
}
b1 := byte(0)
if !c.isServer {
b1 |= maskBit
}
// Assume that the frame starts at beginning of c.writeBuf.
framePos := 0
if c.isServer {
// Adjust up if mask not included in the header.
framePos = 4
}
switch {
case length >= 65536:
c.writeBuf[framePos] = b0
c.writeBuf[framePos+1] = b1 | 127
binary.BigEndian.PutUint64(c.writeBuf[framePos+2:], uint64(length))
case length > 125:
framePos += 6
c.writeBuf[framePos] = b0
c.writeBuf[framePos+1] = b1 | 126
binary.BigEndian.PutUint16(c.writeBuf[framePos+2:], uint16(length))
default:
framePos += 8
c.writeBuf[framePos] = b0
c.writeBuf[framePos+1] = b1 | byte(length)
}
if !c.isServer {
key := newMaskKey()
copy(c.writeBuf[maxFrameHeaderSize-4:], key[:])
maskBytes(key, 0, c.writeBuf[maxFrameHeaderSize:c.writePos])
if len(extra) > 0 {
c.writeErr = errors.New("websocket: internal error, extra used in client mode")
return c.writeErr
}
}
// Write the buffers to the connection.
c.writeErr = c.write(c.writeFrameType, c.writeDeadline, c.writeBuf[framePos:c.writePos], extra)
// Setup for next frame.
c.writePos = maxFrameHeaderSize
c.writeFrameType = continuationFrame
if final {
c.writeSeq++
c.writeFrameType = noFrame
}
return c.writeErr
}
type messageWriter struct {
c *Conn
seq int
}
func (w messageWriter) err() error {
c := w.c
if c.writeSeq != w.seq {
return errWriteClosed
}
if c.writeErr != nil {
return c.writeErr
}
return nil
}
func (w messageWriter) ncopy(max int) (int, error) {
n := len(w.c.writeBuf) - w.c.writePos
if n <= 0 {
if err := w.c.flushFrame(false, nil); err != nil {
return 0, err
}
n = len(w.c.writeBuf) - w.c.writePos
}
if n > max {
n = max
}
return n, nil
}
func (w messageWriter) write(final bool, p []byte) (int, error) {
if err := w.err(); err != nil {
return 0, err
}
if len(p) > 2*len(w.c.writeBuf) && w.c.isServer {
// Don't buffer large messages.
err := w.c.flushFrame(final, p)
if err != nil {
return 0, err
}
return len(p), nil
}
nn := len(p)
for len(p) > 0 {
n, err := w.ncopy(len(p))
if err != nil {
return 0, err
}
copy(w.c.writeBuf[w.c.writePos:], p[:n])
w.c.writePos += n
p = p[n:]
}
return nn, nil
}
func (w messageWriter) Write(p []byte) (int, error) {
return w.write(false, p)
}
func (w messageWriter) WriteString(p string) (int, error) {
if err := w.err(); err != nil {
return 0, err
}
nn := len(p)
for len(p) > 0 {
n, err := w.ncopy(len(p))
if err != nil {
return 0, err
}
copy(w.c.writeBuf[w.c.writePos:], p[:n])
w.c.writePos += n
p = p[n:]
}
return nn, nil
}
func (w messageWriter) ReadFrom(r io.Reader) (nn int64, err error) {
if err := w.err(); err != nil {
return 0, err
}
for {
if w.c.writePos == len(w.c.writeBuf) {
err = w.c.flushFrame(false, nil)
if err != nil {
break
}
}
var n int
n, err = r.Read(w.c.writeBuf[w.c.writePos:])
w.c.writePos += n
nn += int64(n)
if err != nil {
if err == io.EOF {
err = nil
}
break
}
}
return nn, err
}
func (w messageWriter) Close() error {
if err := w.err(); err != nil {
return err
}
return w.c.flushFrame(true, nil)
}
// WriteMessage is a helper method for getting a writer using NextWriter,
// writing the message and closing the writer.
func (c *Conn) WriteMessage(messageType int, data []byte) error {
wr, err := c.NextWriter(messageType)
if err != nil {
return err
}
w := wr.(messageWriter)
if _, err := w.write(true, data); err != nil {
return err
}
if c.writeSeq == w.seq {
if err := c.flushFrame(true, nil); err != nil {
return err
}
}
return nil
}
// SetWriteDeadline sets the write deadline on the underlying network
// connection. After a write has timed out, the websocket state is corrupt and
// all future writes will return an error. A zero value for t means writes will
// not time out.
func (c *Conn) SetWriteDeadline(t time.Time) error {
c.writeDeadline = t
return nil
}
// Read methods
// readFull is like io.ReadFull except that io.EOF is never returned.
func (c *Conn) readFull(p []byte) (err error) {
var n int
for n < len(p) && err == nil {
var nn int
nn, err = c.br.Read(p[n:])
n += nn
}
if n == len(p) {
err = nil
} else if err == io.EOF {
err = errUnexpectedEOF
}
return
}
func (c *Conn) advanceFrame() (int, error) {
// 1. Skip remainder of previous frame.
if c.readRemaining > 0 {
if _, err := io.CopyN(ioutil.Discard, c.br, c.readRemaining); err != nil {
return noFrame, err
}
}
// 2. Read and parse first two bytes of frame header.
var b [8]byte
if err := c.readFull(b[:2]); err != nil {
return noFrame, err
}
final := b[0]&finalBit != 0
frameType := int(b[0] & 0xf)
reserved := int((b[0] >> 4) & 0x7)
mask := b[1]&maskBit != 0
c.readRemaining = int64(b[1] & 0x7f)
if reserved != 0 {
return noFrame, c.handleProtocolError("unexpected reserved bits " + strconv.Itoa(reserved))
}
switch frameType {
case CloseMessage, PingMessage, PongMessage:
if c.readRemaining > maxControlFramePayloadSize {
return noFrame, c.handleProtocolError("control frame length > 125")
}
if !final {
return noFrame, c.handleProtocolError("control frame not final")
}
case TextMessage, BinaryMessage:
if !c.readFinal {
return noFrame, c.handleProtocolError("message start before final message frame")
}
c.readFinal = final
case continuationFrame:
if c.readFinal {
return noFrame, c.handleProtocolError("continuation after final message frame")
}
c.readFinal = final
default:
return noFrame, c.handleProtocolError("unknown opcode " + strconv.Itoa(frameType))
}
// 3. Read and parse frame length.
switch c.readRemaining {
case 126:
if err := c.readFull(b[:2]); err != nil {
return noFrame, err
}
c.readRemaining = int64(binary.BigEndian.Uint16(b[:2]))
case 127:
if err := c.readFull(b[:8]); err != nil {
return noFrame, err
}
c.readRemaining = int64(binary.BigEndian.Uint64(b[:8]))
}
// 4. Handle frame masking.
if mask != c.isServer {
return noFrame, c.handleProtocolError("incorrect mask flag")
}
if mask {
c.readMaskPos = 0
if err := c.readFull(c.readMaskKey[:]); err != nil {
return noFrame, err
}
}
// 5. For text and binary messages, enforce read limit and return.
if frameType == continuationFrame || frameType == TextMessage || frameType == BinaryMessage {
c.readLength += c.readRemaining
if c.readLimit > 0 && c.readLength > c.readLimit {
c.WriteControl(CloseMessage, FormatCloseMessage(CloseMessageTooBig, ""), time.Now().Add(writeWait))
return noFrame, ErrReadLimit
}
return frameType, nil
}
// 6. Read control frame payload.
var payload []byte
if c.readRemaining > 0 {
payload = make([]byte, c.readRemaining)
c.readRemaining = 0
if err := c.readFull(payload); err != nil {
return noFrame, err
}
if c.isServer {
maskBytes(c.readMaskKey, 0, payload)
}
}
// 7. Process control frame payload.
switch frameType {
case PongMessage:
if err := c.handlePong(string(payload)); err != nil {
return noFrame, err
}
case PingMessage:
if err := c.handlePing(string(payload)); err != nil {
return noFrame, err
}
case CloseMessage:
c.WriteControl(CloseMessage, []byte{}, time.Now().Add(writeWait))
closeCode := CloseNoStatusReceived
closeText := ""
if len(payload) >= 2 {
closeCode = int(binary.BigEndian.Uint16(payload))
closeText = string(payload[2:])
}
switch closeCode {
case CloseNormalClosure, CloseGoingAway:
return noFrame, io.EOF
default:
return noFrame, &closeError{code: closeCode, text: closeText}
}
}
return frameType, nil
}
func (c *Conn) handleProtocolError(message string) error {
c.WriteControl(CloseMessage, FormatCloseMessage(CloseProtocolError, message), time.Now().Add(writeWait))
return errors.New("websocket: " + message)
}
// NextReader returns the next data message received from the peer. The
// returned messageType is either TextMessage or BinaryMessage.
//
// There can be at most one open reader on a connection. NextReader discards
// the previous message if the application has not already consumed it.
//
// The NextReader method and the readers returned from the method cannot be
// accessed by more than one goroutine at a time.
func (c *Conn) NextReader() (messageType int, r io.Reader, err error) {
c.readSeq++
c.readLength = 0
for c.readErr == nil {
frameType, err := c.advanceFrame()
if err != nil {
c.readErr = hideTempErr(err)
break
}
if frameType == TextMessage || frameType == BinaryMessage {
return frameType, messageReader{c, c.readSeq}, nil
}
}
return noFrame, nil, c.readErr
}
type messageReader struct {
c *Conn
seq int
}
func (r messageReader) Read(b []byte) (int, error) {
if r.seq != r.c.readSeq {
return 0, io.EOF
}
for r.c.readErr == nil {
if r.c.readRemaining > 0 {
if int64(len(b)) > r.c.readRemaining {
b = b[:r.c.readRemaining]
}
n, err := r.c.br.Read(b)
r.c.readErr = hideTempErr(err)
if r.c.isServer {
r.c.readMaskPos = maskBytes(r.c.readMaskKey, r.c.readMaskPos, b[:n])
}
r.c.readRemaining -= int64(n)
return n, r.c.readErr
}
if r.c.readFinal {
r.c.readSeq++
return 0, io.EOF
}
frameType, err := r.c.advanceFrame()
switch {
case err != nil:
r.c.readErr = hideTempErr(err)
case frameType == TextMessage || frameType == BinaryMessage:
r.c.readErr = errors.New("websocket: internal error, unexpected text or binary in Reader")
}
}
err := r.c.readErr
if err == io.EOF && r.seq == r.c.readSeq {
err = errUnexpectedEOF
}
return 0, err
}
// ReadMessage is a helper method for getting a reader using NextReader and
// reading from that reader to a buffer.
func (c *Conn) ReadMessage() (messageType int, p []byte, err error) {
var r io.Reader
messageType, r, err = c.NextReader()
if err != nil {
return messageType, nil, err
}
p, err = ioutil.ReadAll(r)
return messageType, p, err
}
// SetReadDeadline sets the read deadline on the underlying network connection.
// After a read has timed out, the websocket connection state is corrupt and
// all future reads will return an error. A zero value for t means reads will
// not time out.
func (c *Conn) SetReadDeadline(t time.Time) error {
return c.conn.SetReadDeadline(t)
}
// SetReadLimit sets the maximum size for a message read from the peer. If a
// message exceeds the limit, the connection sends a close frame to the peer
// and returns ErrReadLimit to the application.
func (c *Conn) SetReadLimit(limit int64) {
c.readLimit = limit
}
// SetPingHandler sets the handler for ping messages received from the peer.
// The default ping handler sends a pong to the peer.
func (c *Conn) SetPingHandler(h func(string) error) {
if h == nil {
h = func(message string) error {
c.WriteControl(PongMessage, []byte(message), time.Now().Add(writeWait))
return nil
}
}
c.handlePing = h
}
// SetPongHandler sets then handler for pong messages received from the peer.
// The default pong handler does nothing.
func (c *Conn) SetPongHandler(h func(string) error) {
if h == nil {
h = func(string) error { return nil }
}
c.handlePong = h
}
// UnderlyingConn returns the internal net.Conn. This can be used to further
// modifications to connection specific flags.
func (c *Conn) UnderlyingConn() net.Conn {
return c.conn
}
// FormatCloseMessage formats closeCode and text as a WebSocket close message.
func FormatCloseMessage(closeCode int, text string) []byte {
buf := make([]byte, 2+len(text))
binary.BigEndian.PutUint16(buf, uint16(closeCode))
copy(buf[2:], text)
return buf
}

View File

@@ -1,238 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package websocket
import (
"bytes"
"fmt"
"io"
"io/ioutil"
"net"
"testing"
"testing/iotest"
"time"
)
var _ net.Error = errWriteTimeout
type fakeNetConn struct {
io.Reader
io.Writer
}
func (c fakeNetConn) Close() error { return nil }
func (c fakeNetConn) LocalAddr() net.Addr { return nil }
func (c fakeNetConn) RemoteAddr() net.Addr { return nil }
func (c fakeNetConn) SetDeadline(t time.Time) error { return nil }
func (c fakeNetConn) SetReadDeadline(t time.Time) error { return nil }
func (c fakeNetConn) SetWriteDeadline(t time.Time) error { return nil }
func TestFraming(t *testing.T) {
frameSizes := []int{0, 1, 2, 124, 125, 126, 127, 128, 129, 65534, 65535, 65536, 65537}
var readChunkers = []struct {
name string
f func(io.Reader) io.Reader
}{
{"half", iotest.HalfReader},
{"one", iotest.OneByteReader},
{"asis", func(r io.Reader) io.Reader { return r }},
}
writeBuf := make([]byte, 65537)
for i := range writeBuf {
writeBuf[i] = byte(i)
}
for _, isServer := range []bool{true, false} {
for _, chunker := range readChunkers {
var connBuf bytes.Buffer
wc := newConn(fakeNetConn{Reader: nil, Writer: &connBuf}, isServer, 1024, 1024)
rc := newConn(fakeNetConn{Reader: chunker.f(&connBuf), Writer: nil}, !isServer, 1024, 1024)
for _, n := range frameSizes {
for _, iocopy := range []bool{true, false} {
name := fmt.Sprintf("s:%v, r:%s, n:%d c:%v", isServer, chunker.name, n, iocopy)
w, err := wc.NextWriter(TextMessage)
if err != nil {
t.Errorf("%s: wc.NextWriter() returned %v", name, err)
continue
}
var nn int
if iocopy {
var n64 int64
n64, err = io.Copy(w, bytes.NewReader(writeBuf[:n]))
nn = int(n64)
} else {
nn, err = w.Write(writeBuf[:n])
}
if err != nil || nn != n {
t.Errorf("%s: w.Write(writeBuf[:n]) returned %d, %v", name, nn, err)
continue
}
err = w.Close()
if err != nil {
t.Errorf("%s: w.Close() returned %v", name, err)
continue
}
opCode, r, err := rc.NextReader()
if err != nil || opCode != TextMessage {
t.Errorf("%s: NextReader() returned %d, r, %v", name, opCode, err)
continue
}
rbuf, err := ioutil.ReadAll(r)
if err != nil {
t.Errorf("%s: ReadFull() returned rbuf, %v", name, err)
continue
}
if len(rbuf) != n {
t.Errorf("%s: len(rbuf) is %d, want %d", name, len(rbuf), n)
continue
}
for i, b := range rbuf {
if byte(i) != b {
t.Errorf("%s: bad byte at offset %d", name, i)
break
}
}
}
}
}
}
}
func TestControl(t *testing.T) {
const message = "this is a ping/pong messsage"
for _, isServer := range []bool{true, false} {
for _, isWriteControl := range []bool{true, false} {
name := fmt.Sprintf("s:%v, wc:%v", isServer, isWriteControl)
var connBuf bytes.Buffer
wc := newConn(fakeNetConn{Reader: nil, Writer: &connBuf}, isServer, 1024, 1024)
rc := newConn(fakeNetConn{Reader: &connBuf, Writer: nil}, !isServer, 1024, 1024)
if isWriteControl {
wc.WriteControl(PongMessage, []byte(message), time.Now().Add(time.Second))
} else {
w, err := wc.NextWriter(PongMessage)
if err != nil {
t.Errorf("%s: wc.NextWriter() returned %v", name, err)
continue
}
if _, err := w.Write([]byte(message)); err != nil {
t.Errorf("%s: w.Write() returned %v", name, err)
continue
}
if err := w.Close(); err != nil {
t.Errorf("%s: w.Close() returned %v", name, err)
continue
}
var actualMessage string
rc.SetPongHandler(func(s string) error { actualMessage = s; return nil })
rc.NextReader()
if actualMessage != message {
t.Errorf("%s: pong=%q, want %q", name, actualMessage, message)
continue
}
}
}
}
}
func TestCloseBeforeFinalFrame(t *testing.T) {
const bufSize = 512
var b1, b2 bytes.Buffer
wc := newConn(fakeNetConn{Reader: nil, Writer: &b1}, false, 1024, bufSize)
rc := newConn(fakeNetConn{Reader: &b1, Writer: &b2}, true, 1024, 1024)
w, _ := wc.NextWriter(BinaryMessage)
w.Write(make([]byte, bufSize+bufSize/2))
wc.WriteControl(CloseMessage, FormatCloseMessage(CloseNormalClosure, ""), time.Now().Add(10*time.Second))
w.Close()
op, r, err := rc.NextReader()
if op != BinaryMessage || err != nil {
t.Fatalf("NextReader() returned %d, %v", op, err)
}
_, err = io.Copy(ioutil.Discard, r)
if err != errUnexpectedEOF {
t.Fatalf("io.Copy() returned %v, want %v", err, errUnexpectedEOF)
}
_, _, err = rc.NextReader()
if err != io.EOF {
t.Fatalf("NextReader() returned %v, want %v", err, io.EOF)
}
}
func TestEOFBeforeFinalFrame(t *testing.T) {
const bufSize = 512
var b1, b2 bytes.Buffer
wc := newConn(fakeNetConn{Reader: nil, Writer: &b1}, false, 1024, bufSize)
rc := newConn(fakeNetConn{Reader: &b1, Writer: &b2}, true, 1024, 1024)
w, _ := wc.NextWriter(BinaryMessage)
w.Write(make([]byte, bufSize+bufSize/2))
op, r, err := rc.NextReader()
if op != BinaryMessage || err != nil {
t.Fatalf("NextReader() returned %d, %v", op, err)
}
_, err = io.Copy(ioutil.Discard, r)
if err != errUnexpectedEOF {
t.Fatalf("io.Copy() returned %v, want %v", err, errUnexpectedEOF)
}
_, _, err = rc.NextReader()
if err != errUnexpectedEOF {
t.Fatalf("NextReader() returned %v, want %v", err, errUnexpectedEOF)
}
}
func TestReadLimit(t *testing.T) {
const readLimit = 512
message := make([]byte, readLimit+1)
var b1, b2 bytes.Buffer
wc := newConn(fakeNetConn{Reader: nil, Writer: &b1}, false, 1024, readLimit-2)
rc := newConn(fakeNetConn{Reader: &b1, Writer: &b2}, true, 1024, 1024)
rc.SetReadLimit(readLimit)
// Send message at the limit with interleaved pong.
w, _ := wc.NextWriter(BinaryMessage)
w.Write(message[:readLimit-1])
wc.WriteControl(PongMessage, []byte("this is a pong"), time.Now().Add(10*time.Second))
w.Write(message[:1])
w.Close()
// Send message larger than the limit.
wc.WriteMessage(BinaryMessage, message[:readLimit+1])
op, _, err := rc.NextReader()
if op != BinaryMessage || err != nil {
t.Fatalf("1: NextReader() returned %d, %v", op, err)
}
op, r, err := rc.NextReader()
if op != BinaryMessage || err != nil {
t.Fatalf("2: NextReader() returned %d, %v", op, err)
}
_, err = io.Copy(ioutil.Discard, r)
if err != ErrReadLimit {
t.Fatalf("io.Copy() returned %v", err)
}
}
func TestUnderlyingConn(t *testing.T) {
var b1, b2 bytes.Buffer
fc := fakeNetConn{Reader: &b1, Writer: &b2}
c := newConn(fc, true, 1024, 1024)
ul := c.UnderlyingConn()
if ul != fc {
t.Fatalf("Underlying conn is not what it should be.")
}
}

View File

@@ -1,148 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// Package websocket implements the WebSocket protocol defined in RFC 6455.
//
// Overview
//
// The Conn type represents a WebSocket connection. A server application uses
// the Upgrade function from an Upgrader object with a HTTP request handler
// to get a pointer to a Conn:
//
// var upgrader = websocket.Upgrader{
// ReadBufferSize: 1024,
// WriteBufferSize: 1024,
// }
//
// func handler(w http.ResponseWriter, r *http.Request) {
// conn, err := upgrader.Upgrade(w, r, nil)
// if err != nil {
// log.Println(err)
// return
// }
// ... Use conn to send and receive messages.
// }
//
// Call the connection WriteMessage and ReadMessages methods to send and
// receive messages as a slice of bytes. This snippet of code shows how to echo
// messages using these methods:
//
// for {
// messageType, p, err := conn.ReadMessage()
// if err != nil {
// return
// }
// if err = conn.WriteMessage(messageType, p); err != nil {
// return err
// }
// }
//
// In above snippet of code, p is a []byte and messageType is an int with value
// websocket.BinaryMessage or websocket.TextMessage.
//
// An application can also send and receive messages using the io.WriteCloser
// and io.Reader interfaces. To send a message, call the connection NextWriter
// method to get an io.WriteCloser, write the message to the writer and close
// the writer when done. To receive a message, call the connection NextReader
// method to get an io.Reader and read until io.EOF is returned. This snippet
// snippet shows how to echo messages using the NextWriter and NextReader
// methods:
//
// for {
// messageType, r, err := conn.NextReader()
// if err != nil {
// return
// }
// w, err := conn.NextWriter(messageType)
// if err != nil {
// return err
// }
// if _, err := io.Copy(w, r); err != nil {
// return err
// }
// if err := w.Close(); err != nil {
// return err
// }
// }
//
// Data Messages
//
// The WebSocket protocol distinguishes between text and binary data messages.
// Text messages are interpreted as UTF-8 encoded text. The interpretation of
// binary messages is left to the application.
//
// This package uses the TextMessage and BinaryMessage integer constants to
// identify the two data message types. The ReadMessage and NextReader methods
// return the type of the received message. The messageType argument to the
// WriteMessage and NextWriter methods specifies the type of a sent message.
//
// It is the application's responsibility to ensure that text messages are
// valid UTF-8 encoded text.
//
// Control Messages
//
// The WebSocket protocol defines three types of control messages: close, ping
// and pong. Call the connection WriteControl, WriteMessage or NextWriter
// methods to send a control message to the peer.
//
// Connections handle received ping and pong messages by invoking a callback
// function set with SetPingHandler and SetPongHandler methods. These callback
// functions can be invoked from the ReadMessage method, the NextReader method
// or from a call to the data message reader returned from NextReader.
//
// Connections handle received close messages by returning an error from the
// ReadMessage method, the NextReader method or from a call to the data message
// reader returned from NextReader.
//
// Concurrency
//
// Connections do not support concurrent calls to the write methods
// (NextWriter, SetWriteDeadline, WriteMessage) or concurrent calls to the read
// methods methods (NextReader, SetReadDeadline, ReadMessage). Connections do
// support a concurrent reader and writer.
//
// The Close and WriteControl methods can be called concurrently with all other
// methods.
//
// Read is Required
//
// The application must read the connection to process ping and close messages
// sent from the peer. If the application is not otherwise interested in
// messages from the peer, then the application should start a goroutine to read
// and discard messages from the peer. A simple example is:
//
// func readLoop(c *websocket.Conn) {
// for {
// if _, _, err := c.NextReader(); err != nil {
// c.Close()
// break
// }
// }
// }
//
// Origin Considerations
//
// Web browsers allow Javascript applications to open a WebSocket connection to
// any host. It's up to the server to enforce an origin policy using the Origin
// request header sent by the browser.
//
// The Upgrader calls the function specified in the CheckOrigin field to check
// the origin. If the CheckOrigin function returns false, then the Upgrade
// method fails the WebSocket handshake with HTTP status 403.
//
// If the CheckOrigin field is nil, then the Upgrader uses a safe default: fail
// the handshake if the Origin request header is present and not equal to the
// Host request header.
//
// An application can allow connections from any origin by specifying a
// function that always returns true:
//
// var upgrader = websocket.Upgrader{
// CheckOrigin: func(r *http.Request) bool { return true },
// }
//
// The deprecated Upgrade function does not enforce an origin policy. It's the
// application's responsibility to check the Origin header before calling
// Upgrade.
package websocket

View File

@@ -1,13 +0,0 @@
# Test Server
This package contains a server for the [Autobahn WebSockets Test Suite](http://autobahn.ws/testsuite).
To test the server, run
go run server.go
and start the client test driver
wstest -m fuzzingclient -s fuzzingclient.json
When the client completes, it writes a report to reports/clients/index.html.

View File

@@ -1,14 +0,0 @@
{
"options": {"failByDrop": false},
"outdir": "./reports/clients",
"servers": [
{"agent": "ReadAllWriteMessage", "url": "ws://localhost:9000/m", "options": {"version": 18}},
{"agent": "ReadAllWrite", "url": "ws://localhost:9000/r", "options": {"version": 18}},
{"agent": "CopyFull", "url": "ws://localhost:9000/f", "options": {"version": 18}},
{"agent": "CopyWriterOnly", "url": "ws://localhost:9000/c", "options": {"version": 18}}
],
"cases": ["*"],
"exclude-cases": [],
"exclude-agent-cases": {}
}

View File

@@ -1,246 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// Command server is a test server for the Autobahn WebSockets Test Suite.
package main
import (
"errors"
"flag"
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/gorilla/websocket"
"io"
"log"
"net/http"
"time"
"unicode/utf8"
)
var upgrader = websocket.Upgrader{
ReadBufferSize: 4096,
WriteBufferSize: 4096,
CheckOrigin: func(r *http.Request) bool {
return true
},
}
// echoCopy echoes messages from the client using io.Copy.
func echoCopy(w http.ResponseWriter, r *http.Request, writerOnly bool) {
conn, err := upgrader.Upgrade(w, r, nil)
if err != nil {
log.Println("Upgrade:", err)
return
}
defer conn.Close()
for {
mt, r, err := conn.NextReader()
if err != nil {
if err != io.EOF {
log.Println("NextReader:", err)
}
return
}
if mt == websocket.TextMessage {
r = &validator{r: r}
}
w, err := conn.NextWriter(mt)
if err != nil {
log.Println("NextWriter:", err)
return
}
if mt == websocket.TextMessage {
r = &validator{r: r}
}
if writerOnly {
_, err = io.Copy(struct{ io.Writer }{w}, r)
} else {
_, err = io.Copy(w, r)
}
if err != nil {
if err == errInvalidUTF8 {
conn.WriteControl(websocket.CloseMessage,
websocket.FormatCloseMessage(websocket.CloseInvalidFramePayloadData, ""),
time.Time{})
}
log.Println("Copy:", err)
return
}
err = w.Close()
if err != nil {
log.Println("Close:", err)
return
}
}
}
func echoCopyWriterOnly(w http.ResponseWriter, r *http.Request) {
echoCopy(w, r, true)
}
func echoCopyFull(w http.ResponseWriter, r *http.Request) {
echoCopy(w, r, false)
}
// echoReadAll echoes messages from the client by reading the entire message
// with ioutil.ReadAll.
func echoReadAll(w http.ResponseWriter, r *http.Request, writeMessage bool) {
conn, err := upgrader.Upgrade(w, r, nil)
if err != nil {
log.Println("Upgrade:", err)
return
}
defer conn.Close()
for {
mt, b, err := conn.ReadMessage()
if err != nil {
if err != io.EOF {
log.Println("NextReader:", err)
}
return
}
if mt == websocket.TextMessage {
if !utf8.Valid(b) {
conn.WriteControl(websocket.CloseMessage,
websocket.FormatCloseMessage(websocket.CloseInvalidFramePayloadData, ""),
time.Time{})
log.Println("ReadAll: invalid utf8")
}
}
if writeMessage {
err = conn.WriteMessage(mt, b)
if err != nil {
log.Println("WriteMessage:", err)
}
} else {
w, err := conn.NextWriter(mt)
if err != nil {
log.Println("NextWriter:", err)
return
}
if _, err := w.Write(b); err != nil {
log.Println("Writer:", err)
return
}
if err := w.Close(); err != nil {
log.Println("Close:", err)
return
}
}
}
}
func echoReadAllWriter(w http.ResponseWriter, r *http.Request) {
echoReadAll(w, r, false)
}
func echoReadAllWriteMessage(w http.ResponseWriter, r *http.Request) {
echoReadAll(w, r, true)
}
func serveHome(w http.ResponseWriter, r *http.Request) {
if r.URL.Path != "/" {
http.Error(w, "Not found.", 404)
return
}
if r.Method != "GET" {
http.Error(w, "Method not allowed", 405)
return
}
w.Header().Set("Content-Type", "text/html; charset=utf-8")
io.WriteString(w, "<html><body>Echo Server</body></html>")
}
var addr = flag.String("addr", ":9000", "http service address")
func main() {
flag.Parse()
http.HandleFunc("/", serveHome)
http.HandleFunc("/c", echoCopyWriterOnly)
http.HandleFunc("/f", echoCopyFull)
http.HandleFunc("/r", echoReadAllWriter)
http.HandleFunc("/m", echoReadAllWriteMessage)
err := http.ListenAndServe(*addr, nil)
if err != nil {
log.Fatal("ListenAndServe: ", err)
}
}
type validator struct {
state int
x rune
r io.Reader
}
var errInvalidUTF8 = errors.New("invalid utf8")
func (r *validator) Read(p []byte) (int, error) {
n, err := r.r.Read(p)
state := r.state
x := r.x
for _, b := range p[:n] {
state, x = decode(state, x, b)
if state == utf8Reject {
break
}
}
r.state = state
r.x = x
if state == utf8Reject || (err == io.EOF && state != utf8Accept) {
return n, errInvalidUTF8
}
return n, err
}
// UTF-8 decoder from http://bjoern.hoehrmann.de/utf-8/decoder/dfa/
//
// Copyright (c) 2008-2009 Bjoern Hoehrmann <bjoern@hoehrmann.de>
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to
// deal in the Software without restriction, including without limitation the
// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
// sell copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
// IN THE SOFTWARE.
var utf8d = [...]byte{
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 00..1f
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 20..3f
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 40..5f
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 60..7f
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, 9, // 80..9f
7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, 7, // a0..bf
8, 8, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, // c0..df
0xa, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x3, 0x4, 0x3, 0x3, // e0..ef
0xb, 0x6, 0x6, 0x6, 0x5, 0x8, 0x8, 0x8, 0x8, 0x8, 0x8, 0x8, 0x8, 0x8, 0x8, 0x8, // f0..ff
0x0, 0x1, 0x2, 0x3, 0x5, 0x8, 0x7, 0x1, 0x1, 0x1, 0x4, 0x6, 0x1, 0x1, 0x1, 0x1, // s0..s0
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 0, 1, 0, 1, 1, 1, 1, 1, 1, // s1..s2
1, 2, 1, 1, 1, 1, 1, 2, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, // s3..s4
1, 2, 1, 1, 1, 1, 1, 1, 1, 2, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 3, 1, 3, 1, 1, 1, 1, 1, 1, // s5..s6
1, 3, 1, 1, 1, 1, 1, 3, 1, 3, 1, 1, 1, 1, 1, 1, 1, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, // s7..s8
}
const (
utf8Accept = 0
utf8Reject = 1
)
func decode(state int, x rune, b byte) (int, rune) {
t := utf8d[b]
if state != utf8Accept {
x = rune(b&0x3f) | (x << 6)
} else {
x = rune((0xff >> t) & b)
}
state = int(utf8d[256+state*16+int(t)])
return state, x
}

View File

@@ -1,19 +0,0 @@
# Chat Example
This application shows how to use use the
[websocket](https://github.com/gorilla/websocket) package and
[jQuery](http://jquery.com) to implement a simple web chat application.
## Running the example
The example requires a working Go development environment. The [Getting
Started](http://golang.org/doc/install) page describes how to install the
development environment.
Once you have Go up and running, you can download, build and run the example
using the following commands.
$ go get github.com/gorilla/websocket
$ cd `go list -f '{{.Dir}}' github.com/gorilla/websocket/examples/chat`
$ go run *.go

View File

@@ -1,106 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package main
import (
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/gorilla/websocket"
"log"
"net/http"
"time"
)
const (
// Time allowed to write a message to the peer.
writeWait = 10 * time.Second
// Time allowed to read the next pong message from the peer.
pongWait = 60 * time.Second
// Send pings to peer with this period. Must be less than pongWait.
pingPeriod = (pongWait * 9) / 10
// Maximum message size allowed from peer.
maxMessageSize = 512
)
var upgrader = websocket.Upgrader{
ReadBufferSize: 1024,
WriteBufferSize: 1024,
}
// connection is an middleman between the websocket connection and the hub.
type connection struct {
// The websocket connection.
ws *websocket.Conn
// Buffered channel of outbound messages.
send chan []byte
}
// readPump pumps messages from the websocket connection to the hub.
func (c *connection) readPump() {
defer func() {
h.unregister <- c
c.ws.Close()
}()
c.ws.SetReadLimit(maxMessageSize)
c.ws.SetReadDeadline(time.Now().Add(pongWait))
c.ws.SetPongHandler(func(string) error { c.ws.SetReadDeadline(time.Now().Add(pongWait)); return nil })
for {
_, message, err := c.ws.ReadMessage()
if err != nil {
break
}
h.broadcast <- message
}
}
// write writes a message with the given message type and payload.
func (c *connection) write(mt int, payload []byte) error {
c.ws.SetWriteDeadline(time.Now().Add(writeWait))
return c.ws.WriteMessage(mt, payload)
}
// writePump pumps messages from the hub to the websocket connection.
func (c *connection) writePump() {
ticker := time.NewTicker(pingPeriod)
defer func() {
ticker.Stop()
c.ws.Close()
}()
for {
select {
case message, ok := <-c.send:
if !ok {
c.write(websocket.CloseMessage, []byte{})
return
}
if err := c.write(websocket.TextMessage, message); err != nil {
return
}
case <-ticker.C:
if err := c.write(websocket.PingMessage, []byte{}); err != nil {
return
}
}
}
}
// serverWs handles websocket requests from the peer.
func serveWs(w http.ResponseWriter, r *http.Request) {
if r.Method != "GET" {
http.Error(w, "Method not allowed", 405)
return
}
ws, err := upgrader.Upgrade(w, r, nil)
if err != nil {
log.Println(err)
return
}
c := &connection{send: make(chan []byte, 256), ws: ws}
h.register <- c
go c.writePump()
c.readPump()
}

View File

@@ -1,92 +0,0 @@
<!DOCTYPE html>
<html lang="en">
<head>
<title>Chat Example</title>
<script src="//ajax.googleapis.com/ajax/libs/jquery/2.0.3/jquery.min.js"></script>
<script type="text/javascript">
$(function() {
var conn;
var msg = $("#msg");
var log = $("#log");
function appendLog(msg) {
var d = log[0]
var doScroll = d.scrollTop == d.scrollHeight - d.clientHeight;
msg.appendTo(log)
if (doScroll) {
d.scrollTop = d.scrollHeight - d.clientHeight;
}
}
$("#form").submit(function() {
if (!conn) {
return false;
}
if (!msg.val()) {
return false;
}
conn.send(msg.val());
msg.val("");
return false
});
if (window["WebSocket"]) {
conn = new WebSocket("ws://{{$}}/ws");
conn.onclose = function(evt) {
appendLog($("<div><b>Connection closed.</b></div>"))
}
conn.onmessage = function(evt) {
appendLog($("<div/>").text(evt.data))
}
} else {
appendLog($("<div><b>Your browser does not support WebSockets.</b></div>"))
}
});
</script>
<style type="text/css">
html {
overflow: hidden;
}
body {
overflow: hidden;
padding: 0;
margin: 0;
width: 100%;
height: 100%;
background: gray;
}
#log {
background: white;
margin: 0;
padding: 0.5em 0.5em 0.5em 0.5em;
position: absolute;
top: 0.5em;
left: 0.5em;
right: 0.5em;
bottom: 3em;
overflow: auto;
}
#form {
padding: 0 0.5em 0 0.5em;
margin: 0;
position: absolute;
bottom: 1em;
left: 0px;
width: 100%;
overflow: hidden;
}
</style>
</head>
<body>
<div id="log"></div>
<form id="form">
<input type="submit" value="Send" />
<input type="text" id="msg" size="64"/>
</form>
</body>
</html>

View File

@@ -1,51 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package main
// hub maintains the set of active connections and broadcasts messages to the
// connections.
type hub struct {
// Registered connections.
connections map[*connection]bool
// Inbound messages from the connections.
broadcast chan []byte
// Register requests from the connections.
register chan *connection
// Unregister requests from connections.
unregister chan *connection
}
var h = hub{
broadcast: make(chan []byte),
register: make(chan *connection),
unregister: make(chan *connection),
connections: make(map[*connection]bool),
}
func (h *hub) run() {
for {
select {
case c := <-h.register:
h.connections[c] = true
case c := <-h.unregister:
if _, ok := h.connections[c]; ok {
delete(h.connections, c)
close(c.send)
}
case m := <-h.broadcast:
for c := range h.connections {
select {
case c.send <- m:
default:
close(c.send)
delete(h.connections, c)
}
}
}
}
}

View File

@@ -1,39 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package main
import (
"flag"
"log"
"net/http"
"text/template"
)
var addr = flag.String("addr", ":8080", "http service address")
var homeTempl = template.Must(template.ParseFiles("home.html"))
func serveHome(w http.ResponseWriter, r *http.Request) {
if r.URL.Path != "/" {
http.Error(w, "Not found", 404)
return
}
if r.Method != "GET" {
http.Error(w, "Method not allowed", 405)
return
}
w.Header().Set("Content-Type", "text/html; charset=utf-8")
homeTempl.Execute(w, r.Host)
}
func main() {
flag.Parse()
go h.run()
http.HandleFunc("/", serveHome)
http.HandleFunc("/ws", serveWs)
err := http.ListenAndServe(*addr, nil)
if err != nil {
log.Fatal("ListenAndServe: ", err)
}
}

View File

@@ -1,9 +0,0 @@
# File Watch example.
This example sends a file to the browser client for display whenever the file is modified.
$ go get github.com/gorilla/websocket
$ cd `go list -f '{{.Dir}}' github.com/gorilla/websocket/examples/filewatch`
$ go run main.go <name of file to watch>
# Open http://localhost:8080/ .
# Modify the file to see it update in the browser.

View File

@@ -1,193 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package main
import (
"flag"
"io/ioutil"
"log"
"net/http"
"os"
"strconv"
"text/template"
"time"
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/gorilla/websocket"
)
const (
// Time allowed to write the file to the client.
writeWait = 10 * time.Second
// Time allowed to read the next pong message from the client.
pongWait = 60 * time.Second
// Send pings to client with this period. Must be less than pongWait.
pingPeriod = (pongWait * 9) / 10
// Poll file for changes with this period.
filePeriod = 10 * time.Second
)
var (
addr = flag.String("addr", ":8080", "http service address")
homeTempl = template.Must(template.New("").Parse(homeHTML))
filename string
upgrader = websocket.Upgrader{
ReadBufferSize: 1024,
WriteBufferSize: 1024,
}
)
func readFileIfModified(lastMod time.Time) ([]byte, time.Time, error) {
fi, err := os.Stat(filename)
if err != nil {
return nil, lastMod, err
}
if !fi.ModTime().After(lastMod) {
return nil, lastMod, nil
}
p, err := ioutil.ReadFile(filename)
if err != nil {
return nil, fi.ModTime(), err
}
return p, fi.ModTime(), nil
}
func reader(ws *websocket.Conn) {
defer ws.Close()
ws.SetReadLimit(512)
ws.SetReadDeadline(time.Now().Add(pongWait))
ws.SetPongHandler(func(string) error { ws.SetReadDeadline(time.Now().Add(pongWait)); return nil })
for {
_, _, err := ws.ReadMessage()
if err != nil {
break
}
}
}
func writer(ws *websocket.Conn, lastMod time.Time) {
lastError := ""
pingTicker := time.NewTicker(pingPeriod)
fileTicker := time.NewTicker(filePeriod)
defer func() {
pingTicker.Stop()
fileTicker.Stop()
ws.Close()
}()
for {
select {
case <-fileTicker.C:
var p []byte
var err error
p, lastMod, err = readFileIfModified(lastMod)
if err != nil {
if s := err.Error(); s != lastError {
lastError = s
p = []byte(lastError)
}
} else {
lastError = ""
}
if p != nil {
ws.SetWriteDeadline(time.Now().Add(writeWait))
if err := ws.WriteMessage(websocket.TextMessage, p); err != nil {
return
}
}
case <-pingTicker.C:
ws.SetWriteDeadline(time.Now().Add(writeWait))
if err := ws.WriteMessage(websocket.PingMessage, []byte{}); err != nil {
return
}
}
}
}
func serveWs(w http.ResponseWriter, r *http.Request) {
ws, err := upgrader.Upgrade(w, r, nil)
if err != nil {
if _, ok := err.(websocket.HandshakeError); !ok {
log.Println(err)
}
return
}
var lastMod time.Time
if n, err := strconv.ParseInt(r.FormValue("lastMod"), 16, 64); err != nil {
lastMod = time.Unix(0, n)
}
go writer(ws, lastMod)
reader(ws)
}
func serveHome(w http.ResponseWriter, r *http.Request) {
if r.URL.Path != "/" {
http.Error(w, "Not found", 404)
return
}
if r.Method != "GET" {
http.Error(w, "Method not allowed", 405)
return
}
w.Header().Set("Content-Type", "text/html; charset=utf-8")
p, lastMod, err := readFileIfModified(time.Time{})
if err != nil {
p = []byte(err.Error())
lastMod = time.Unix(0, 0)
}
var v = struct {
Host string
Data string
LastMod string
}{
r.Host,
string(p),
strconv.FormatInt(lastMod.UnixNano(), 16),
}
homeTempl.Execute(w, &v)
}
func main() {
flag.Parse()
if flag.NArg() != 1 {
log.Fatal("filename not specified")
}
filename = flag.Args()[0]
http.HandleFunc("/", serveHome)
http.HandleFunc("/ws", serveWs)
if err := http.ListenAndServe(*addr, nil); err != nil {
log.Fatal(err)
}
}
const homeHTML = `<!DOCTYPE html>
<html lang="en">
<head>
<title>WebSocket Example</title>
</head>
<body>
<pre id="fileData">{{.Data}}</pre>
<script type="text/javascript">
(function() {
var data = document.getElementById("fileData");
var conn = new WebSocket("ws://{{.Host}}/ws?lastMod={{.LastMod}}");
conn.onclose = function(evt) {
data.textContent = 'Connection closed';
}
conn.onmessage = function(evt) {
console.log('file updated');
data.textContent = evt.data;
}
})();
</script>
</body>
</html>
`

View File

@@ -1,49 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package websocket
import (
"encoding/json"
)
// WriteJSON is deprecated, use c.WriteJSON instead.
func WriteJSON(c *Conn, v interface{}) error {
return c.WriteJSON(v)
}
// WriteJSON writes the JSON encoding of v to the connection.
//
// See the documentation for encoding/json Marshal for details about the
// conversion of Go values to JSON.
func (c *Conn) WriteJSON(v interface{}) error {
w, err := c.NextWriter(TextMessage)
if err != nil {
return err
}
err1 := json.NewEncoder(w).Encode(v)
err2 := w.Close()
if err1 != nil {
return err1
}
return err2
}
// ReadJSON is deprecated, use c.ReadJSON instead.
func ReadJSON(c *Conn, v interface{}) error {
return c.ReadJSON(v)
}
// ReadJSON reads the next JSON-encoded message from the connection and stores
// it in the value pointed to by v.
//
// See the documentation for the encoding/json Unmarshal function for details
// about the conversion of JSON to a Go value.
func (c *Conn) ReadJSON(v interface{}) error {
_, r, err := c.NextReader()
if err != nil {
return err
}
return json.NewDecoder(r).Decode(v)
}

View File

@@ -1,63 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package websocket
import (
"bytes"
"reflect"
"testing"
)
func TestJSON(t *testing.T) {
var buf bytes.Buffer
c := fakeNetConn{&buf, &buf}
wc := newConn(c, true, 1024, 1024)
rc := newConn(c, false, 1024, 1024)
var actual, expect struct {
A int
B string
}
expect.A = 1
expect.B = "hello"
if err := wc.WriteJSON(&expect); err != nil {
t.Fatal("write", err)
}
if err := rc.ReadJSON(&actual); err != nil {
t.Fatal("read", err)
}
if !reflect.DeepEqual(&actual, &expect) {
t.Fatal("equal", actual, expect)
}
}
func TestDeprecatedJSON(t *testing.T) {
var buf bytes.Buffer
c := fakeNetConn{&buf, &buf}
wc := newConn(c, true, 1024, 1024)
rc := newConn(c, false, 1024, 1024)
var actual, expect struct {
A int
B string
}
expect.A = 1
expect.B = "hello"
if err := WriteJSON(wc, &expect); err != nil {
t.Fatal("write", err)
}
if err := ReadJSON(rc, &actual); err != nil {
t.Fatal("read", err)
}
if !reflect.DeepEqual(&actual, &expect) {
t.Fatal("equal", actual, expect)
}
}

View File

@@ -1,247 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package websocket
import (
"bufio"
"errors"
"net"
"net/http"
"net/url"
"strings"
"time"
)
// HandshakeError describes an error with the handshake from the peer.
type HandshakeError struct {
message string
}
func (e HandshakeError) Error() string { return e.message }
// Upgrader specifies parameters for upgrading an HTTP connection to a
// WebSocket connection.
type Upgrader struct {
// HandshakeTimeout specifies the duration for the handshake to complete.
HandshakeTimeout time.Duration
// ReadBufferSize and WriteBufferSize specify I/O buffer sizes. If a buffer
// size is zero, then a default value of 4096 is used. The I/O buffer sizes
// do not limit the size of the messages that can be sent or received.
ReadBufferSize, WriteBufferSize int
// Subprotocols specifies the server's supported protocols in order of
// preference. If this field is set, then the Upgrade method negotiates a
// subprotocol by selecting the first match in this list with a protocol
// requested by the client.
Subprotocols []string
// Error specifies the function for generating HTTP error responses. If Error
// is nil, then http.Error is used to generate the HTTP response.
Error func(w http.ResponseWriter, r *http.Request, status int, reason error)
// CheckOrigin returns true if the request Origin header is acceptable. If
// CheckOrigin is nil, the host in the Origin header must not be set or
// must match the host of the request.
CheckOrigin func(r *http.Request) bool
}
func (u *Upgrader) returnError(w http.ResponseWriter, r *http.Request, status int, reason string) (*Conn, error) {
err := HandshakeError{reason}
if u.Error != nil {
u.Error(w, r, status, err)
} else {
http.Error(w, http.StatusText(status), status)
}
return nil, err
}
// checkSameOrigin returns true if the origin is not set or is equal to the request host.
func checkSameOrigin(r *http.Request) bool {
origin := r.Header["Origin"]
if len(origin) == 0 {
return true
}
u, err := url.Parse(origin[0])
if err != nil {
return false
}
return u.Host == r.Host
}
func (u *Upgrader) selectSubprotocol(r *http.Request, responseHeader http.Header) string {
if u.Subprotocols != nil {
clientProtocols := Subprotocols(r)
for _, serverProtocol := range u.Subprotocols {
for _, clientProtocol := range clientProtocols {
if clientProtocol == serverProtocol {
return clientProtocol
}
}
}
} else if responseHeader != nil {
return responseHeader.Get("Sec-Websocket-Protocol")
}
return ""
}
// Upgrade upgrades the HTTP server connection to the WebSocket protocol.
//
// The responseHeader is included in the response to the client's upgrade
// request. Use the responseHeader to specify cookies (Set-Cookie) and the
// application negotiated subprotocol (Sec-Websocket-Protocol).
func (u *Upgrader) Upgrade(w http.ResponseWriter, r *http.Request, responseHeader http.Header) (*Conn, error) {
if values := r.Header["Sec-Websocket-Version"]; len(values) == 0 || values[0] != "13" {
return u.returnError(w, r, http.StatusBadRequest, "websocket: version != 13")
}
if !tokenListContainsValue(r.Header, "Connection", "upgrade") {
return u.returnError(w, r, http.StatusBadRequest, "websocket: connection header != upgrade")
}
if !tokenListContainsValue(r.Header, "Upgrade", "websocket") {
return u.returnError(w, r, http.StatusBadRequest, "websocket: upgrade != websocket")
}
checkOrigin := u.CheckOrigin
if checkOrigin == nil {
checkOrigin = checkSameOrigin
}
if !checkOrigin(r) {
return u.returnError(w, r, http.StatusForbidden, "websocket: origin not allowed")
}
challengeKey := r.Header.Get("Sec-Websocket-Key")
if challengeKey == "" {
return u.returnError(w, r, http.StatusBadRequest, "websocket: key missing or blank")
}
subprotocol := u.selectSubprotocol(r, responseHeader)
var (
netConn net.Conn
br *bufio.Reader
err error
)
h, ok := w.(http.Hijacker)
if !ok {
return u.returnError(w, r, http.StatusInternalServerError, "websocket: response does not implement http.Hijacker")
}
var rw *bufio.ReadWriter
netConn, rw, err = h.Hijack()
if err != nil {
return u.returnError(w, r, http.StatusInternalServerError, err.Error())
}
br = rw.Reader
if br.Buffered() > 0 {
netConn.Close()
return nil, errors.New("websocket: client sent data before handshake is complete")
}
c := newConn(netConn, true, u.ReadBufferSize, u.WriteBufferSize)
c.subprotocol = subprotocol
p := c.writeBuf[:0]
p = append(p, "HTTP/1.1 101 Switching Protocols\r\nUpgrade: websocket\r\nConnection: Upgrade\r\nSec-WebSocket-Accept: "...)
p = append(p, computeAcceptKey(challengeKey)...)
p = append(p, "\r\n"...)
if c.subprotocol != "" {
p = append(p, "Sec-Websocket-Protocol: "...)
p = append(p, c.subprotocol...)
p = append(p, "\r\n"...)
}
for k, vs := range responseHeader {
if k == "Sec-Websocket-Protocol" {
continue
}
for _, v := range vs {
p = append(p, k...)
p = append(p, ": "...)
for i := 0; i < len(v); i++ {
b := v[i]
if b <= 31 {
// prevent response splitting.
b = ' '
}
p = append(p, b)
}
p = append(p, "\r\n"...)
}
}
p = append(p, "\r\n"...)
// Clear deadlines set by HTTP server.
netConn.SetDeadline(time.Time{})
if u.HandshakeTimeout > 0 {
netConn.SetWriteDeadline(time.Now().Add(u.HandshakeTimeout))
}
if _, err = netConn.Write(p); err != nil {
netConn.Close()
return nil, err
}
if u.HandshakeTimeout > 0 {
netConn.SetWriteDeadline(time.Time{})
}
return c, nil
}
// Upgrade upgrades the HTTP server connection to the WebSocket protocol.
//
// This function is deprecated, use websocket.Upgrader instead.
//
// The application is responsible for checking the request origin before
// calling Upgrade. An example implementation of the same origin policy is:
//
// if req.Header.Get("Origin") != "http://"+req.Host {
// http.Error(w, "Origin not allowed", 403)
// return
// }
//
// If the endpoint supports subprotocols, then the application is responsible
// for negotiating the protocol used on the connection. Use the Subprotocols()
// function to get the subprotocols requested by the client. Use the
// Sec-Websocket-Protocol response header to specify the subprotocol selected
// by the application.
//
// The responseHeader is included in the response to the client's upgrade
// request. Use the responseHeader to specify cookies (Set-Cookie) and the
// negotiated subprotocol (Sec-Websocket-Protocol).
//
// The connection buffers IO to the underlying network connection. The
// readBufSize and writeBufSize parameters specify the size of the buffers to
// use. Messages can be larger than the buffers.
//
// If the request is not a valid WebSocket handshake, then Upgrade returns an
// error of type HandshakeError. Applications should handle this error by
// replying to the client with an HTTP error response.
func Upgrade(w http.ResponseWriter, r *http.Request, responseHeader http.Header, readBufSize, writeBufSize int) (*Conn, error) {
u := Upgrader{ReadBufferSize: readBufSize, WriteBufferSize: writeBufSize}
u.Error = func(w http.ResponseWriter, r *http.Request, status int, reason error) {
// don't return errors to maintain backwards compatibility
}
u.CheckOrigin = func(r *http.Request) bool {
// allow all connections by default
return true
}
return u.Upgrade(w, r, responseHeader)
}
// Subprotocols returns the subprotocols requested by the client in the
// Sec-Websocket-Protocol header.
func Subprotocols(r *http.Request) []string {
h := strings.TrimSpace(r.Header.Get("Sec-Websocket-Protocol"))
if h == "" {
return nil
}
protocols := strings.Split(h, ",")
for i := range protocols {
protocols[i] = strings.TrimSpace(protocols[i])
}
return protocols
}

View File

@@ -1,33 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package websocket
import (
"net/http"
"reflect"
"testing"
)
var subprotocolTests = []struct {
h string
protocols []string
}{
{"", nil},
{"foo", []string{"foo"}},
{"foo,bar", []string{"foo", "bar"}},
{"foo, bar", []string{"foo", "bar"}},
{" foo, bar", []string{"foo", "bar"}},
{" foo, bar ", []string{"foo", "bar"}},
}
func TestSubprotocols(t *testing.T) {
for _, st := range subprotocolTests {
r := http.Request{Header: http.Header{"Sec-Websocket-Protocol": {st.h}}}
protocols := Subprotocols(&r)
if !reflect.DeepEqual(st.protocols, protocols) {
t.Errorf("SubProtocols(%q) returned %#v, want %#v", st.h, protocols, st.protocols)
}
}
}

View File

@@ -1,44 +0,0 @@
// Copyright 2013 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package websocket
import (
"crypto/rand"
"crypto/sha1"
"encoding/base64"
"io"
"net/http"
"strings"
)
// tokenListContainsValue returns true if the 1#token header with the given
// name contains token.
func tokenListContainsValue(header http.Header, name string, value string) bool {
for _, v := range header[name] {
for _, s := range strings.Split(v, ",") {
if strings.EqualFold(value, strings.TrimSpace(s)) {
return true
}
}
}
return false
}
var keyGUID = []byte("258EAFA5-E914-47DA-95CA-C5AB0DC85B11")
func computeAcceptKey(challengeKey string) string {
h := sha1.New()
h.Write([]byte(challengeKey))
h.Write(keyGUID)
return base64.StdEncoding.EncodeToString(h.Sum(nil))
}
func generateChallengeKey() (string, error) {
p := make([]byte, 16)
if _, err := io.ReadFull(rand.Reader, p); err != nil {
return "", err
}
return base64.StdEncoding.EncodeToString(p), nil
}

View File

@@ -1,34 +0,0 @@
// Copyright 2014 The Gorilla WebSocket Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package websocket
import (
"net/http"
"testing"
)
var tokenListContainsValueTests = []struct {
value string
ok bool
}{
{"WebSocket", true},
{"WEBSOCKET", true},
{"websocket", true},
{"websockets", false},
{"x websocket", false},
{"websocket x", false},
{"other,websocket,more", true},
{"other, websocket, more", true},
}
func TestTokenListContainsValue(t *testing.T) {
for _, tt := range tokenListContainsValueTests {
h := http.Header{"Upgrade": {tt.value}}
ok := tokenListContainsValue(h, "Upgrade", "websocket")
if ok != tt.ok {
t.Errorf("tokenListContainsValue(h, n, %q) = %v, want %v", tt.value, ok, tt.ok)
}
}
}

View File

@@ -1,225 +0,0 @@
// Package stack implements utilities to capture, manipulate, and format call
// stacks.
package stack
import (
"fmt"
"path/filepath"
"runtime"
"strings"
)
// Call records a single function invocation from a goroutine stack. It is a
// wrapper for the program counter values returned by runtime.Caller and
// runtime.Callers and consumed by runtime.FuncForPC.
type Call uintptr
// Format implements fmt.Formatter with support for the following verbs.
//
// %s source file
// %d line number
// %n function name
// %v equivalent to %s:%d
//
// It accepts the '+' and '#' flags for most of the verbs as follows.
//
// %+s path of source file relative to the compile time GOPATH
// %#s full path of source file
// %+n import path qualified function name
// %+v equivalent to %+s:%d
// %#v equivalent to %#s:%d
func (pc Call) Format(s fmt.State, c rune) {
// BUG(ChrisHines): Subtracting one from pc is a work around for
// https://code.google.com/p/go/issues/detail?id=7690. The idea for this
// work around comes from rsc's initial patch at
// https://codereview.appspot.com/84100043/#ps20001, but as noted in the
// issue discussion, it is not a complete fix since it doesn't handle some
// cases involving signals. Just the same, it handles all of the other
// cases I have tested.
pcFix := uintptr(pc) - 1
fn := runtime.FuncForPC(pcFix)
if fn == nil {
fmt.Fprintf(s, "%%!%c(NOFUNC)", c)
return
}
switch c {
case 's', 'v':
file, line := fn.FileLine(pcFix)
switch {
case s.Flag('#'):
// done
case s.Flag('+'):
// Here we want to get the source file path relative to the
// compile time GOPATH. As of Go 1.3.x there is no direct way to
// know the compiled GOPATH at runtime, but we can infer the
// number of path segments in the GOPATH. We note that fn.Name()
// returns the function name qualified by the import path, which
// does not include the GOPATH. Thus we can trim segments from the
// beginning of the file path until the number of path separators
// remaining is one more than the number of path separators in the
// function name. For example, given:
//
// GOPATH /home/user
// file /home/user/src/pkg/sub/file.go
// fn.Name() pkg/sub.Type.Method
//
// We want to produce:
//
// pkg/sub/file.go
//
// From this we can easily see that fn.Name() has one less path
// separator than our desired output.
const sep = "/"
impCnt := strings.Count(fn.Name(), sep) + 1
pathCnt := strings.Count(file, sep)
for pathCnt > impCnt {
i := strings.Index(file, sep)
if i == -1 {
break
}
file = file[i+len(sep):]
pathCnt--
}
default:
const sep = "/"
if i := strings.LastIndex(file, sep); i != -1 {
file = file[i+len(sep):]
}
}
fmt.Fprint(s, file)
if c == 'v' {
fmt.Fprint(s, ":", line)
}
case 'd':
_, line := fn.FileLine(pcFix)
fmt.Fprint(s, line)
case 'n':
name := fn.Name()
if !s.Flag('+') {
const pathSep = "/"
if i := strings.LastIndex(name, pathSep); i != -1 {
name = name[i+len(pathSep):]
}
const pkgSep = "."
if i := strings.Index(name, pkgSep); i != -1 {
name = name[i+len(pkgSep):]
}
}
fmt.Fprint(s, name)
}
}
// Callers returns a Trace for the current goroutine with element 0
// identifying the calling function.
func Callers() Trace {
pcs := poolBuf()
pcs = pcs[:cap(pcs)]
n := runtime.Callers(2, pcs)
cs := make([]Call, n)
for i, pc := range pcs[:n] {
cs[i] = Call(pc)
}
putPoolBuf(pcs)
return cs
}
// name returns the import path qualified name of the function containing the
// call.
func (pc Call) name() string {
pcFix := uintptr(pc) - 1 // work around for go issue #7690
fn := runtime.FuncForPC(pcFix)
if fn == nil {
return "???"
}
return fn.Name()
}
func (pc Call) file() string {
pcFix := uintptr(pc) - 1 // work around for go issue #7690
fn := runtime.FuncForPC(pcFix)
if fn == nil {
return "???"
}
file, _ := fn.FileLine(pcFix)
return file
}
// Trace records a sequence of function invocations from a goroutine stack.
type Trace []Call
// Format implements fmt.Formatter by printing the Trace as square brackes ([,
// ]) surrounding a space separated list of Calls each formatted with the
// supplied verb and options.
func (pcs Trace) Format(s fmt.State, c rune) {
s.Write([]byte("["))
for i, pc := range pcs {
if i > 0 {
s.Write([]byte(" "))
}
pc.Format(s, c)
}
s.Write([]byte("]"))
}
// TrimBelow returns a slice of the Trace with all entries below pc removed.
func (pcs Trace) TrimBelow(pc Call) Trace {
for len(pcs) > 0 && pcs[0] != pc {
pcs = pcs[1:]
}
return pcs
}
// TrimAbove returns a slice of the Trace with all entries above pc removed.
func (pcs Trace) TrimAbove(pc Call) Trace {
for len(pcs) > 0 && pcs[len(pcs)-1] != pc {
pcs = pcs[:len(pcs)-1]
}
return pcs
}
// TrimBelowName returns a slice of the Trace with all entries below the
// lowest with function name name removed.
func (pcs Trace) TrimBelowName(name string) Trace {
for len(pcs) > 0 && pcs[0].name() != name {
pcs = pcs[1:]
}
return pcs
}
// TrimAboveName returns a slice of the Trace with all entries above the
// highest with function name name removed.
func (pcs Trace) TrimAboveName(name string) Trace {
for len(pcs) > 0 && pcs[len(pcs)-1].name() != name {
pcs = pcs[:len(pcs)-1]
}
return pcs
}
var goroot string
func init() {
goroot = filepath.ToSlash(runtime.GOROOT())
if runtime.GOOS == "windows" {
goroot = strings.ToLower(goroot)
}
}
func inGoroot(path string) bool {
if runtime.GOOS == "windows" {
path = strings.ToLower(path)
}
return strings.HasPrefix(path, goroot)
}
// TrimRuntime returns a slice of the Trace with the topmost entries from the
// go runtime removed. It considers any calls originating from files under
// GOROOT as part of the runtime.
func (pcs Trace) TrimRuntime() Trace {
for len(pcs) > 0 && inGoroot(pcs[len(pcs)-1].file()) {
pcs = pcs[:len(pcs)-1]
}
return pcs
}

View File

@@ -1,19 +0,0 @@
// +build go1.3
package stack
import (
"sync"
)
var pcStackPool = sync.Pool{
New: func() interface{} { return make([]uintptr, 1000) },
}
func poolBuf() []uintptr {
return pcStackPool.Get().([]uintptr)
}
func putPoolBuf(p []uintptr) {
pcStackPool.Put(p)
}

View File

@@ -1,27 +0,0 @@
// +build !go1.3 appengine
package stack
const (
stackPoolSize = 64
)
var (
pcStackPool = make(chan []uintptr, stackPoolSize)
)
func poolBuf() []uintptr {
select {
case p := <-pcStackPool:
return p
default:
return make([]uintptr, 1000)
}
}
func putPoolBuf(p []uintptr) {
select {
case pcStackPool <- p:
default:
}
}

View File

@@ -1,231 +0,0 @@
package stack_test
import (
"fmt"
"io/ioutil"
"os"
"path"
"path/filepath"
"runtime"
"testing"
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/inconshreveable/log15/stack"
)
type testType struct{}
func (tt testType) testMethod() (pc uintptr, file string, line int, ok bool) {
return runtime.Caller(0)
}
func TestCallFormat(t *testing.T) {
t.Parallel()
pc, file, line, ok := runtime.Caller(0)
if !ok {
t.Fatal("runtime.Caller(0) failed")
}
gopathSrc := filepath.Join(os.Getenv("GOPATH"), "src")
relFile, err := filepath.Rel(gopathSrc, file)
if err != nil {
t.Fatalf("failed to determine path relative to GOPATH: %v", err)
}
relFile = filepath.ToSlash(relFile)
pc2, file2, line2, ok2 := testType{}.testMethod()
if !ok2 {
t.Fatal("runtime.Caller(0) failed")
}
relFile2, err := filepath.Rel(gopathSrc, file)
if err != nil {
t.Fatalf("failed to determine path relative to GOPATH: %v", err)
}
relFile2 = filepath.ToSlash(relFile2)
data := []struct {
pc uintptr
desc string
fmt string
out string
}{
{0, "error", "%s", "%!s(NOFUNC)"},
{pc, "func", "%s", path.Base(file)},
{pc, "func", "%+s", relFile},
{pc, "func", "%#s", file},
{pc, "func", "%d", fmt.Sprint(line)},
{pc, "func", "%n", "TestCallFormat"},
{pc, "func", "%+n", runtime.FuncForPC(pc).Name()},
{pc, "func", "%v", fmt.Sprint(path.Base(file), ":", line)},
{pc, "func", "%+v", fmt.Sprint(relFile, ":", line)},
{pc, "func", "%#v", fmt.Sprint(file, ":", line)},
{pc, "func", "%v|%[1]n()", fmt.Sprint(path.Base(file), ":", line, "|", "TestCallFormat()")},
{pc2, "meth", "%s", path.Base(file2)},
{pc2, "meth", "%+s", relFile2},
{pc2, "meth", "%#s", file2},
{pc2, "meth", "%d", fmt.Sprint(line2)},
{pc2, "meth", "%n", "testType.testMethod"},
{pc2, "meth", "%+n", runtime.FuncForPC(pc2).Name()},
{pc2, "meth", "%v", fmt.Sprint(path.Base(file2), ":", line2)},
{pc2, "meth", "%+v", fmt.Sprint(relFile2, ":", line2)},
{pc2, "meth", "%#v", fmt.Sprint(file2, ":", line2)},
{pc2, "meth", "%v|%[1]n()", fmt.Sprint(path.Base(file2), ":", line2, "|", "testType.testMethod()")},
}
for _, d := range data {
got := fmt.Sprintf(d.fmt, stack.Call(d.pc))
if got != d.out {
t.Errorf("fmt.Sprintf(%q, Call(%s)) = %s, want %s", d.fmt, d.desc, got, d.out)
}
}
}
func BenchmarkCallVFmt(b *testing.B) {
pc, _, _, ok := runtime.Caller(0)
if !ok {
b.Fatal("runtime.Caller(0) failed")
}
b.ResetTimer()
for i := 0; i < b.N; i++ {
fmt.Fprint(ioutil.Discard, stack.Call(pc))
}
}
func BenchmarkCallPlusVFmt(b *testing.B) {
pc, _, _, ok := runtime.Caller(0)
if !ok {
b.Fatal("runtime.Caller(0) failed")
}
b.ResetTimer()
for i := 0; i < b.N; i++ {
fmt.Fprintf(ioutil.Discard, "%+v", stack.Call(pc))
}
}
func BenchmarkCallSharpVFmt(b *testing.B) {
pc, _, _, ok := runtime.Caller(0)
if !ok {
b.Fatal("runtime.Caller(0) failed")
}
b.ResetTimer()
for i := 0; i < b.N; i++ {
fmt.Fprintf(ioutil.Discard, "%#v", stack.Call(pc))
}
}
func BenchmarkCallSFmt(b *testing.B) {
pc, _, _, ok := runtime.Caller(0)
if !ok {
b.Fatal("runtime.Caller(0) failed")
}
b.ResetTimer()
for i := 0; i < b.N; i++ {
fmt.Fprintf(ioutil.Discard, "%s", stack.Call(pc))
}
}
func BenchmarkCallPlusSFmt(b *testing.B) {
pc, _, _, ok := runtime.Caller(0)
if !ok {
b.Fatal("runtime.Caller(0) failed")
}
b.ResetTimer()
for i := 0; i < b.N; i++ {
fmt.Fprintf(ioutil.Discard, "%+s", stack.Call(pc))
}
}
func BenchmarkCallSharpSFmt(b *testing.B) {
pc, _, _, ok := runtime.Caller(0)
if !ok {
b.Fatal("runtime.Caller(0) failed")
}
b.ResetTimer()
for i := 0; i < b.N; i++ {
fmt.Fprintf(ioutil.Discard, "%#s", stack.Call(pc))
}
}
func BenchmarkCallDFmt(b *testing.B) {
pc, _, _, ok := runtime.Caller(0)
if !ok {
b.Fatal("runtime.Caller(0) failed")
}
b.ResetTimer()
for i := 0; i < b.N; i++ {
fmt.Fprintf(ioutil.Discard, "%d", stack.Call(pc))
}
}
func BenchmarkCallNFmt(b *testing.B) {
pc, _, _, ok := runtime.Caller(0)
if !ok {
b.Fatal("runtime.Caller(0) failed")
}
b.ResetTimer()
for i := 0; i < b.N; i++ {
fmt.Fprintf(ioutil.Discard, "%n", stack.Call(pc))
}
}
func BenchmarkCallPlusNFmt(b *testing.B) {
pc, _, _, ok := runtime.Caller(0)
if !ok {
b.Fatal("runtime.Caller(0) failed")
}
b.ResetTimer()
for i := 0; i < b.N; i++ {
fmt.Fprintf(ioutil.Discard, "%+n", stack.Call(pc))
}
}
func BenchmarkCallers(b *testing.B) {
for i := 0; i < b.N; i++ {
stack.Callers()
}
}
func deepStack(depth int, b *testing.B) stack.Trace {
if depth > 0 {
return deepStack(depth-1, b)
}
b.StartTimer()
s := stack.Callers()
b.StopTimer()
return s
}
func BenchmarkCallers10(b *testing.B) {
b.StopTimer()
for i := 0; i < b.N; i++ {
deepStack(10, b)
}
}
func BenchmarkCallers50(b *testing.B) {
b.StopTimer()
for i := 0; i < b.N; i++ {
deepStack(50, b)
}
}
func BenchmarkCallers100(b *testing.B) {
b.StopTimer()
for i := 0; i < b.N; i++ {
deepStack(100, b)
}
}

View File

@@ -1,21 +0,0 @@
The MIT License (MIT)
Copyright (c) 2014 Simon Eskildsen
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.

View File

@@ -1,13 +0,0 @@
// Based on ssh/terminal:
// Copyright 2013 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// +build appengine
package term
// IsTty always returns false on AppEngine.
func IsTty(fd uintptr) bool {
return false
}

View File

@@ -1,12 +0,0 @@
// Based on ssh/terminal:
// Copyright 2013 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package term
import "syscall"
const ioctlReadTermios = syscall.TIOCGETA
type Termios syscall.Termios

View File

@@ -1,18 +0,0 @@
package term
import (
"syscall"
)
const ioctlReadTermios = syscall.TIOCGETA
// Go 1.2 doesn't include Termios for FreeBSD. This should be added in 1.3 and this could be merged with terminal_darwin.
type Termios struct {
Iflag uint32
Oflag uint32
Cflag uint32
Lflag uint32
Cc [20]uint8
Ispeed uint32
Ospeed uint32
}

View File

@@ -1,14 +0,0 @@
// Based on ssh/terminal:
// Copyright 2013 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// +build !appengine
package term
import "syscall"
const ioctlReadTermios = syscall.TCGETS
type Termios syscall.Termios

View File

@@ -1,20 +0,0 @@
// Based on ssh/terminal:
// Copyright 2011 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// +build linux,!appengine darwin freebsd
package term
import (
"syscall"
"unsafe"
)
// IsTty returns true if the given file descriptor is a terminal.
func IsTty(fd uintptr) bool {
var termios Termios
_, _, err := syscall.Syscall6(syscall.SYS_IOCTL, fd, ioctlReadTermios, uintptr(unsafe.Pointer(&termios)), 0, 0, 0)
return err == 0
}

View File

@@ -1,26 +0,0 @@
// Based on ssh/terminal:
// Copyright 2011 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// +build windows
package term
import (
"syscall"
"unsafe"
)
var kernel32 = syscall.NewLazyDLL("kernel32.dll")
var (
procGetConsoleMode = kernel32.NewProc("GetConsoleMode")
)
// IsTty returns true if the given file descriptor is a terminal.
func IsTty(fd uintptr) bool {
var st uint32
r, _, e := syscall.Syscall(procGetConsoleMode.Addr(), 2, fd, uintptr(unsafe.Pointer(&st)), 0)
return r != 0 && e == 0
}

View File

@@ -1,42 +0,0 @@
# go-colorable
Colorable writer for windows.
For example, most of logger packages doesn't show colors on windows. (I know we can do it with ansicon. But I don't want.)
This package is possible to handle escape sequence for ansi color on windows.
## Too Bad!
![](https://raw.githubusercontent.com/mattn/go-colorable/gh-pages/bad.png)
## So Good!
![](https://raw.githubusercontent.com/mattn/go-colorable/gh-pages/good.png)
## Usage
```go
logrus.SetOutput(colorable.NewColorableStdout())
logrus.Info("succeeded")
logrus.Warn("not correct")
logrus.Error("something error")
logrus.Fatal("panic")
```
You can compile above code on non-windows OSs.
## Installation
```
$ go get github.com/mattn/go-colorable
```
# License
MIT
# Author
Yasuhiro Matsumoto (a.k.a mattn)

View File

@@ -1,16 +0,0 @@
// +build !windows
package colorable
import (
"io"
"os"
)
func NewColorableStdout() io.Writer {
return os.Stdout
}
func NewColorableStderr() io.Writer {
return os.Stderr
}

View File

@@ -1,594 +0,0 @@
package colorable
import (
"bytes"
"fmt"
"io"
"os"
"strconv"
"strings"
"syscall"
"unsafe"
"github.com/mattn/go-isatty"
)
const (
foregroundBlue = 0x1
foregroundGreen = 0x2
foregroundRed = 0x4
foregroundIntensity = 0x8
foregroundMask = (foregroundRed | foregroundBlue | foregroundGreen | foregroundIntensity)
backgroundBlue = 0x10
backgroundGreen = 0x20
backgroundRed = 0x40
backgroundIntensity = 0x80
backgroundMask = (backgroundRed | backgroundBlue | backgroundGreen | backgroundIntensity)
)
type wchar uint16
type short int16
type dword uint32
type word uint16
type coord struct {
x short
y short
}
type smallRect struct {
left short
top short
right short
bottom short
}
type consoleScreenBufferInfo struct {
size coord
cursorPosition coord
attributes word
window smallRect
maximumWindowSize coord
}
var (
kernel32 = syscall.NewLazyDLL("kernel32.dll")
procGetConsoleScreenBufferInfo = kernel32.NewProc("GetConsoleScreenBufferInfo")
procSetConsoleTextAttribute = kernel32.NewProc("SetConsoleTextAttribute")
)
type Writer struct {
out io.Writer
handle syscall.Handle
lastbuf bytes.Buffer
oldattr word
}
func NewColorableStdout() io.Writer {
var csbi consoleScreenBufferInfo
out := os.Stdout
if !isatty.IsTerminal(out.Fd()) {
return out
}
handle := syscall.Handle(out.Fd())
procGetConsoleScreenBufferInfo.Call(uintptr(handle), uintptr(unsafe.Pointer(&csbi)))
return &Writer{out: out, handle: handle, oldattr: csbi.attributes}
}
func NewColorableStderr() io.Writer {
var csbi consoleScreenBufferInfo
out := os.Stderr
if !isatty.IsTerminal(out.Fd()) {
return out
}
handle := syscall.Handle(out.Fd())
procGetConsoleScreenBufferInfo.Call(uintptr(handle), uintptr(unsafe.Pointer(&csbi)))
return &Writer{out: out, handle: handle, oldattr: csbi.attributes}
}
var color256 = map[int]int{
0: 0x000000,
1: 0x800000,
2: 0x008000,
3: 0x808000,
4: 0x000080,
5: 0x800080,
6: 0x008080,
7: 0xc0c0c0,
8: 0x808080,
9: 0xff0000,
10: 0x00ff00,
11: 0xffff00,
12: 0x0000ff,
13: 0xff00ff,
14: 0x00ffff,
15: 0xffffff,
16: 0x000000,
17: 0x00005f,
18: 0x000087,
19: 0x0000af,
20: 0x0000d7,
21: 0x0000ff,
22: 0x005f00,
23: 0x005f5f,
24: 0x005f87,
25: 0x005faf,
26: 0x005fd7,
27: 0x005fff,
28: 0x008700,
29: 0x00875f,
30: 0x008787,
31: 0x0087af,
32: 0x0087d7,
33: 0x0087ff,
34: 0x00af00,
35: 0x00af5f,
36: 0x00af87,
37: 0x00afaf,
38: 0x00afd7,
39: 0x00afff,
40: 0x00d700,
41: 0x00d75f,
42: 0x00d787,
43: 0x00d7af,
44: 0x00d7d7,
45: 0x00d7ff,
46: 0x00ff00,
47: 0x00ff5f,
48: 0x00ff87,
49: 0x00ffaf,
50: 0x00ffd7,
51: 0x00ffff,
52: 0x5f0000,
53: 0x5f005f,
54: 0x5f0087,
55: 0x5f00af,
56: 0x5f00d7,
57: 0x5f00ff,
58: 0x5f5f00,
59: 0x5f5f5f,
60: 0x5f5f87,
61: 0x5f5faf,
62: 0x5f5fd7,
63: 0x5f5fff,
64: 0x5f8700,
65: 0x5f875f,
66: 0x5f8787,
67: 0x5f87af,
68: 0x5f87d7,
69: 0x5f87ff,
70: 0x5faf00,
71: 0x5faf5f,
72: 0x5faf87,
73: 0x5fafaf,
74: 0x5fafd7,
75: 0x5fafff,
76: 0x5fd700,
77: 0x5fd75f,
78: 0x5fd787,
79: 0x5fd7af,
80: 0x5fd7d7,
81: 0x5fd7ff,
82: 0x5fff00,
83: 0x5fff5f,
84: 0x5fff87,
85: 0x5fffaf,
86: 0x5fffd7,
87: 0x5fffff,
88: 0x870000,
89: 0x87005f,
90: 0x870087,
91: 0x8700af,
92: 0x8700d7,
93: 0x8700ff,
94: 0x875f00,
95: 0x875f5f,
96: 0x875f87,
97: 0x875faf,
98: 0x875fd7,
99: 0x875fff,
100: 0x878700,
101: 0x87875f,
102: 0x878787,
103: 0x8787af,
104: 0x8787d7,
105: 0x8787ff,
106: 0x87af00,
107: 0x87af5f,
108: 0x87af87,
109: 0x87afaf,
110: 0x87afd7,
111: 0x87afff,
112: 0x87d700,
113: 0x87d75f,
114: 0x87d787,
115: 0x87d7af,
116: 0x87d7d7,
117: 0x87d7ff,
118: 0x87ff00,
119: 0x87ff5f,
120: 0x87ff87,
121: 0x87ffaf,
122: 0x87ffd7,
123: 0x87ffff,
124: 0xaf0000,
125: 0xaf005f,
126: 0xaf0087,
127: 0xaf00af,
128: 0xaf00d7,
129: 0xaf00ff,
130: 0xaf5f00,
131: 0xaf5f5f,
132: 0xaf5f87,
133: 0xaf5faf,
134: 0xaf5fd7,
135: 0xaf5fff,
136: 0xaf8700,
137: 0xaf875f,
138: 0xaf8787,
139: 0xaf87af,
140: 0xaf87d7,
141: 0xaf87ff,
142: 0xafaf00,
143: 0xafaf5f,
144: 0xafaf87,
145: 0xafafaf,
146: 0xafafd7,
147: 0xafafff,
148: 0xafd700,
149: 0xafd75f,
150: 0xafd787,
151: 0xafd7af,
152: 0xafd7d7,
153: 0xafd7ff,
154: 0xafff00,
155: 0xafff5f,
156: 0xafff87,
157: 0xafffaf,
158: 0xafffd7,
159: 0xafffff,
160: 0xd70000,
161: 0xd7005f,
162: 0xd70087,
163: 0xd700af,
164: 0xd700d7,
165: 0xd700ff,
166: 0xd75f00,
167: 0xd75f5f,
168: 0xd75f87,
169: 0xd75faf,
170: 0xd75fd7,
171: 0xd75fff,
172: 0xd78700,
173: 0xd7875f,
174: 0xd78787,
175: 0xd787af,
176: 0xd787d7,
177: 0xd787ff,
178: 0xd7af00,
179: 0xd7af5f,
180: 0xd7af87,
181: 0xd7afaf,
182: 0xd7afd7,
183: 0xd7afff,
184: 0xd7d700,
185: 0xd7d75f,
186: 0xd7d787,
187: 0xd7d7af,
188: 0xd7d7d7,
189: 0xd7d7ff,
190: 0xd7ff00,
191: 0xd7ff5f,
192: 0xd7ff87,
193: 0xd7ffaf,
194: 0xd7ffd7,
195: 0xd7ffff,
196: 0xff0000,
197: 0xff005f,
198: 0xff0087,
199: 0xff00af,
200: 0xff00d7,
201: 0xff00ff,
202: 0xff5f00,
203: 0xff5f5f,
204: 0xff5f87,
205: 0xff5faf,
206: 0xff5fd7,
207: 0xff5fff,
208: 0xff8700,
209: 0xff875f,
210: 0xff8787,
211: 0xff87af,
212: 0xff87d7,
213: 0xff87ff,
214: 0xffaf00,
215: 0xffaf5f,
216: 0xffaf87,
217: 0xffafaf,
218: 0xffafd7,
219: 0xffafff,
220: 0xffd700,
221: 0xffd75f,
222: 0xffd787,
223: 0xffd7af,
224: 0xffd7d7,
225: 0xffd7ff,
226: 0xffff00,
227: 0xffff5f,
228: 0xffff87,
229: 0xffffaf,
230: 0xffffd7,
231: 0xffffff,
232: 0x080808,
233: 0x121212,
234: 0x1c1c1c,
235: 0x262626,
236: 0x303030,
237: 0x3a3a3a,
238: 0x444444,
239: 0x4e4e4e,
240: 0x585858,
241: 0x626262,
242: 0x6c6c6c,
243: 0x767676,
244: 0x808080,
245: 0x8a8a8a,
246: 0x949494,
247: 0x9e9e9e,
248: 0xa8a8a8,
249: 0xb2b2b2,
250: 0xbcbcbc,
251: 0xc6c6c6,
252: 0xd0d0d0,
253: 0xdadada,
254: 0xe4e4e4,
255: 0xeeeeee,
}
func (w *Writer) Write(data []byte) (n int, err error) {
var csbi consoleScreenBufferInfo
procGetConsoleScreenBufferInfo.Call(uintptr(w.handle), uintptr(unsafe.Pointer(&csbi)))
er := bytes.NewBuffer(data)
loop:
for {
r1, _, err := procGetConsoleScreenBufferInfo.Call(uintptr(w.handle), uintptr(unsafe.Pointer(&csbi)))
if r1 == 0 {
break loop
}
c1, _, err := er.ReadRune()
if err != nil {
break loop
}
if c1 != 0x1b {
fmt.Fprint(w.out, string(c1))
continue
}
c2, _, err := er.ReadRune()
if err != nil {
w.lastbuf.WriteRune(c1)
break loop
}
if c2 != 0x5b {
w.lastbuf.WriteRune(c1)
w.lastbuf.WriteRune(c2)
continue
}
var buf bytes.Buffer
var m rune
for {
c, _, err := er.ReadRune()
if err != nil {
w.lastbuf.WriteRune(c1)
w.lastbuf.WriteRune(c2)
w.lastbuf.Write(buf.Bytes())
break loop
}
if ('a' <= c && c <= 'z') || ('A' <= c && c <= 'Z') || c == '@' {
m = c
break
}
buf.Write([]byte(string(c)))
}
switch m {
case 'm':
attr := csbi.attributes
cs := buf.String()
if cs == "" {
procSetConsoleTextAttribute.Call(uintptr(w.handle), uintptr(w.oldattr))
continue
}
token := strings.Split(cs, ";")
for i, ns := range token {
if n, err = strconv.Atoi(ns); err == nil {
switch {
case n == 0 || n == 100:
attr = w.oldattr
case 1 <= n && n <= 5:
attr |= foregroundIntensity
case n == 7:
attr = ((attr & foregroundMask) << 4) | ((attr & backgroundMask) >> 4)
case 22 == n || n == 25 || n == 25:
attr |= foregroundIntensity
case n == 27:
attr = ((attr & foregroundMask) << 4) | ((attr & backgroundMask) >> 4)
case 30 <= n && n <= 37:
attr = (attr & backgroundMask)
if (n-30)&1 != 0 {
attr |= foregroundRed
}
if (n-30)&2 != 0 {
attr |= foregroundGreen
}
if (n-30)&4 != 0 {
attr |= foregroundBlue
}
case n == 38: // set foreground color.
if i < len(token)-2 && token[i+1] == "5" {
if n256, err := strconv.Atoi(token[i+2]); err == nil {
if n256foreAttr == nil {
n256setup()
}
attr &= backgroundMask
attr |= n256foreAttr[n256]
i += 2
}
} else {
attr = attr & (w.oldattr & backgroundMask)
}
case n == 39: // reset foreground color.
attr &= backgroundMask
attr |= w.oldattr & foregroundMask
case 40 <= n && n <= 47:
attr = (attr & foregroundMask)
if (n-40)&1 != 0 {
attr |= backgroundRed
}
if (n-40)&2 != 0 {
attr |= backgroundGreen
}
if (n-40)&4 != 0 {
attr |= backgroundBlue
}
case n == 48: // set background color.
if i < len(token)-2 && token[i+1] == "5" {
if n256, err := strconv.Atoi(token[i+2]); err == nil {
if n256backAttr == nil {
n256setup()
}
attr &= foregroundMask
attr |= n256backAttr[n256]
i += 2
}
} else {
attr = attr & (w.oldattr & foregroundMask)
}
case n == 49: // reset foreground color.
attr &= foregroundMask
attr |= w.oldattr & backgroundMask
}
procSetConsoleTextAttribute.Call(uintptr(w.handle), uintptr(attr))
}
}
}
}
return len(data) - w.lastbuf.Len(), nil
}
type consoleColor struct {
red bool
green bool
blue bool
intensity bool
}
func minmax3(a, b, c int) (min, max int) {
if a < b {
if b < c {
return a, c
} else if a < c {
return a, b
} else {
return c, b
}
} else {
if a < c {
return b, c
} else if b < c {
return b, a
} else {
return c, a
}
}
}
func toConsoleColor(rgb int) (c consoleColor) {
r, g, b := (rgb&0xFF0000)>>16, (rgb&0x00FF00)>>8, rgb&0x0000FF
min, max := minmax3(r, g, b)
a := (min + max) / 2
if r < 128 && g < 128 && b < 128 {
if r >= a {
c.red = true
}
if g >= a {
c.green = true
}
if b >= a {
c.blue = true
}
// non-intensed white is lighter than intensed black, so swap those.
if c.red && c.green && c.blue {
c.red, c.green, c.blue = false, false, false
c.intensity = true
}
} else {
if min < 128 {
min = 128
a = (min + max) / 2
}
if r >= a {
c.red = true
}
if g >= a {
c.green = true
}
if b >= a {
c.blue = true
}
c.intensity = true
// intensed black is darker than non-intensed white, so swap those.
if !c.red && !c.green && !c.blue {
c.red, c.green, c.blue = true, true, true
c.intensity = false
}
}
return c
}
func (c consoleColor) foregroundAttr() (attr word) {
if c.red {
attr |= foregroundRed
}
if c.green {
attr |= foregroundGreen
}
if c.blue {
attr |= foregroundBlue
}
if c.intensity {
attr |= foregroundIntensity
}
return
}
func (c consoleColor) backgroundAttr() (attr word) {
if c.red {
attr |= backgroundRed
}
if c.green {
attr |= backgroundGreen
}
if c.blue {
attr |= backgroundBlue
}
if c.intensity {
attr |= backgroundIntensity
}
return
}
var n256foreAttr []word
var n256backAttr []word
func n256setup() {
n256foreAttr = make([]word, 256)
n256backAttr = make([]word, 256)
for i, rgb := range color256 {
c := toConsoleColor(rgb)
n256foreAttr[i] = c.foregroundAttr()
n256backAttr[i] = c.backgroundAttr()
}
}

View File

@@ -1,9 +0,0 @@
language: go
go:
- 1.3
- 1.4
- tip
install:
- go get -v github.com/naoina/go-stringutil
script:
- go test -v ./... -bench . -benchmem

View File

@@ -1,19 +0,0 @@
Copyright (c) 2015 Naoya Inada <naoina@kuune.org>
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.

View File

@@ -1,13 +0,0 @@
# stringutil [![Build Status](https://travis-ci.org/naoina/go-stringutil.png?branch=master)](https://travis-ci.org/naoina/go-stringutil)
## Installation
go get -u github.com/naoina/go-stringutil
## Documentation
See https://godoc.org/github.com/naoina/go-stringutil
## License
MIT

View File

@@ -1,120 +0,0 @@
package stringutil
import (
"bytes"
"unicode"
)
// ToUpperCamelCase returns a copy of the string s with all Unicode letters mapped to their camel case.
// It will convert to upper case previous letter of '_' and first letter, and remove letter of '_'.
func ToUpperCamelCase(s string) string {
if s == "" {
return ""
}
upper := true
var result bytes.Buffer
for _, c := range s {
if c == '_' {
upper = true
continue
}
if upper {
result.WriteRune(unicode.ToUpper(c))
upper = false
continue
}
result.WriteRune(c)
}
return result.String()
}
// ToUpperCamelCaseASCII is similar to ToUpperCamelCase, but optimized for
// only the ASCII characters.
// ToUpperCamelCaseASCII is faster than ToUpperCamelCase, but doesn't work if
// contains non-ASCII characters.
func ToUpperCamelCaseASCII(s string) string {
if s == "" {
return ""
}
upper := true
result := make([]byte, 0, len(s))
for i := 0; i < len(s); i++ {
c := s[i]
if c == '_' {
upper = true
continue
}
if upper {
result = append(result, toUpperASCII(c))
upper = false
continue
}
result = append(result, c)
}
return string(result)
}
// ToSnakeCase returns a copy of the string s with all Unicode letters mapped to their snake case.
// It will insert letter of '_' at position of previous letter of uppercase and all
// letters convert to lower case.
func ToSnakeCase(s string) string {
if s == "" {
return ""
}
var result bytes.Buffer
for _, c := range s {
if unicode.IsUpper(c) {
result.WriteByte('_')
}
result.WriteRune(unicode.ToLower(c))
}
s = result.String()
if s[0] == '_' {
return s[1:]
}
return s
}
// ToSnakeCaseASCII is similar to ToSnakeCase, but optimized for only the ASCII
// characters.
// ToSnakeCaseASCII is faster than ToSnakeCase, but doesn't work correctly if
// contains non-ASCII characters.
func ToSnakeCaseASCII(s string) string {
if s == "" {
return ""
}
result := make([]byte, 0, len(s))
for i := 0; i < len(s); i++ {
c := s[i]
if isUpperASCII(c) {
result = append(result, '_')
}
result = append(result, toLowerASCII(c))
}
if result[0] == '_' {
return string(result[1:])
}
return string(result)
}
func isUpperASCII(c byte) bool {
return 'A' <= c && c <= 'Z'
}
func isLowerASCII(c byte) bool {
return 'a' <= c && c <= 'z'
}
func toUpperASCII(c byte) byte {
if isLowerASCII(c) {
return c - ('a' - 'A')
}
return c
}
func toLowerASCII(c byte) byte {
if isUpperASCII(c) {
return c + 'a' - 'A'
}
return c
}

View File

@@ -1,35 +0,0 @@
package stringutil_test
import (
"testing"
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/naoina/go-stringutil"
)
var benchcaseForCamelCase = "the_quick_brown_fox_jumps_over_the_lazy_dog"
func BenchmarkToUpperCamelCase(b *testing.B) {
for i := 0; i < b.N; i++ {
stringutil.ToUpperCamelCase(benchcaseForCamelCase)
}
}
func BenchmarkToUpperCamelCaseASCII(b *testing.B) {
for i := 0; i < b.N; i++ {
stringutil.ToUpperCamelCaseASCII(benchcaseForCamelCase)
}
}
var benchcaseForSnakeCase = "TheQuickBrownFoxJumpsOverTheLazyDog"
func BenchmarkToSnakeCase(b *testing.B) {
for i := 0; i < b.N; i++ {
stringutil.ToSnakeCase(benchcaseForSnakeCase)
}
}
func BenchmarkToSnakeCaseASCII(b *testing.B) {
for i := 0; i < b.N; i++ {
stringutil.ToSnakeCaseASCII(benchcaseForSnakeCase)
}
}

View File

@@ -1,88 +0,0 @@
package stringutil_test
import (
"reflect"
"testing"
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/naoina/go-stringutil"
)
func TestToUpperCamelCase(t *testing.T) {
for _, v := range []struct {
input, expect string
}{
{"", ""},
{"thequickbrownfoxoverthelazydog", "Thequickbrownfoxoverthelazydog"},
{"thequickbrownfoxoverthelazydoG", "ThequickbrownfoxoverthelazydoG"},
{"thequickbrownfoxoverthelazydo_g", "ThequickbrownfoxoverthelazydoG"},
{"TheQuickBrownFoxJumpsOverTheLazyDog", "TheQuickBrownFoxJumpsOverTheLazyDog"},
{"the_quick_brown_fox_jumps_over_the_lazy_dog", "TheQuickBrownFoxJumpsOverTheLazyDog"},
{"the_Quick_Brown_Fox_Jumps_Over_The_Lazy_Dog", "TheQuickBrownFoxJumpsOverTheLazyDog"},
{"_______", ""},
} {
actual := stringutil.ToUpperCamelCase(v.input)
expect := v.expect
if !reflect.DeepEqual(actual, expect) {
t.Errorf(`stringutil.ToUpperCamelCase(%#v) => %#v; want %#v`, v.input, actual, expect)
}
}
}
func TestToUpperCamelCaseASCII(t *testing.T) {
for _, v := range []struct {
input, expect string
}{
{"", ""},
{"thequickbrownfoxoverthelazydog", "Thequickbrownfoxoverthelazydog"},
{"thequickbrownfoxoverthelazydoG", "ThequickbrownfoxoverthelazydoG"},
{"thequickbrownfoxoverthelazydo_g", "ThequickbrownfoxoverthelazydoG"},
{"TheQuickBrownFoxJumpsOverTheLazyDog", "TheQuickBrownFoxJumpsOverTheLazyDog"},
{"the_quick_brown_fox_jumps_over_the_lazy_dog", "TheQuickBrownFoxJumpsOverTheLazyDog"},
{"the_Quick_Brown_Fox_Jumps_Over_The_Lazy_Dog", "TheQuickBrownFoxJumpsOverTheLazyDog"},
} {
actual := stringutil.ToUpperCamelCaseASCII(v.input)
expect := v.expect
if !reflect.DeepEqual(actual, expect) {
t.Errorf(`stringutil.ToUpperCamelCaseASCII(%#v) => %#v; want %#v`, v.input, actual, expect)
}
}
}
func TestToSnakeCase(t *testing.T) {
for _, v := range []struct {
input, expect string
}{
{"", ""},
{"thequickbrownfoxjumpsoverthelazydog", "thequickbrownfoxjumpsoverthelazydog"},
{"Thequickbrownfoxjumpsoverthelazydog", "thequickbrownfoxjumpsoverthelazydog"},
{"ThequickbrownfoxjumpsoverthelazydoG", "thequickbrownfoxjumpsoverthelazydo_g"},
{"TheQuickBrownFoxJumpsOverTheLazyDog", "the_quick_brown_fox_jumps_over_the_lazy_dog"},
{"the_quick_brown_fox_jumps_over_the_lazy_dog", "the_quick_brown_fox_jumps_over_the_lazy_dog"},
{"", "_______"},
} {
actual := stringutil.ToSnakeCase(v.input)
expect := v.expect
if !reflect.DeepEqual(actual, expect) {
t.Errorf(`stringutil.ToSnakeCase(%#v) => %#v; want %#v`, v.input, actual, expect)
}
}
}
func TestToSnakeCaseASCII(t *testing.T) {
for _, v := range []struct {
input, expect string
}{
{"", ""},
{"thequickbrownfoxjumpsoverthelazydog", "thequickbrownfoxjumpsoverthelazydog"},
{"Thequickbrownfoxjumpsoverthelazydog", "thequickbrownfoxjumpsoverthelazydog"},
{"ThequickbrownfoxjumpsoverthelazydoG", "thequickbrownfoxjumpsoverthelazydo_g"},
{"TheQuickBrownFoxJumpsOverTheLazyDog", "the_quick_brown_fox_jumps_over_the_lazy_dog"},
{"the_quick_brown_fox_jumps_over_the_lazy_dog", "the_quick_brown_fox_jumps_over_the_lazy_dog"},
} {
actual := stringutil.ToSnakeCaseASCII(v.input)
expect := v.expect
if !reflect.DeepEqual(actual, expect) {
t.Errorf(`stringutil.ToSnakeCaseASCII(%#v) => %#v; want %#v`, v.input, actual, expect)
}
}
}

View File

@@ -1,11 +0,0 @@
language: go
go:
- 1.3
- tip
install:
- go get -v ./...
script:
- go test ./...

View File

@@ -1,19 +0,0 @@
Copyright (c) 2014 Naoya Inada <naoina@kuune.org>
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in
all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.

View File

@@ -1,16 +0,0 @@
GO = go
PEG = peg
.SUFFIXES: .peg .peg.go
.PHONY: all test clean
all: parse.peg.go
.peg.peg.go:
$(PEG) -switch -inline $<
test: all
$(GO) test ./...
clean:
$(RM) *.peg.go

View File

@@ -1,364 +0,0 @@
# TOML parser and encoder library for Golang [![Build Status](https://travis-ci.org/naoina/toml.png?branch=master)](https://travis-ci.org/naoina/toml)
[TOML](https://github.com/toml-lang/toml) parser and encoder library for [Golang](http://golang.org/).
This library is compatible with TOML version [v0.4.0](https://github.com/toml-lang/toml/blob/master/versions/en/toml-v0.4.0.md).
## Installation
go get -u github.com/naoina/toml
## Usage
The following TOML save as `example.toml`.
```toml
# This is a TOML document. Boom.
title = "TOML Example"
[owner]
name = "Lance Uppercut"
dob = 1979-05-27T07:32:00-08:00 # First class dates? Why not?
[database]
server = "192.168.1.1"
ports = [ 8001, 8001, 8002 ]
connection_max = 5000
enabled = true
[servers]
# You can indent as you please. Tabs or spaces. TOML don't care.
[servers.alpha]
ip = "10.0.0.1"
dc = "eqdc10"
[servers.beta]
ip = "10.0.0.2"
dc = "eqdc10"
[clients]
data = [ ["gamma", "delta"], [1, 2] ]
# Line breaks are OK when inside arrays
hosts = [
"alpha",
"omega"
]
```
Then above TOML will mapping to `tomlConfig` struct using `toml.Unmarshal`.
```go
package main
import (
"io/ioutil"
"os"
"time"
"github.com/naoina/toml"
)
type tomlConfig struct {
Title string
Owner struct {
Name string
Dob time.Time
}
Database struct {
Server string
Ports []int
ConnectionMax uint
Enabled bool
}
Servers map[string]Server
Clients struct {
Data [][]interface{}
Hosts []string
}
}
type Server struct {
IP string
DC string
}
func main() {
f, err := os.Open("example.toml")
if err != nil {
panic(err)
}
defer f.Close()
buf, err := ioutil.ReadAll(f)
if err != nil {
panic(err)
}
var config tomlConfig
if err := toml.Unmarshal(buf, &config); err != nil {
panic(err)
}
// then to use the unmarshaled config...
}
```
## Mappings
A key and value of TOML will map to the corresponding field.
The fields of struct for mapping must be exported.
The rules of the mapping of key are following:
#### Exact matching
```toml
timeout_seconds = 256
```
```go
type Config struct {
Timeout_seconds int
}
```
#### Camelcase matching
```toml
server_name = "srv1"
```
```go
type Config struct {
ServerName string
}
```
#### Uppercase matching
```toml
ip = "10.0.0.1"
```
```go
type Config struct {
IP string
}
```
See the following examples for the value mappings.
### String
```toml
val = "string"
```
```go
type Config struct {
Val string
}
```
### Integer
```toml
val = 100
```
```go
type Config struct {
Val int
}
```
All types that can be used are following:
* int8 (from `-128` to `127`)
* int16 (from `-32768` to `32767`)
* int32 (from `-2147483648` to `2147483647`)
* int64 (from `-9223372036854775808` to `9223372036854775807`)
* int (same as `int32` on 32bit environment, or `int64` on 64bit environment)
* uint8 (from `0` to `255`)
* uint16 (from `0` to `65535`)
* uint32 (from `0` to `4294967295`)
* uint64 (from `0` to `18446744073709551615`)
* uint (same as `uint` on 32bit environment, or `uint64` on 64bit environment)
### Float
```toml
val = 3.1415
```
```go
type Config struct {
Val float32
}
```
All types that can be used are following:
* float32
* float64
### Boolean
```toml
val = true
```
```go
type Config struct {
Val bool
}
```
### Datetime
```toml
val = 2014-09-28T21:27:39Z
```
```go
type Config struct {
Val time.Time
}
```
### Array
```toml
val = ["a", "b", "c"]
```
```go
type Config struct {
Val []string
}
```
Also following examples all can be mapped:
```toml
val1 = [1, 2, 3]
val2 = [["a", "b"], ["c", "d"]]
val3 = [[1, 2, 3], ["a", "b", "c"]]
val4 = [[1, 2, 3], [["a", "b"], [true, false]]]
```
```go
type Config struct {
Val1 []int
Val2 [][]string
Val3 [][]interface{}
Val4 [][]interface{}
}
```
### Table
```toml
[server]
type = "app"
[server.development]
ip = "10.0.0.1"
[server.production]
ip = "10.0.0.2"
```
```go
type Config struct {
Server map[string]Server
}
type Server struct {
IP string
}
```
You can also use the following struct instead of map of struct.
```go
type Config struct {
Server struct {
Development Server
Production Server
}
}
type Server struct {
IP string
}
```
### Array of Tables
```toml
[[fruit]]
name = "apple"
[fruit.physical]
color = "red"
shape = "round"
[[fruit.variety]]
name = "red delicious"
[[fruit.variety]]
name = "granny smith"
[[fruit]]
name = "banana"
[[fruit.variety]]
name = "plantain"
```
```go
type Config struct {
Fruit []struct {
Name string
Physical struct {
Color string
Shape string
}
Variety []struct {
Name string
}
}
}
```
### Using `toml.UnmarshalTOML` interface
```toml
duration = "10s"
```
```go
import time
type Config struct {
Duration Duration
}
type Duration struct {
time.Duration
}
func (d *Duration) UnmarshalTOML(data []byte) error {
d.Duration, err := time.ParseDuration(string(data))
return err
}
```
## API documentation
See [Godoc](http://godoc.org/github.com/naoina/toml).
## License
MIT

View File

@@ -1,184 +0,0 @@
package ast
import (
"strconv"
"time"
)
type Position struct {
Begin int
End int
}
type Value interface {
Pos() int
End() int
Source() string
}
type String struct {
Position Position
Value string
Data []rune
}
func (s *String) Pos() int {
return s.Position.Begin
}
func (s *String) End() int {
return s.Position.End
}
func (s *String) Source() string {
return string(s.Data)
}
type Integer struct {
Position Position
Value string
Data []rune
}
func (i *Integer) Pos() int {
return i.Position.Begin
}
func (i *Integer) End() int {
return i.Position.End
}
func (i *Integer) Source() string {
return string(i.Data)
}
func (i *Integer) Int() (int64, error) {
return strconv.ParseInt(i.Value, 10, 64)
}
type Float struct {
Position Position
Value string
Data []rune
}
func (f *Float) Pos() int {
return f.Position.Begin
}
func (f *Float) End() int {
return f.Position.End
}
func (f *Float) Source() string {
return string(f.Data)
}
func (f *Float) Float() (float64, error) {
return strconv.ParseFloat(f.Value, 64)
}
type Boolean struct {
Position Position
Value string
Data []rune
}
func (b *Boolean) Pos() int {
return b.Position.Begin
}
func (b *Boolean) End() int {
return b.Position.End
}
func (b *Boolean) Source() string {
return string(b.Data)
}
func (b *Boolean) Boolean() (bool, error) {
return strconv.ParseBool(b.Value)
}
type Datetime struct {
Position Position
Value string
Data []rune
}
func (d *Datetime) Pos() int {
return d.Position.Begin
}
func (d *Datetime) End() int {
return d.Position.End
}
func (d *Datetime) Source() string {
return string(d.Data)
}
func (d *Datetime) Time() (time.Time, error) {
return time.Parse(time.RFC3339Nano, d.Value)
}
type Array struct {
Position Position
Value []Value
Data []rune
}
func (a *Array) Pos() int {
return a.Position.Begin
}
func (a *Array) End() int {
return a.Position.End
}
func (a *Array) Source() string {
return string(a.Data)
}
type TableType uint8
const (
TableTypeNormal TableType = iota
TableTypeArray
)
var tableTypes = [...]string{
"normal",
"array",
}
func (t TableType) String() string {
return tableTypes[t]
}
type Table struct {
Position Position
Line int
Name string
Fields map[string]interface{}
Type TableType
Data []rune
}
func (t *Table) Pos() int {
return t.Position.Begin
}
func (t *Table) End() int {
return t.Position.End
}
func (t *Table) Source() string {
return string(t.Data)
}
type KeyValue struct {
Key string
Value Value
Line int
}

View File

@@ -1,649 +0,0 @@
package toml
import (
"fmt"
"reflect"
"strconv"
"strings"
"github.com/tendermint/tendermint/Godeps/_workspace/src/github.com/naoina/toml/ast"
)
const (
tableSeparator = '.'
)
var (
escapeReplacer = strings.NewReplacer(
"\b", "\\n",
"\f", "\\f",
"\n", "\\n",
"\r", "\\r",
"\t", "\\t",
)
underscoreReplacer = strings.NewReplacer(
"_", "",
)
)
// Unmarshal parses the TOML data and stores the result in the value pointed to by v.
//
// Unmarshal will mapped to v that according to following rules:
//
// TOML strings to string
// TOML integers to any int type
// TOML floats to float32 or float64
// TOML booleans to bool
// TOML datetimes to time.Time
// TOML arrays to any type of slice or []interface{}
// TOML tables to struct
// TOML array of tables to slice of struct
func Unmarshal(data []byte, v interface{}) error {
table, err := Parse(data)
if err != nil {
return err
}
if err := UnmarshalTable(table, v); err != nil {
return fmt.Errorf("toml: unmarshal: %v", err)
}
return nil
}
// Unmarshaler is the interface implemented by objects that can unmarshal a
// TOML description of themselves.
// The input can be assumed to be a valid encoding of a TOML value.
// UnmarshalJSON must copy the TOML data if it wishes to retain the data after
// returning.
type Unmarshaler interface {
UnmarshalTOML([]byte) error
}
// UnmarshalTable applies the contents of an ast.Table to the value pointed at by v.
//
// UnmarshalTable will mapped to v that according to following rules:
//
// TOML strings to string
// TOML integers to any int type
// TOML floats to float32 or float64
// TOML booleans to bool
// TOML datetimes to time.Time
// TOML arrays to any type of slice or []interface{}
// TOML tables to struct
// TOML array of tables to slice of struct
func UnmarshalTable(t *ast.Table, v interface{}) (err error) {
if v == nil {
return fmt.Errorf("v must not be nil")
}
rv := reflect.ValueOf(v)
if kind := rv.Kind(); kind != reflect.Ptr && kind != reflect.Map {
return fmt.Errorf("v must be a pointer or map")
}
for rv.Kind() == reflect.Ptr {
rv = rv.Elem()
}
for key, val := range t.Fields {
switch av := val.(type) {
case *ast.KeyValue:
fv, fieldName, found := findField(rv, key)
if !found {
return fmt.Errorf("line %d: field corresponding to `%s' is not defined in `%T'", av.Line, key, v)
}
switch fv.Kind() {
case reflect.Map:
mv := reflect.New(fv.Type().Elem()).Elem()
if err := UnmarshalTable(t, mv.Addr().Interface()); err != nil {
return err
}
fv.SetMapIndex(reflect.ValueOf(fieldName), mv)
default:
if err := setValue(fv, av.Value); err != nil {
return fmt.Errorf("line %d: %v.%s: %v", av.Line, rv.Type(), fieldName, err)
}
if rv.Kind() == reflect.Map {
rv.SetMapIndex(reflect.ValueOf(fieldName), fv)
}
}
case *ast.Table:
fv, fieldName, found := findField(rv, key)
if !found {
return fmt.Errorf("line %d: field corresponding to `%s' is not defined in `%T'", av.Line, key, v)
}
if err, ok := setUnmarshaler(fv, string(av.Data)); ok {
if err != nil {
return err
}
continue
}
for fv.Kind() == reflect.Ptr {
fv.Set(reflect.New(fv.Type().Elem()))
fv = fv.Elem()
}
switch fv.Kind() {
case reflect.Struct:
vv := reflect.New(fv.Type()).Elem()
if err := UnmarshalTable(av, vv.Addr().Interface()); err != nil {
return err
}
fv.Set(vv)
if rv.Kind() == reflect.Map {
rv.SetMapIndex(reflect.ValueOf(fieldName), fv)
}
case reflect.Map:
mv := reflect.MakeMap(fv.Type())
if err := UnmarshalTable(av, mv.Interface()); err != nil {
return err
}
fv.Set(mv)
default:
return fmt.Errorf("line %d: `%v.%s' must be struct or map, but %v given", av.Line, rv.Type(), fieldName, fv.Kind())
}
case []*ast.Table:
fv, fieldName, found := findField(rv, key)
if !found {
return fmt.Errorf("line %d: field corresponding to `%s' is not defined in `%T'", av[0].Line, key, v)
}
data := make([]string, 0, len(av))
for _, tbl := range av {
data = append(data, string(tbl.Data))
}
if err, ok := setUnmarshaler(fv, strings.Join(data, "\n")); ok {
if err != nil {
return err
}
continue
}
t := fv.Type().Elem()
pc := 0
for ; t.Kind() == reflect.Ptr; pc++ {
t = t.Elem()
}
if fv.Kind() != reflect.Slice {
return fmt.Errorf("line %d: `%v.%s' must be slice type, but %v given", av[0].Line, rv.Type(), fieldName, fv.Kind())
}
for _, tbl := range av {
var vv reflect.Value
switch t.Kind() {
case reflect.Map:
vv = reflect.MakeMap(t)
if err := UnmarshalTable(tbl, vv.Interface()); err != nil {
return err
}
default:
vv = reflect.New(t).Elem()
if err := UnmarshalTable(tbl, vv.Addr().Interface()); err != nil {
return err
}
}
for i := 0; i < pc; i++ {
vv = vv.Addr()
pv := reflect.New(vv.Type()).Elem()
pv.Set(vv)
vv = pv
}
fv.Set(reflect.Append(fv, vv))
}
if rv.Kind() == reflect.Map {
rv.SetMapIndex(reflect.ValueOf(fieldName), fv)
}
default:
return fmt.Errorf("BUG: unknown type `%T'", t)
}
}
return nil
}
func setUnmarshaler(lhs reflect.Value, data string) (error, bool) {
for lhs.Kind() == reflect.Ptr {
lhs.Set(reflect.New(lhs.Type().Elem()))
lhs = lhs.Elem()
}
if lhs.CanAddr() {
if u, ok := lhs.Addr().Interface().(Unmarshaler); ok {
return u.UnmarshalTOML([]byte(data)), true
}
}
return nil, false
}
func setValue(lhs reflect.Value, val ast.Value) error {
for lhs.Kind() == reflect.Ptr {
lhs.Set(reflect.New(lhs.Type().Elem()))
lhs = lhs.Elem()
}
if err, ok := setUnmarshaler(lhs, val.Source()); ok {
return err
}
switch v := val.(type) {
case *ast.Integer:
if err := setInt(lhs, v); err != nil {
return err
}
case *ast.Float:
if err := setFloat(lhs, v); err != nil {
return err
}
case *ast.String:
if err := setString(lhs, v); err != nil {
return err
}
case *ast.Boolean:
if err := setBoolean(lhs, v); err != nil {
return err
}
case *ast.Datetime:
if err := setDatetime(lhs, v); err != nil {
return err
}
case *ast.Array:
if err := setArray(lhs, v); err != nil {
return err
}
}
return nil
}
func setInt(fv reflect.Value, v *ast.Integer) error {
i, err := v.Int()
if err != nil {
return err
}
switch fv.Kind() {
case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
if fv.OverflowInt(i) {
return &errorOutOfRange{fv.Kind(), i}
}
fv.SetInt(i)
case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64:
fv.SetUint(uint64(i))
case reflect.Interface:
fv.Set(reflect.ValueOf(i))
default:
return fmt.Errorf("`%v' is not any types of int", fv.Type())
}
return nil
}
func setFloat(fv reflect.Value, v *ast.Float) error {
f, err := v.Float()
if err != nil {
return err
}
switch fv.Kind() {
case reflect.Float32, reflect.Float64:
if fv.OverflowFloat(f) {
return &errorOutOfRange{fv.Kind(), f}
}
fv.SetFloat(f)
case reflect.Interface:
fv.Set(reflect.ValueOf(f))
default:
return fmt.Errorf("`%v' is not float32 or float64", fv.Type())
}
return nil
}
func setString(fv reflect.Value, v *ast.String) error {
return set(fv, v.Value)
}
func setBoolean(fv reflect.Value, v *ast.Boolean) error {
b, err := v.Boolean()
if err != nil {
return err
}
return set(fv, b)
}
func setDatetime(fv reflect.Value, v *ast.Datetime) error {
tm, err := v.Time()
if err != nil {
return err
}
return set(fv, tm)
}
func setArray(fv reflect.Value, v *ast.Array) error {
if len(v.Value) == 0 {
return nil
}
typ := reflect.TypeOf(v.Value[0])
for _, vv := range v.Value[1:] {
if typ != reflect.TypeOf(vv) {
return fmt.Errorf("array cannot contain multiple types")
}
}
sliceType := fv.Type()
if fv.Kind() == reflect.Interface {
sliceType = reflect.SliceOf(sliceType)
}
slice := reflect.MakeSlice(sliceType, 0, len(v.Value))
t := sliceType.Elem()
for _, vv := range v.Value {
tmp := reflect.New(t).Elem()
if err := setValue(tmp, vv); err != nil {
return err
}
slice = reflect.Append(slice, tmp)
}
fv.Set(slice)
return nil
}
func set(fv reflect.Value, v interface{}) error {
rhs := reflect.ValueOf(v)
if !rhs.Type().AssignableTo(fv.Type()) {
return fmt.Errorf("`%v' type is not assignable to `%v' type", rhs.Type(), fv.Type())
}
fv.Set(rhs)
return nil
}
type stack struct {
key string
table *ast.Table
}
type toml struct {
table *ast.Table
line int
currentTable *ast.Table
s string
key string
val ast.Value
arr *array
tableMap map[string]*ast.Table
stack []*stack
skip bool
}
func (p *toml) init() {
p.line = 1
p.table = &ast.Table{
Line: p.line,
Type: ast.TableTypeNormal,
}
p.tableMap = map[string]*ast.Table{
"": p.table,
}
p.currentTable = p.table
}
func (p *toml) Error(err error) {
panic(convertError{fmt.Errorf("toml: line %d: %v", p.line, err)})
}
func (p *tomlParser) SetTime(begin, end int) {
p.val = &ast.Datetime{
Position: ast.Position{Begin: begin, End: end},
Data: p.buffer[begin:end],
Value: string(p.buffer[begin:end]),
}
}
func (p *tomlParser) SetFloat64(begin, end int) {
p.val = &ast.Float{
Position: ast.Position{Begin: begin, End: end},
Data: p.buffer[begin:end],
Value: underscoreReplacer.Replace(string(p.buffer[begin:end])),
}
}
func (p *tomlParser) SetInt64(begin, end int) {
p.val = &ast.Integer{
Position: ast.Position{Begin: begin, End: end},
Data: p.buffer[begin:end],
Value: underscoreReplacer.Replace(string(p.buffer[begin:end])),
}
}
func (p *tomlParser) SetString(begin, end int) {
p.val = &ast.String{
Position: ast.Position{Begin: begin, End: end},
Data: p.buffer[begin:end],
Value: p.s,
}
p.s = ""
}
func (p *tomlParser) SetBool(begin, end int) {
p.val = &ast.Boolean{
Position: ast.Position{Begin: begin, End: end},
Data: p.buffer[begin:end],
Value: string(p.buffer[begin:end]),
}
}
func (p *tomlParser) StartArray() {
if p.arr == nil {
p.arr = &array{line: p.line, current: &ast.Array{}}
return
}
p.arr.child = &array{parent: p.arr, line: p.line, current: &ast.Array{}}
p.arr = p.arr.child
}
func (p *tomlParser) AddArrayVal() {
if p.arr.current == nil {
p.arr.current = &ast.Array{}
}
p.arr.current.Value = append(p.arr.current.Value, p.val)
}
func (p *tomlParser) SetArray(begin, end int) {
p.arr.current.Position = ast.Position{Begin: begin, End: end}
p.arr.current.Data = p.buffer[begin:end]
p.val = p.arr.current
p.arr = p.arr.parent
}
func (p *toml) SetTable(buf []rune, begin, end int) {
p.setTable(p.table, buf, begin, end)
}
func (p *toml) setTable(t *ast.Table, buf []rune, begin, end int) {
name := string(buf[begin:end])
names := splitTableKey(name)
if t, exists := p.tableMap[name]; exists {
if lt := p.tableMap[names[len(names)-1]]; t.Type == ast.TableTypeArray || lt != nil && lt.Type == ast.TableTypeNormal {
p.Error(fmt.Errorf("table `%s' is in conflict with %v table in line %d", name, t.Type, t.Line))
}
}
t, err := p.lookupTable(t, names)
if err != nil {
p.Error(err)
}
p.currentTable = t
p.tableMap[name] = p.currentTable
}
func (p *tomlParser) SetTableString(begin, end int) {
p.currentTable.Data = p.buffer[begin:end]
p.currentTable.Position.Begin = begin
p.currentTable.Position.End = end
}
func (p *toml) SetArrayTable(buf []rune, begin, end int) {
p.setArrayTable(p.table, buf, begin, end)
}
func (p *toml) setArrayTable(t *ast.Table, buf []rune, begin, end int) {
name := string(buf[begin:end])
if t, exists := p.tableMap[name]; exists && t.Type == ast.TableTypeNormal {
p.Error(fmt.Errorf("table `%s' is in conflict with %v table in line %d", name, t.Type, t.Line))
}
names := splitTableKey(name)
t, err := p.lookupTable(t, names[:len(names)-1])
if err != nil {
p.Error(err)
}
last := names[len(names)-1]
tbl := &ast.Table{
Position: ast.Position{begin, end},
Line: p.line,
Name: last,
Type: ast.TableTypeArray,
}
switch v := t.Fields[last].(type) {
case nil:
if t.Fields == nil {
t.Fields = make(map[string]interface{})
}
t.Fields[last] = []*ast.Table{tbl}
case []*ast.Table:
t.Fields[last] = append(v, tbl)
case *ast.KeyValue:
p.Error(fmt.Errorf("key `%s' is in conflict with line %d", last, v.Line))
default:
p.Error(fmt.Errorf("BUG: key `%s' is in conflict but it's unknown type `%T'", last, v))
}
p.currentTable = tbl
p.tableMap[name] = p.currentTable
}
func (p *toml) StartInlineTable() {
p.skip = false
p.stack = append(p.stack, &stack{p.key, p.currentTable})
buf := []rune(p.key)
if p.arr == nil {
p.setTable(p.currentTable, buf, 0, len(buf))
} else {
p.setArrayTable(p.currentTable, buf, 0, len(buf))
}
}
func (p *toml) EndInlineTable() {
st := p.stack[len(p.stack)-1]
p.key, p.currentTable = st.key, st.table
p.stack[len(p.stack)-1] = nil
p.stack = p.stack[:len(p.stack)-1]
p.skip = true
}
func (p *toml) AddLineCount(i int) {
p.line += i
}
func (p *toml) SetKey(buf []rune, begin, end int) {
p.key = string(buf[begin:end])
}
func (p *toml) AddKeyValue() {
if p.skip {
p.skip = false
return
}
if val, exists := p.currentTable.Fields[p.key]; exists {
switch v := val.(type) {
case *ast.Table:
p.Error(fmt.Errorf("key `%s' is in conflict with %v table in line %d", p.key, v.Type, v.Line))
case *ast.KeyValue:
p.Error(fmt.Errorf("key `%s' is in conflict with line %d", p.key, v.Line))
default:
p.Error(fmt.Errorf("BUG: key `%s' is in conflict but it's unknown type `%T'", p.key, v))
}
}
if p.currentTable.Fields == nil {
p.currentTable.Fields = make(map[string]interface{})
}
p.currentTable.Fields[p.key] = &ast.KeyValue{
Key: p.key,
Value: p.val,
Line: p.line,
}
}
func (p *toml) SetBasicString(buf []rune, begin, end int) {
p.s = p.unquote(string(buf[begin:end]))
}
func (p *toml) SetMultilineString() {
p.s = p.unquote(`"` + escapeReplacer.Replace(strings.TrimLeft(p.s, "\r\n")) + `"`)
}
func (p *toml) AddMultilineBasicBody(buf []rune, begin, end int) {
p.s += string(buf[begin:end])
}
func (p *toml) SetLiteralString(buf []rune, begin, end int) {
p.s = string(buf[begin:end])
}
func (p *toml) SetMultilineLiteralString(buf []rune, begin, end int) {
p.s = strings.TrimLeft(string(buf[begin:end]), "\r\n")
}
func (p *toml) unquote(s string) string {
s, err := strconv.Unquote(s)
if err != nil {
p.Error(err)
}
return s
}
func (p *toml) lookupTable(t *ast.Table, keys []string) (*ast.Table, error) {
for _, s := range keys {
val, exists := t.Fields[s]
if !exists {
tbl := &ast.Table{
Line: p.line,
Name: s,
Type: ast.TableTypeNormal,
}
if t.Fields == nil {
t.Fields = make(map[string]interface{})
}
t.Fields[s] = tbl
t = tbl
continue
}
switch v := val.(type) {
case *ast.Table:
t = v
case []*ast.Table:
t = v[len(v)-1]
case *ast.KeyValue:
return nil, fmt.Errorf("key `%s' is in conflict with line %d", s, v.Line)
default:
return nil, fmt.Errorf("BUG: key `%s' is in conflict but it's unknown type `%T'", s, v)
}
}
return t, nil
}
func splitTableKey(tk string) []string {
key := make([]byte, 0, 1)
keys := make([]string, 0, 1)
inQuote := false
for i := 0; i < len(tk); i++ {
k := tk[i]
switch {
case k == tableSeparator && !inQuote:
keys = append(keys, string(key))
key = key[:0] // reuse buffer.
case k == '"':
inQuote = !inQuote
case (k == ' ' || k == '\t') && !inQuote:
// skip.
default:
key = append(key, k)
}
}
keys = append(keys, string(key))
return keys
}
type convertError struct {
err error
}
func (e convertError) Error() string {
return e.err.Error()
}
type array struct {
parent *array
child *array
current *ast.Array
line int
}

Some files were not shown because too many files have changed in this diff Show More