From 83d16574444d0b389755c9003e74a90d2ab7ca2e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Felf=C3=B6ldi=20Zsolt?= Date: Tue, 9 Jan 2018 11:41:59 +0100 Subject: [PATCH 01/13] les: fix les/1 CHT compatibility issue (#15692) --- les/handler.go | 4 ++-- les/peer.go | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/les/handler.go b/les/handler.go index e310942ba0ae..d627c3e1845e 100644 --- a/les/handler.go +++ b/les/handler.go @@ -846,8 +846,8 @@ func (pm *ProtocolManager) handleMsg(p *peer) error { } if header := pm.blockchain.GetHeaderByNumber(req.BlockNum); header != nil { - sectionHead := core.GetCanonicalHash(pm.chainDb, (req.ChtNum+1)*light.ChtV1Frequency-1) - if root := light.GetChtRoot(pm.chainDb, req.ChtNum, sectionHead); root != (common.Hash{}) { + sectionHead := core.GetCanonicalHash(pm.chainDb, req.ChtNum*light.ChtV1Frequency-1) + if root := light.GetChtRoot(pm.chainDb, req.ChtNum-1, sectionHead); root != (common.Hash{}) { if tr, _ := trie.New(root, trieDb); tr != nil { var encNumber [8]byte binary.BigEndian.PutUint64(encNumber[:], req.BlockNum) diff --git a/les/peer.go b/les/peer.go index 04d747a6b3a4..b72c80d35a1d 100644 --- a/les/peer.go +++ b/les/peer.go @@ -296,7 +296,7 @@ func (p *peer) RequestHelperTrieProofs(reqID, cost uint64, reqs []HelperTrieReq) } blockNum := binary.BigEndian.Uint64(req.Key) // convert HelperTrie request to old CHT request - reqsV1[i] = ChtReq{ChtNum: (req.TrieIdx+1)*(light.ChtFrequency/light.ChtV1Frequency) - 1, BlockNum: blockNum, FromLevel: req.FromLevel} + reqsV1[i] = ChtReq{ChtNum: (req.TrieIdx + 1) * (light.ChtFrequency / light.ChtV1Frequency), BlockNum: blockNum, FromLevel: req.FromLevel} } return sendRequest(p.rw, GetHeaderProofsMsg, reqID, cost, reqsV1) case lpv2: From 3a5a5599dd387e70da2df3240fa5553722851bb9 Mon Sep 17 00:00:00 2001 From: gary rong Date: Wed, 10 Jan 2018 16:58:03 +0800 Subject: [PATCH 02/13] consensus/ethash: fix byzantium difficulty comment typo (#15842) --- consensus/ethash/consensus.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/consensus/ethash/consensus.go b/consensus/ethash/consensus.go index 0af68c31ab69..82d23c92b604 100644 --- a/consensus/ethash/consensus.go +++ b/consensus/ethash/consensus.go @@ -347,7 +347,7 @@ func calcDifficultyByzantium(time uint64, parent *types.Header) *big.Int { if x.Cmp(bigMinus99) < 0 { x.Set(bigMinus99) } - // (parent_diff + parent_diff // 2048 * max(1 - (block_timestamp - parent_timestamp) // 10, -99)) + // parent_diff + (parent_diff / 2048 * max((2 if len(parent.uncles) else 1) - ((timestamp - parent.timestamp) // 9), -99)) y.Div(parent.Difficulty, params.DifficultyBoundDivisor) x.Mul(y, x) x.Add(parent.Difficulty, x) From b06e20bc7c498adef658b58f10f5c729b46d84f9 Mon Sep 17 00:00:00 2001 From: Nick Johnson Date: Wed, 10 Jan 2018 12:57:36 +0000 Subject: [PATCH 03/13] eth/gasprice: set default percentile to 60%, count blocks instead of transactions (#15828) The first should address a long term issue where we recommend a gas price that is greater than that required for 50% of transactions in recent blocks, which can lead to gas price inflation as people take this figure and add a margin to it, resulting in a positive feedback loop. --- eth/config.go | 4 ++-- eth/gasprice/gasprice.go | 49 ++++++++++++++++++++++++++-------------- 2 files changed, 34 insertions(+), 19 deletions(-) diff --git a/eth/config.go b/eth/config.go index 383cd6783c12..4399560fa391 100644 --- a/eth/config.go +++ b/eth/config.go @@ -49,8 +49,8 @@ var DefaultConfig = Config{ TxPool: core.DefaultTxPoolConfig, GPO: gasprice.Config{ - Blocks: 10, - Percentile: 50, + Blocks: 20, + Percentile: 60, }, } diff --git a/eth/gasprice/gasprice.go b/eth/gasprice/gasprice.go index c662348e165b..54325692c6ef 100644 --- a/eth/gasprice/gasprice.go +++ b/eth/gasprice/gasprice.go @@ -23,6 +23,7 @@ import ( "sync" "github.com/ethereum/go-ethereum/common" + "github.com/ethereum/go-ethereum/core/types" "github.com/ethereum/go-ethereum/internal/ethapi" "github.com/ethereum/go-ethereum/params" "github.com/ethereum/go-ethereum/rpc" @@ -101,9 +102,9 @@ func (gpo *Oracle) SuggestPrice(ctx context.Context) (*big.Int, error) { ch := make(chan getBlockPricesResult, gpo.checkBlocks) sent := 0 exp := 0 - var txPrices []*big.Int + var blockPrices []*big.Int for sent < gpo.checkBlocks && blockNum > 0 { - go gpo.getBlockPrices(ctx, blockNum, ch) + go gpo.getBlockPrices(ctx, types.MakeSigner(gpo.backend.ChainConfig(), big.NewInt(int64(blockNum))), blockNum, ch) sent++ exp++ blockNum-- @@ -115,8 +116,8 @@ func (gpo *Oracle) SuggestPrice(ctx context.Context) (*big.Int, error) { return lastPrice, res.err } exp-- - if len(res.prices) > 0 { - txPrices = append(txPrices, res.prices...) + if res.price != nil { + blockPrices = append(blockPrices, res.price) continue } if maxEmpty > 0 { @@ -124,16 +125,16 @@ func (gpo *Oracle) SuggestPrice(ctx context.Context) (*big.Int, error) { continue } if blockNum > 0 && sent < gpo.maxBlocks { - go gpo.getBlockPrices(ctx, blockNum, ch) + go gpo.getBlockPrices(ctx, types.MakeSigner(gpo.backend.ChainConfig(), big.NewInt(int64(blockNum))), blockNum, ch) sent++ exp++ blockNum-- } } price := lastPrice - if len(txPrices) > 0 { - sort.Sort(bigIntArray(txPrices)) - price = txPrices[(len(txPrices)-1)*gpo.percentile/100] + if len(blockPrices) > 0 { + sort.Sort(bigIntArray(blockPrices)) + price = blockPrices[(len(blockPrices)-1)*gpo.percentile/100] } if price.Cmp(maxPrice) > 0 { price = new(big.Int).Set(maxPrice) @@ -147,24 +148,38 @@ func (gpo *Oracle) SuggestPrice(ctx context.Context) (*big.Int, error) { } type getBlockPricesResult struct { - prices []*big.Int - err error + price *big.Int + err error } -// getLowestPrice calculates the lowest transaction gas price in a given block +type transactionsByGasPrice []*types.Transaction + +func (t transactionsByGasPrice) Len() int { return len(t) } +func (t transactionsByGasPrice) Swap(i, j int) { t[i], t[j] = t[j], t[i] } +func (t transactionsByGasPrice) Less(i, j int) bool { return t[i].GasPrice().Cmp(t[j].GasPrice()) < 0 } + +// getBlockPrices calculates the lowest transaction gas price in a given block // and sends it to the result channel. If the block is empty, price is nil. -func (gpo *Oracle) getBlockPrices(ctx context.Context, blockNum uint64, ch chan getBlockPricesResult) { +func (gpo *Oracle) getBlockPrices(ctx context.Context, signer types.Signer, blockNum uint64, ch chan getBlockPricesResult) { block, err := gpo.backend.BlockByNumber(ctx, rpc.BlockNumber(blockNum)) if block == nil { ch <- getBlockPricesResult{nil, err} return } - txs := block.Transactions() - prices := make([]*big.Int, len(txs)) - for i, tx := range txs { - prices[i] = tx.GasPrice() + + blockTxs := block.Transactions() + txs := make([]*types.Transaction, len(blockTxs)) + copy(txs, blockTxs) + sort.Sort(transactionsByGasPrice(txs)) + + for _, tx := range txs { + sender, err := types.Sender(signer, tx) + if err == nil && sender != block.Coinbase() { + ch <- getBlockPricesResult{tx.GasPrice(), nil} + return + } } - ch <- getBlockPricesResult{prices, nil} + ch <- getBlockPricesResult{nil, nil} } type bigIntArray []*big.Int From 023769d9d48fab92c1d4d7d97c0a08ae3ef2cdca Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jean-Andr=C3=A9=20Santoni?= Date: Thu, 11 Jan 2018 22:02:01 +0700 Subject: [PATCH 04/13] travis.yml: remove alias for 'cd' to avoid hang on macOS (#15849) This works around travis-ci/travis-ci#8703. --- .travis.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.travis.yml b/.travis.yml index bc296bf2f161..ba62b87bf55b 100644 --- a/.travis.yml +++ b/.travis.yml @@ -40,6 +40,7 @@ matrix: - os: osx go: 1.9.x script: + - unset -f cd # workaround for https://github.com/travis-ci/travis-ci/issues/8703 - brew update - brew install caskroom/cask/brew-cask - brew cask install osxfuse From 56152b31ac251d1cc68fcddbdad159ba5234c415 Mon Sep 17 00:00:00 2001 From: Ricardo Domingos Date: Thu, 11 Jan 2018 21:55:21 +0100 Subject: [PATCH 05/13] common/fdlimit: Move fdlimit files to separate package (#15850) * common/fdlimit: Move fdlimit files to separate package When go-ethereum is used as a library the calling program need to set the FD limit. This commit extract fdlimit files to a separate package so it can be used outside of go-ethereum. * common/fdlimit: Remove FdLimit from functions signature * common/fdlimit: Rename fdlimit functions --- cmd/utils/flags.go | 5 +++-- .../fdlimit}/fdlimit_freebsd.go | 14 +++++++------- {cmd/utils => common/fdlimit}/fdlimit_test.go | 10 +++++----- {cmd/utils => common/fdlimit}/fdlimit_unix.go | 14 +++++++------- .../fdlimit}/fdlimit_windows.go | 18 +++++++++--------- 5 files changed, 31 insertions(+), 30 deletions(-) rename {cmd/utils => common/fdlimit}/fdlimit_freebsd.go (81%) rename {cmd/utils => common/fdlimit}/fdlimit_test.go (85%) rename {cmd/utils => common/fdlimit}/fdlimit_unix.go (80%) rename {cmd/utils => common/fdlimit}/fdlimit_windows.go (74%) diff --git a/cmd/utils/flags.go b/cmd/utils/flags.go index edf3dc2c210d..94ab64c2e069 100644 --- a/cmd/utils/flags.go +++ b/cmd/utils/flags.go @@ -31,6 +31,7 @@ import ( "github.com/ethereum/go-ethereum/accounts" "github.com/ethereum/go-ethereum/accounts/keystore" "github.com/ethereum/go-ethereum/common" + "github.com/ethereum/go-ethereum/common/fdlimit" "github.com/ethereum/go-ethereum/consensus" "github.com/ethereum/go-ethereum/consensus/clique" "github.com/ethereum/go-ethereum/consensus/ethash" @@ -721,10 +722,10 @@ func setIPC(ctx *cli.Context, cfg *node.Config) { // makeDatabaseHandles raises out the number of allowed file handles per process // for Geth and returns half of the allowance to assign to the database. func makeDatabaseHandles() int { - if err := raiseFdLimit(2048); err != nil { + if err := fdlimit.Raise(2048); err != nil { Fatalf("Failed to raise file descriptor allowance: %v", err) } - limit, err := getFdLimit() + limit, err := fdlimit.Current() if err != nil { Fatalf("Failed to retrieve file descriptor allowance: %v", err) } diff --git a/cmd/utils/fdlimit_freebsd.go b/common/fdlimit/fdlimit_freebsd.go similarity index 81% rename from cmd/utils/fdlimit_freebsd.go rename to common/fdlimit/fdlimit_freebsd.go index f9ed8937ee9d..25caaafe21e5 100644 --- a/cmd/utils/fdlimit_freebsd.go +++ b/common/fdlimit/fdlimit_freebsd.go @@ -16,7 +16,7 @@ // +build freebsd -package utils +package fdlimit import "syscall" @@ -24,9 +24,9 @@ import "syscall" // but Rlimit fields have type int64 on FreeBSD so it needs // an extra conversion. -// raiseFdLimit tries to maximize the file descriptor allowance of this process +// Raise tries to maximize the file descriptor allowance of this process // to the maximum hard-limit allowed by the OS. -func raiseFdLimit(max uint64) error { +func Raise(max uint64) error { // Get the current limit var limit syscall.Rlimit if err := syscall.Getrlimit(syscall.RLIMIT_NOFILE, &limit); err != nil { @@ -43,9 +43,9 @@ func raiseFdLimit(max uint64) error { return nil } -// getFdLimit retrieves the number of file descriptors allowed to be opened by this +// Current retrieves the number of file descriptors allowed to be opened by this // process. -func getFdLimit() (int, error) { +func Current() (int, error) { var limit syscall.Rlimit if err := syscall.Getrlimit(syscall.RLIMIT_NOFILE, &limit); err != nil { return 0, err @@ -53,9 +53,9 @@ func getFdLimit() (int, error) { return int(limit.Cur), nil } -// getFdMaxLimit retrieves the maximum number of file descriptors this process is +// Maximum retrieves the maximum number of file descriptors this process is // allowed to request for itself. -func getFdMaxLimit() (int, error) { +func Maximum() (int, error) { var limit syscall.Rlimit if err := syscall.Getrlimit(syscall.RLIMIT_NOFILE, &limit); err != nil { return 0, err diff --git a/cmd/utils/fdlimit_test.go b/common/fdlimit/fdlimit_test.go similarity index 85% rename from cmd/utils/fdlimit_test.go rename to common/fdlimit/fdlimit_test.go index 48489cf4c71f..05e9f0b6585d 100644 --- a/cmd/utils/fdlimit_test.go +++ b/common/fdlimit/fdlimit_test.go @@ -14,7 +14,7 @@ // You should have received a copy of the GNU General Public License // along with go-ethereum. If not, see . -package utils +package fdlimit import ( "fmt" @@ -25,7 +25,7 @@ import ( // per this process can be retrieved. func TestFileDescriptorLimits(t *testing.T) { target := 4096 - hardlimit, err := getFdMaxLimit() + hardlimit, err := Maximum() if err != nil { t.Fatal(err) } @@ -33,13 +33,13 @@ func TestFileDescriptorLimits(t *testing.T) { t.Skip(fmt.Sprintf("system limit is less than desired test target: %d < %d", hardlimit, target)) } - if limit, err := getFdLimit(); err != nil || limit <= 0 { + if limit, err := Current(); err != nil || limit <= 0 { t.Fatalf("failed to retrieve file descriptor limit (%d): %v", limit, err) } - if err := raiseFdLimit(uint64(target)); err != nil { + if err := Raise(uint64(target)); err != nil { t.Fatalf("failed to raise file allowance") } - if limit, err := getFdLimit(); err != nil || limit < target { + if limit, err := Current(); err != nil || limit < target { t.Fatalf("failed to retrieve raised descriptor limit (have %v, want %v): %v", limit, target, err) } } diff --git a/cmd/utils/fdlimit_unix.go b/common/fdlimit/fdlimit_unix.go similarity index 80% rename from cmd/utils/fdlimit_unix.go rename to common/fdlimit/fdlimit_unix.go index c08d1fab08cf..27c7e783f706 100644 --- a/cmd/utils/fdlimit_unix.go +++ b/common/fdlimit/fdlimit_unix.go @@ -16,13 +16,13 @@ // +build linux darwin netbsd openbsd solaris -package utils +package fdlimit import "syscall" -// raiseFdLimit tries to maximize the file descriptor allowance of this process +// Raise tries to maximize the file descriptor allowance of this process // to the maximum hard-limit allowed by the OS. -func raiseFdLimit(max uint64) error { +func Raise(max uint64) error { // Get the current limit var limit syscall.Rlimit if err := syscall.Getrlimit(syscall.RLIMIT_NOFILE, &limit); err != nil { @@ -39,9 +39,9 @@ func raiseFdLimit(max uint64) error { return nil } -// getFdLimit retrieves the number of file descriptors allowed to be opened by this +// Current retrieves the number of file descriptors allowed to be opened by this // process. -func getFdLimit() (int, error) { +func Current() (int, error) { var limit syscall.Rlimit if err := syscall.Getrlimit(syscall.RLIMIT_NOFILE, &limit); err != nil { return 0, err @@ -49,9 +49,9 @@ func getFdLimit() (int, error) { return int(limit.Cur), nil } -// getFdMaxLimit retrieves the maximum number of file descriptors this process is +// Maximum retrieves the maximum number of file descriptors this process is // allowed to request for itself. -func getFdMaxLimit() (int, error) { +func Maximum() (int, error) { var limit syscall.Rlimit if err := syscall.Getrlimit(syscall.RLIMIT_NOFILE, &limit); err != nil { return 0, err diff --git a/cmd/utils/fdlimit_windows.go b/common/fdlimit/fdlimit_windows.go similarity index 74% rename from cmd/utils/fdlimit_windows.go rename to common/fdlimit/fdlimit_windows.go index f239683d2adb..efcd3220eae8 100644 --- a/cmd/utils/fdlimit_windows.go +++ b/common/fdlimit/fdlimit_windows.go @@ -14,13 +14,13 @@ // You should have received a copy of the GNU General Public License // along with go-ethereum. If not, see . -package utils +package fdlimit import "errors" -// raiseFdLimit tries to maximize the file descriptor allowance of this process +// Raise tries to maximize the file descriptor allowance of this process // to the maximum hard-limit allowed by the OS. -func raiseFdLimit(max uint64) error { +func Raise(max uint64) error { // This method is NOP by design: // * Linux/Darwin counterparts need to manually increase per process limits // * On Windows Go uses the CreateFile API, which is limited to 16K files, non @@ -33,15 +33,15 @@ func raiseFdLimit(max uint64) error { return nil } -// getFdLimit retrieves the number of file descriptors allowed to be opened by this +// Current retrieves the number of file descriptors allowed to be opened by this // process. -func getFdLimit() (int, error) { - // Please see raiseFdLimit for the reason why we use hard coded 16K as the limit +func Current() (int, error) { + // Please see Raise for the reason why we use hard coded 16K as the limit return 16384, nil } -// getFdMaxLimit retrieves the maximum number of file descriptors this process is +// Maximum retrieves the maximum number of file descriptors this process is // allowed to request for itself. -func getFdMaxLimit() (int, error) { - return getFdLimit() +func Maximum() (int, error) { + return Current() } From bd0dbfa2a889972814166129e3a166cec7c71951 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?P=C3=A9ter=20Szil=C3=A1gyi?= Date: Fri, 12 Jan 2018 11:59:18 +0200 Subject: [PATCH 06/13] cmd/geth: user friendly light miner error --- cmd/geth/main.go | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/cmd/geth/main.go b/cmd/geth/main.go index bdb7fad62afb..b955bd243e87 100644 --- a/cmd/geth/main.go +++ b/cmd/geth/main.go @@ -278,9 +278,12 @@ func startNode(ctx *cli.Context, stack *node.Node) { // Start auxiliary services if enabled if ctx.GlobalBool(utils.MiningEnabledFlag.Name) || ctx.GlobalBool(utils.DeveloperFlag.Name) { // Mining only makes sense if a full Ethereum node is running + if ctx.GlobalBool(utils.LightModeFlag.Name) || ctx.GlobalString(utils.SyncModeFlag.Name) == "light" { + utils.Fatalf("Light clients do not support mining") + } var ethereum *eth.Ethereum if err := stack.Service(ðereum); err != nil { - utils.Fatalf("ethereum service not running: %v", err) + utils.Fatalf("Ethereum service not running: %v", err) } // Use a reduced number of threads if requested if threads := ctx.GlobalInt(utils.MinerThreadsFlag.Name); threads > 0 { From fd869dc839e2b3696e130224a43b9b25455ceb46 Mon Sep 17 00:00:00 2001 From: gluk256 Date: Fri, 12 Jan 2018 13:11:22 +0200 Subject: [PATCH 07/13] whisper/whisperv6: implement pow/bloom exchange protocol (#15802) This is the main feature of v6. --- whisper/whisperv6/api.go | 9 +- whisper/whisperv6/doc.go | 20 +-- whisper/whisperv6/envelope.go | 35 ++++- whisper/whisperv6/peer.go | 54 ++++++- whisper/whisperv6/peer_test.go | 105 ++++++++++--- whisper/whisperv6/whisper.go | 242 +++++++++++++++++++++++++----- whisper/whisperv6/whisper_test.go | 61 ++++++++ 7 files changed, 451 insertions(+), 75 deletions(-) diff --git a/whisper/whisperv6/api.go b/whisper/whisperv6/api.go index 3dddb69539f0..0e8490b41956 100644 --- a/whisper/whisperv6/api.go +++ b/whisper/whisperv6/api.go @@ -116,12 +116,17 @@ func (api *PublicWhisperAPI) SetMaxMessageSize(ctx context.Context, size uint32) return true, api.w.SetMaxMessageSize(size) } -// SetMinPow sets the minimum PoW for a message before it is accepted. +// SetMinPow sets the minimum PoW, and notifies the peers. func (api *PublicWhisperAPI) SetMinPoW(ctx context.Context, pow float64) (bool, error) { return true, api.w.SetMinimumPoW(pow) } -// MarkTrustedPeer marks a peer trusted. , which will allow it to send historic (expired) messages. +// SetBloomFilter sets the new value of bloom filter, and notifies the peers. +func (api *PublicWhisperAPI) SetBloomFilter(ctx context.Context, bloom hexutil.Bytes) (bool, error) { + return true, api.w.SetBloomFilter(bloom) +} + +// MarkTrustedPeer marks a peer trusted, which will allow it to send historic (expired) messages. // Note: This function is not adding new nodes, the node needs to exists as a peer. func (api *PublicWhisperAPI) MarkTrustedPeer(ctx context.Context, enode string) (bool, error) { n, err := discover.ParseNode(enode) diff --git a/whisper/whisperv6/doc.go b/whisper/whisperv6/doc.go index 2a4911d65aa3..da1b4ee5bae9 100644 --- a/whisper/whisperv6/doc.go +++ b/whisper/whisperv6/doc.go @@ -35,7 +35,6 @@ import ( ) const ( - EnvelopeVersion = uint64(0) ProtocolVersion = uint64(6) ProtocolVersionStr = "6.0" ProtocolName = "shh" @@ -52,11 +51,14 @@ const ( paddingMask = byte(3) signatureFlag = byte(4) - TopicLength = 4 - signatureLength = 65 - aesKeyLength = 32 - AESNonceLength = 12 - keyIdSize = 32 + TopicLength = 4 // in bytes + signatureLength = 65 // in bytes + aesKeyLength = 32 // in bytes + AESNonceLength = 12 // in bytes + keyIdSize = 32 // in bytes + bloomFilterSize = 64 // in bytes + + EnvelopeHeaderLength = 20 MaxMessageSize = uint32(10 * 1024 * 1024) // maximum accepted size of a message. DefaultMaxMessageSize = uint32(1024 * 1024) @@ -68,10 +70,8 @@ const ( expirationCycle = time.Second transmissionCycle = 300 * time.Millisecond - DefaultTTL = 50 // seconds - SynchAllowance = 10 // seconds - - EnvelopeHeaderLength = 20 + DefaultTTL = 50 // seconds + DefaultSyncAllowance = 10 // seconds ) type unknownVersionError uint64 diff --git a/whisper/whisperv6/envelope.go b/whisper/whisperv6/envelope.go index 676df669bf7e..9ed712b93446 100644 --- a/whisper/whisperv6/envelope.go +++ b/whisper/whisperv6/envelope.go @@ -42,9 +42,11 @@ type Envelope struct { Data []byte Nonce uint64 - pow float64 // Message-specific PoW as described in the Whisper specification. - hash common.Hash // Cached hash of the envelope to avoid rehashing every time. - // Don't access hash directly, use Hash() function instead. + pow float64 // Message-specific PoW as described in the Whisper specification. + + // the following variables should not be accessed directly, use the corresponding function instead: Hash(), Bloom() + hash common.Hash // Cached hash of the envelope to avoid rehashing every time. + bloom []byte } // size returns the size of envelope as it is sent (i.e. public fields only) @@ -227,3 +229,30 @@ func (e *Envelope) Open(watcher *Filter) (msg *ReceivedMessage) { } return msg } + +// Bloom maps 4-bytes Topic into 64-byte bloom filter with 3 bits set (at most). +func (e *Envelope) Bloom() []byte { + if e.bloom == nil { + e.bloom = TopicToBloom(e.Topic) + } + return e.bloom +} + +// TopicToBloom converts the topic (4 bytes) to the bloom filter (64 bytes) +func TopicToBloom(topic TopicType) []byte { + b := make([]byte, bloomFilterSize) + var index [3]int + for j := 0; j < 3; j++ { + index[j] = int(topic[j]) + if (topic[3] & (1 << uint(j))) != 0 { + index[j] += 256 + } + } + + for j := 0; j < 3; j++ { + byteIndex := index[j] / 8 + bitIndex := index[j] % 8 + b[byteIndex] = (1 << uint(bitIndex)) + } + return b +} diff --git a/whisper/whisperv6/peer.go b/whisper/whisperv6/peer.go index 65e0c77b0c3f..08071c0f77be 100644 --- a/whisper/whisperv6/peer.go +++ b/whisper/whisperv6/peer.go @@ -36,6 +36,7 @@ type Peer struct { trusted bool powRequirement float64 + bloomFilter []byte // may contain nil in case of full node known *set.Set // Messages already known by the peer to avoid wasting bandwidth @@ -74,8 +75,12 @@ func (p *Peer) handshake() error { // Send the handshake status message asynchronously errc := make(chan error, 1) go func() { - errc <- p2p.Send(p.ws, statusCode, ProtocolVersion) + pow := p.host.MinPow() + powConverted := math.Float64bits(pow) + bloom := p.host.BloomFilter() + errc <- p2p.SendItems(p.ws, statusCode, ProtocolVersion, powConverted, bloom) }() + // Fetch the remote status packet and verify protocol match packet, err := p.ws.ReadMsg() if err != nil { @@ -85,14 +90,42 @@ func (p *Peer) handshake() error { return fmt.Errorf("peer [%x] sent packet %x before status packet", p.ID(), packet.Code) } s := rlp.NewStream(packet.Payload, uint64(packet.Size)) - peerVersion, err := s.Uint() + _, err = s.List() if err != nil { return fmt.Errorf("peer [%x] sent bad status message: %v", p.ID(), err) } + peerVersion, err := s.Uint() + if err != nil { + return fmt.Errorf("peer [%x] sent bad status message (unable to decode version): %v", p.ID(), err) + } if peerVersion != ProtocolVersion { return fmt.Errorf("peer [%x]: protocol version mismatch %d != %d", p.ID(), peerVersion, ProtocolVersion) } - // Wait until out own status is consumed too + + // only version is mandatory, subsequent parameters are optional + powRaw, err := s.Uint() + if err == nil { + pow := math.Float64frombits(powRaw) + if math.IsInf(pow, 0) || math.IsNaN(pow) || pow < 0.0 { + return fmt.Errorf("peer [%x] sent bad status message: invalid pow", p.ID()) + } + p.powRequirement = pow + + var bloom []byte + err = s.Decode(&bloom) + if err == nil { + sz := len(bloom) + if sz != bloomFilterSize && sz != 0 { + return fmt.Errorf("peer [%x] sent bad status message: wrong bloom filter size %d", p.ID(), sz) + } + if isFullNode(bloom) { + p.bloomFilter = nil + } else { + p.bloomFilter = bloom + } + } + } + if err := <-errc; err != nil { return fmt.Errorf("peer [%x] failed to send status packet: %v", p.ID(), err) } @@ -156,7 +189,7 @@ func (p *Peer) broadcast() error { envelopes := p.host.Envelopes() bundle := make([]*Envelope, 0, len(envelopes)) for _, envelope := range envelopes { - if !p.marked(envelope) && envelope.PoW() >= p.powRequirement { + if !p.marked(envelope) && envelope.PoW() >= p.powRequirement && p.bloomMatch(envelope) { bundle = append(bundle, envelope) } } @@ -186,3 +219,16 @@ func (p *Peer) notifyAboutPowRequirementChange(pow float64) error { i := math.Float64bits(pow) return p2p.Send(p.ws, powRequirementCode, i) } + +func (p *Peer) notifyAboutBloomFilterChange(bloom []byte) error { + return p2p.Send(p.ws, bloomFilterExCode, bloom) +} + +func (p *Peer) bloomMatch(env *Envelope) bool { + if p.bloomFilter == nil { + // no filter - full node, accepts all envelops + return true + } + + return bloomFilterMatch(p.bloomFilter, env.Bloom()) +} diff --git a/whisper/whisperv6/peer_test.go b/whisper/whisperv6/peer_test.go index 599a479be490..8a65cb71432b 100644 --- a/whisper/whisperv6/peer_test.go +++ b/whisper/whisperv6/peer_test.go @@ -20,6 +20,7 @@ import ( "bytes" "crypto/ecdsa" "fmt" + mrand "math/rand" "net" "sync" "testing" @@ -87,6 +88,9 @@ var nodes [NumNodes]*TestNode var sharedKey []byte = []byte("some arbitrary data here") var sharedTopic TopicType = TopicType{0xF, 0x1, 0x2, 0} var expectedMessage []byte = []byte("per rectum ad astra") +var masterBloomFilter []byte +var masterPow = 0.00000001 +var round int = 1 func TestSimulation(t *testing.T) { // create a chain of whisper nodes, @@ -104,8 +108,13 @@ func TestSimulation(t *testing.T) { // check if each node have received and decrypted exactly one message checkPropagation(t, true) - // send protocol-level messages (powRequirementCode) and check the new PoW requirement values - powReqExchange(t) + // check if Status message was correctly decoded + checkBloomFilterExchange(t) + checkPowExchange(t) + + // send new pow and bloom exchange messages + resetParams(t) + round++ // node #1 sends one expected (decryptable) message sendMsg(t, true, 1) @@ -113,18 +122,65 @@ func TestSimulation(t *testing.T) { // check if each node (except node #0) have received and decrypted exactly one message checkPropagation(t, false) + for i := 1; i < NumNodes; i++ { + time.Sleep(20 * time.Millisecond) + sendMsg(t, true, i) + } + + // check if corresponding protocol-level messages were correctly decoded + checkPowExchangeForNodeZero(t) + checkBloomFilterExchange(t) + stopServers() } +func resetParams(t *testing.T) { + // change pow only for node zero + masterPow = 7777777.0 + nodes[0].shh.SetMinimumPoW(masterPow) + + // change bloom for all nodes + masterBloomFilter = TopicToBloom(sharedTopic) + for i := 0; i < NumNodes; i++ { + nodes[i].shh.SetBloomFilter(masterBloomFilter) + } +} + +func initBloom(t *testing.T) { + masterBloomFilter = make([]byte, bloomFilterSize) + _, err := mrand.Read(masterBloomFilter) + if err != nil { + t.Fatalf("rand failed: %s.", err) + } + + msgBloom := TopicToBloom(sharedTopic) + masterBloomFilter = addBloom(masterBloomFilter, msgBloom) + for i := 0; i < 32; i++ { + masterBloomFilter[i] = 0xFF + } + + if !bloomFilterMatch(masterBloomFilter, msgBloom) { + t.Fatalf("bloom mismatch on initBloom.") + } +} + func initialize(t *testing.T) { + initBloom(t) + var err error ip := net.IPv4(127, 0, 0, 1) port0 := 30303 for i := 0; i < NumNodes; i++ { var node TestNode + b := make([]byte, bloomFilterSize) + copy(b, masterBloomFilter) node.shh = New(&DefaultConfig) - node.shh.SetMinimumPowTest(0.00000001) + node.shh.SetMinimumPoW(masterPow) + node.shh.SetBloomFilter(b) + if !bytes.Equal(node.shh.BloomFilter(), masterBloomFilter) { + t.Fatalf("bloom mismatch on init.") + } node.shh.Start(nil) topics := make([]TopicType, 0) topics = append(topics, sharedTopic) @@ -206,7 +262,7 @@ func checkPropagation(t *testing.T, includingNodeZero bool) { for i := first; i < NumNodes; i++ { f := nodes[i].shh.GetFilter(nodes[i].filerId) if f == nil { - t.Fatalf("failed to get filterId %s from node %d.", nodes[i].filerId, i) + t.Fatalf("failed to get filterId %s from node %d, round %d.", nodes[i].filerId, i, round) } mail := f.Retrieve() @@ -332,34 +388,43 @@ func TestPeerBasic(t *testing.T) { } } -func powReqExchange(t *testing.T) { +func checkPowExchangeForNodeZero(t *testing.T) { + cnt := 0 for i, node := range nodes { for peer := range node.shh.peers { - if peer.powRequirement > 1000.0 { - t.Fatalf("node %d: one of the peers' pow requirement is too big (%f).", i, peer.powRequirement) + if peer.peer.ID() == discover.PubkeyID(&nodes[0].id.PublicKey) { + cnt++ + if peer.powRequirement != masterPow { + t.Fatalf("node %d: failed to set the new pow requirement.", i) + } } } } + if cnt == 0 { + t.Fatalf("no matching peers found.") + } +} - const pow float64 = 7777777.0 - nodes[0].shh.SetMinimumPoW(pow) - - // wait until all the messages are delivered - time.Sleep(64 * time.Millisecond) - - cnt := 0 +func checkPowExchange(t *testing.T) { for i, node := range nodes { for peer := range node.shh.peers { - if peer.peer.ID() == discover.PubkeyID(&nodes[0].id.PublicKey) { - cnt++ - if peer.powRequirement != pow { - t.Fatalf("node %d: failed to set the new pow requirement.", i) + if peer.peer.ID() != discover.PubkeyID(&nodes[0].id.PublicKey) { + if peer.powRequirement != masterPow { + t.Fatalf("node %d: failed to exchange pow requirement in round %d; expected %f, got %f", + i, round, masterPow, peer.powRequirement) } } } } +} - if cnt == 0 { - t.Fatalf("no matching peers found.") +func checkBloomFilterExchange(t *testing.T) { + for i, node := range nodes { + for peer := range node.shh.peers { + if !bytes.Equal(peer.bloomFilter, masterBloomFilter) { + t.Fatalf("node %d: failed to exchange bloom filter requirement in round %d. \n%x expected \n%x got", + i, round, masterBloomFilter, peer.bloomFilter) + } + } } } diff --git a/whisper/whisperv6/whisper.go b/whisper/whisperv6/whisper.go index 492591486b94..bc89aadccd9f 100644 --- a/whisper/whisperv6/whisper.go +++ b/whisper/whisperv6/whisper.go @@ -48,9 +48,12 @@ type Statistics struct { } const ( - minPowIdx = iota // Minimal PoW required by the whisper node - maxMsgSizeIdx = iota // Maximal message length allowed by the whisper node - overflowIdx = iota // Indicator of message queue overflow + maxMsgSizeIdx = iota // Maximal message length allowed by the whisper node + overflowIdx // Indicator of message queue overflow + minPowIdx // Minimal PoW required by the whisper node + minPowToleranceIdx // Minimal PoW tolerated by the whisper node for a limited time + bloomFilterIdx // Bloom filter for topics of interest for this node + bloomFilterToleranceIdx // Bloom filter tolerated by the whisper node for a limited time ) // Whisper represents a dark communication interface through the Ethereum @@ -76,7 +79,7 @@ type Whisper struct { settings syncmap.Map // holds configuration settings that can be dynamically changed - reactionAllowance int // maximum time in seconds allowed to process the whisper-related messages + syncAllowance int // maximum time in seconds allowed to process the whisper-related messages statsMu sync.Mutex // guard stats stats Statistics // Statistics of whisper node @@ -91,15 +94,15 @@ func New(cfg *Config) *Whisper { } whisper := &Whisper{ - privateKeys: make(map[string]*ecdsa.PrivateKey), - symKeys: make(map[string][]byte), - envelopes: make(map[common.Hash]*Envelope), - expirations: make(map[uint32]*set.SetNonTS), - peers: make(map[*Peer]struct{}), - messageQueue: make(chan *Envelope, messageQueueLimit), - p2pMsgQueue: make(chan *Envelope, messageQueueLimit), - quit: make(chan struct{}), - reactionAllowance: SynchAllowance, + privateKeys: make(map[string]*ecdsa.PrivateKey), + symKeys: make(map[string][]byte), + envelopes: make(map[common.Hash]*Envelope), + expirations: make(map[uint32]*set.SetNonTS), + peers: make(map[*Peer]struct{}), + messageQueue: make(chan *Envelope, messageQueueLimit), + p2pMsgQueue: make(chan *Envelope, messageQueueLimit), + quit: make(chan struct{}), + syncAllowance: DefaultSyncAllowance, } whisper.filters = NewFilters(whisper) @@ -126,11 +129,55 @@ func New(cfg *Config) *Whisper { return whisper } +// MinPow returns the PoW value required by this node. func (w *Whisper) MinPow() float64 { - val, _ := w.settings.Load(minPowIdx) + val, exist := w.settings.Load(minPowIdx) + if !exist || val == nil { + return DefaultMinimumPoW + } + v, ok := val.(float64) + if !ok { + log.Error("Error loading minPowIdx, using default") + return DefaultMinimumPoW + } + return v +} + +// MinPowTolerance returns the value of minimum PoW which is tolerated for a limited +// time after PoW was changed. If sufficient time have elapsed or no change of PoW +// have ever occurred, the return value will be the same as return value of MinPow(). +func (w *Whisper) MinPowTolerance() float64 { + val, exist := w.settings.Load(minPowToleranceIdx) + if !exist || val == nil { + return DefaultMinimumPoW + } return val.(float64) } +// BloomFilter returns the aggregated bloom filter for all the topics of interest. +// The nodes are required to send only messages that match the advertised bloom filter. +// If a message does not match the bloom, it will tantamount to spam, and the peer will +// be disconnected. +func (w *Whisper) BloomFilter() []byte { + val, exist := w.settings.Load(bloomFilterIdx) + if !exist || val == nil { + return nil + } + return val.([]byte) +} + +// BloomFilterTolerance returns the bloom filter which is tolerated for a limited +// time after new bloom was advertised to the peers. If sufficient time have elapsed +// or no change of bloom filter have ever occurred, the return value will be the same +// as return value of BloomFilter(). +func (w *Whisper) BloomFilterTolerance() []byte { + val, exist := w.settings.Load(bloomFilterToleranceIdx) + if !exist || val == nil { + return nil + } + return val.([]byte) +} + // MaxMessageSize returns the maximum accepted message size. func (w *Whisper) MaxMessageSize() uint32 { val, _ := w.settings.Load(maxMsgSizeIdx) @@ -180,18 +227,40 @@ func (w *Whisper) SetMaxMessageSize(size uint32) error { return nil } +// SetBloomFilter sets the new bloom filter +func (w *Whisper) SetBloomFilter(bloom []byte) error { + if len(bloom) != bloomFilterSize { + return fmt.Errorf("invalid bloom filter size: %d", len(bloom)) + } + + b := make([]byte, bloomFilterSize) + copy(b, bloom) + + w.settings.Store(bloomFilterIdx, b) + w.notifyPeersAboutBloomFilterChange(b) + + go func() { + // allow some time before all the peers have processed the notification + time.Sleep(time.Duration(w.syncAllowance) * time.Second) + w.settings.Store(bloomFilterToleranceIdx, b) + }() + + return nil +} + // SetMinimumPoW sets the minimal PoW required by this node func (w *Whisper) SetMinimumPoW(val float64) error { if val < 0.0 { return fmt.Errorf("invalid PoW: %f", val) } + w.settings.Store(minPowIdx, val) w.notifyPeersAboutPowRequirementChange(val) go func() { // allow some time before all the peers have processed the notification - time.Sleep(time.Duration(w.reactionAllowance) * time.Second) - w.settings.Store(minPowIdx, val) + time.Sleep(time.Duration(w.syncAllowance) * time.Second) + w.settings.Store(minPowToleranceIdx, val) }() return nil @@ -199,21 +268,13 @@ func (w *Whisper) SetMinimumPoW(val float64) error { // SetMinimumPoW sets the minimal PoW in test environment func (w *Whisper) SetMinimumPowTest(val float64) { - w.notifyPeersAboutPowRequirementChange(val) w.settings.Store(minPowIdx, val) + w.notifyPeersAboutPowRequirementChange(val) + w.settings.Store(minPowToleranceIdx, val) } func (w *Whisper) notifyPeersAboutPowRequirementChange(pow float64) { - arr := make([]*Peer, len(w.peers)) - i := 0 - - w.peerMu.Lock() - for p := range w.peers { - arr[i] = p - i++ - } - w.peerMu.Unlock() - + arr := w.getPeers() for _, p := range arr { err := p.notifyAboutPowRequirementChange(pow) if err != nil { @@ -221,11 +282,37 @@ func (w *Whisper) notifyPeersAboutPowRequirementChange(pow float64) { err = p.notifyAboutPowRequirementChange(pow) } if err != nil { - log.Warn("oversized message received", "peer", p.ID(), "error", err) + log.Warn("failed to notify peer about new pow requirement", "peer", p.ID(), "error", err) + } + } +} + +func (w *Whisper) notifyPeersAboutBloomFilterChange(bloom []byte) { + arr := w.getPeers() + for _, p := range arr { + err := p.notifyAboutBloomFilterChange(bloom) + if err != nil { + // allow one retry + err = p.notifyAboutBloomFilterChange(bloom) + } + if err != nil { + log.Warn("failed to notify peer about new bloom filter", "peer", p.ID(), "error", err) } } } +func (w *Whisper) getPeers() []*Peer { + arr := make([]*Peer, len(w.peers)) + i := 0 + w.peerMu.Lock() + for p := range w.peers { + arr[i] = p + i++ + } + w.peerMu.Unlock() + return arr +} + // getPeer retrieves peer by ID func (w *Whisper) getPeer(peerID []byte) (*Peer, error) { w.peerMu.Lock() @@ -459,7 +546,28 @@ func (w *Whisper) GetSymKey(id string) ([]byte, error) { // Subscribe installs a new message handler used for filtering, decrypting // and subsequent storing of incoming messages. func (w *Whisper) Subscribe(f *Filter) (string, error) { - return w.filters.Install(f) + s, err := w.filters.Install(f) + if err == nil { + w.updateBloomFilter(f) + } + return s, err +} + +// updateBloomFilter recalculates the new value of bloom filter, +// and informs the peers if necessary. +func (w *Whisper) updateBloomFilter(f *Filter) { + aggregate := make([]byte, bloomFilterSize) + for _, t := range f.Topics { + top := BytesToTopic(t) + b := TopicToBloom(top) + aggregate = addBloom(aggregate, b) + } + + if !bloomFilterMatch(w.BloomFilter(), aggregate) { + // existing bloom filter must be updated + aggregate = addBloom(w.BloomFilter(), aggregate) + w.SetBloomFilter(aggregate) + } } // GetFilter returns the filter by id. @@ -592,7 +700,21 @@ func (wh *Whisper) runMessageLoop(p *Peer, rw p2p.MsgReadWriter) error { } p.powRequirement = f case bloomFilterExCode: - // to be implemented + var bloom []byte + err := packet.Decode(&bloom) + if err == nil && len(bloom) != bloomFilterSize { + err = fmt.Errorf("wrong bloom filter size %d", len(bloom)) + } + + if err != nil { + log.Warn("failed to decode bloom filter exchange message, peer will be disconnected", "peer", p.peer.ID(), "err", err) + return errors.New("invalid bloom filter exchange message") + } + if isFullNode(bloom) { + p.bloomFilter = nil + } else { + p.bloomFilter = bloom + } case p2pMessageCode: // peer-to-peer message, sent directly to peer bypassing PoW checks, etc. // this message is not supposed to be forwarded to other peers, and @@ -633,7 +755,7 @@ func (wh *Whisper) add(envelope *Envelope) (bool, error) { sent := envelope.Expiry - envelope.TTL if sent > now { - if sent-SynchAllowance > now { + if sent-DefaultSyncAllowance > now { return false, fmt.Errorf("envelope created in the future [%x]", envelope.Hash()) } else { // recalculate PoW, adjusted for the time difference, plus one second for latency @@ -642,7 +764,7 @@ func (wh *Whisper) add(envelope *Envelope) (bool, error) { } if envelope.Expiry < now { - if envelope.Expiry+SynchAllowance*2 < now { + if envelope.Expiry+DefaultSyncAllowance*2 < now { return false, fmt.Errorf("very old message") } else { log.Debug("expired envelope dropped", "hash", envelope.Hash().Hex()) @@ -655,11 +777,22 @@ func (wh *Whisper) add(envelope *Envelope) (bool, error) { } if envelope.PoW() < wh.MinPow() { - log.Debug("envelope with low PoW dropped", "PoW", envelope.PoW(), "hash", envelope.Hash().Hex()) - return false, nil // drop envelope without error for now + // maybe the value was recently changed, and the peers did not adjust yet. + // in this case the previous value is retrieved by MinPowTolerance() + // for a short period of peer synchronization. + if envelope.PoW() < wh.MinPowTolerance() { + return false, fmt.Errorf("envelope with low PoW received: PoW=%f, hash=[%v]", envelope.PoW(), envelope.Hash().Hex()) + } + } - // once the status message includes the PoW requirement, an error should be returned here: - //return false, fmt.Errorf("envelope with low PoW dropped: PoW=%f, hash=[%v]", envelope.PoW(), envelope.Hash().Hex()) + if !bloomFilterMatch(wh.BloomFilter(), envelope.Bloom()) { + // maybe the value was recently changed, and the peers did not adjust yet. + // in this case the previous value is retrieved by BloomFilterTolerance() + // for a short period of peer synchronization. + if !bloomFilterMatch(wh.BloomFilterTolerance(), envelope.Bloom()) { + return false, fmt.Errorf("envelope does not match bloom filter, hash=[%v], bloom: \n%x \n%x \n%x", + envelope.Hash().Hex(), wh.BloomFilter(), envelope.Bloom(), envelope.Topic) + } } hash := envelope.Hash() @@ -897,3 +1030,40 @@ func GenerateRandomID() (id string, err error) { id = common.Bytes2Hex(buf) return id, err } + +func isFullNode(bloom []byte) bool { + if bloom == nil { + return true + } + for _, b := range bloom { + if b != 255 { + return false + } + } + return true +} + +func bloomFilterMatch(filter, sample []byte) bool { + if filter == nil { + // full node, accepts all messages + return true + } + + for i := 0; i < bloomFilterSize; i++ { + f := filter[i] + s := sample[i] + if (f | s) != f { + return false + } + } + + return true +} + +func addBloom(a, b []byte) []byte { + c := make([]byte, bloomFilterSize) + for i := 0; i < bloomFilterSize; i++ { + c[i] = a[i] | b[i] + } + return c +} diff --git a/whisper/whisperv6/whisper_test.go b/whisper/whisperv6/whisper_test.go index b391a1161b45..fa14acb1b1b4 100644 --- a/whisper/whisperv6/whisper_test.go +++ b/whisper/whisperv6/whisper_test.go @@ -843,3 +843,64 @@ func TestSymmetricSendKeyMismatch(t *testing.T) { t.Fatalf("received a message when keys weren't matching") } } + +func TestBloom(t *testing.T) { + topic := TopicType{0, 0, 255, 6} + b := TopicToBloom(topic) + x := make([]byte, bloomFilterSize) + x[0] = byte(1) + x[32] = byte(1) + x[bloomFilterSize-1] = byte(128) + if !bloomFilterMatch(x, b) || !bloomFilterMatch(b, x) { + t.Fatalf("bloom filter does not match the mask") + } + + _, err := mrand.Read(b) + if err != nil { + t.Fatalf("math rand error") + } + _, err = mrand.Read(x) + if err != nil { + t.Fatalf("math rand error") + } + if !bloomFilterMatch(b, b) { + t.Fatalf("bloom filter does not match self") + } + x = addBloom(x, b) + if !bloomFilterMatch(x, b) { + t.Fatalf("bloom filter does not match combined bloom") + } + if !isFullNode(nil) { + t.Fatalf("isFullNode did not recognize nil as full node") + } + x[17] = 254 + if isFullNode(x) { + t.Fatalf("isFullNode false positive") + } + for i := 0; i < bloomFilterSize; i++ { + b[i] = byte(255) + } + if !isFullNode(b) { + t.Fatalf("isFullNode false negative") + } + if bloomFilterMatch(x, b) { + t.Fatalf("bloomFilterMatch false positive") + } + if !bloomFilterMatch(b, x) { + t.Fatalf("bloomFilterMatch false negative") + } + + w := New(&DefaultConfig) + f := w.BloomFilter() + if f != nil { + t.Fatalf("wrong bloom on creation") + } + err = w.SetBloomFilter(x) + if err != nil { + t.Fatalf("failed to set bloom filter: %s", err) + } + f = w.BloomFilter() + if !bloomFilterMatch(f, x) || !bloomFilterMatch(x, f) { + t.Fatalf("retireved wrong bloom filter") + } +} From 90e5744d6f54a11b0727ab7583158ab7d72302fd Mon Sep 17 00:00:00 2001 From: Magicking Date: Fri, 12 Jan 2018 17:01:41 +0100 Subject: [PATCH 08/13] ethstats: Fix ethstats reporting while syncing --- ethstats/ethstats.go | 1 + 1 file changed, 1 insertion(+) diff --git a/ethstats/ethstats.go b/ethstats/ethstats.go index 7065d71629e1..3d370bfdc613 100644 --- a/ethstats/ethstats.go +++ b/ethstats/ethstats.go @@ -613,6 +613,7 @@ func (s *Service) reportHistory(conn *websocket.Conn, list []uint64) error { } // Ran out of blocks, cut the report short and send history = history[len(history)-i:] + break } // Assemble the history report and send it to the server if len(history) > 0 { From 938cf4528ab5acbb6013be79a0548956713807a8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Kurk=C3=B3=20Mih=C3=A1ly?= Date: Mon, 15 Jan 2018 11:20:00 +0200 Subject: [PATCH 09/13] dashboard: deep state update, version in footer (#15837) * dashboard: footer, deep state update * dashboard: resolve asset path * dashboard: remove bundle.js * dashboard: prevent state update on every reconnection * dashboard: fix linter issue * dashboard, cmd: minor UI fix, include commit hash * remove geth binary * dashboard: gitCommit renamed to commit * dashboard: move the geth version to the right, make commit optional * dashboard: commit limited to 7 characters * dashboard: limit commit length on client side * dashboard: run go generate --- .gitignore | 2 +- cmd/geth/config.go | 2 +- cmd/utils/flags.go | 4 +- dashboard/README.md | 2 +- dashboard/assets.go | 6352 ++++-------------- dashboard/assets/components/Common.jsx | 28 - dashboard/assets/components/Dashboard.jsx | 193 +- dashboard/assets/components/Footer.jsx | 80 + dashboard/assets/components/Home.jsx | 13 +- dashboard/assets/{public => }/dashboard.html | 0 dashboard/assets/package.json | 14 +- dashboard/assets/types/content.jsx | 41 +- dashboard/assets/types/message.jsx | 61 - dashboard/assets/webpack.config.js | 2 +- dashboard/dashboard.go | 53 +- dashboard/message.go | 17 +- 16 files changed, 1486 insertions(+), 5378 deletions(-) create mode 100644 dashboard/assets/components/Footer.jsx rename dashboard/assets/{public => }/dashboard.html (100%) delete mode 100644 dashboard/assets/types/message.jsx diff --git a/.gitignore b/.gitignore index 9e054bad1b02..0763d8492ccb 100644 --- a/.gitignore +++ b/.gitignore @@ -38,4 +38,4 @@ profile.cov /dashboard/assets/flow-typed /dashboard/assets/node_modules /dashboard/assets/stats.json -/dashboard/assets/public/bundle.js +/dashboard/assets/bundle.js diff --git a/cmd/geth/config.go b/cmd/geth/config.go index 27490c40486f..9c703758e044 100644 --- a/cmd/geth/config.go +++ b/cmd/geth/config.go @@ -158,7 +158,7 @@ func makeFullNode(ctx *cli.Context) *node.Node { utils.RegisterEthService(stack, &cfg.Eth) if ctx.GlobalBool(utils.DashboardEnabledFlag.Name) { - utils.RegisterDashboardService(stack, &cfg.Dashboard) + utils.RegisterDashboardService(stack, &cfg.Dashboard, gitCommit) } // Whisper must be explicitly enabled by specifying at least 1 whisper flag or in dev mode shhEnabled := enableWhisper(ctx) diff --git a/cmd/utils/flags.go b/cmd/utils/flags.go index 94ab64c2e069..3766ea4a60ce 100644 --- a/cmd/utils/flags.go +++ b/cmd/utils/flags.go @@ -1104,9 +1104,9 @@ func RegisterEthService(stack *node.Node, cfg *eth.Config) { } // RegisterDashboardService adds a dashboard to the stack. -func RegisterDashboardService(stack *node.Node, cfg *dashboard.Config) { +func RegisterDashboardService(stack *node.Node, cfg *dashboard.Config, commit string) { stack.Register(func(ctx *node.ServiceContext) (node.Service, error) { - return dashboard.New(cfg) + return dashboard.New(cfg, commit) }) } diff --git a/dashboard/README.md b/dashboard/README.md index da28f5a19276..e010095ab2cb 100644 --- a/dashboard/README.md +++ b/dashboard/README.md @@ -20,7 +20,7 @@ Normally the dashboard assets are bundled into Geth via `go-bindata` to avoid ex ``` $ (cd dashboard/assets && ./node_modules/.bin/webpack --watch) -$ geth --dashboard --dashboard.assets=dashboard/assets/public --vmodule=dashboard=5 +$ geth --dashboard --dashboard.assets=dashboard/assets --vmodule=dashboard=5 ``` To bundle up the final UI into Geth, run `go generate`: diff --git a/dashboard/assets.go b/dashboard/assets.go index 043a5d72867d..b2c12032341a 100644 --- a/dashboard/assets.go +++ b/dashboard/assets.go @@ -1,7 +1,7 @@ // Code generated by go-bindata. DO NOT EDIT. // sources: -// assets/public/bundle.js -// assets/public/dashboard.html +// assets/dashboard.html +// assets/bundle.js package dashboard @@ -46,7 +46,48 @@ func (fi bindataFileInfo) Sys() interface{} { } //nolint:misspell -var _publicBundleJs = []byte((((((((((`!function(modules) { +var _dashboardHtml = []byte(` + + + + + + + Go Ethereum Dashboard + + + + +
+ + + +`) + +func dashboardHtmlBytes() ([]byte, error) { + return _dashboardHtml, nil +} + +func dashboardHtml() (*asset, error) { + bytes, err := dashboardHtmlBytes() + if err != nil { + return nil, err + } + + info := bindataFileInfo{name: "dashboard.html", size: 0, mode: os.FileMode(0), modTime: time.Unix(0, 0)} + a := &asset{bytes: bytes, info: info} + return a, nil +} + +//nolint:misspell +var _bundleJs = []byte((((((((((`!function(modules) { function __webpack_require__(moduleId) { if (installedModules[moduleId]) return installedModules[moduleId].exports; var module = installedModules[moduleId] = { @@ -73,45 +114,21 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { return __webpack_require__.d(getter, "a", getter), getter; }, __webpack_require__.o = function(object, property) { return Object.prototype.hasOwnProperty.call(object, property); - }, __webpack_require__.p = "", __webpack_require__(__webpack_require__.s = 453); -}([ function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - function _curry2(fn) { - return function f2(a, b) { - switch (arguments.length) { - case 0: - return f2; - - case 1: - return Object(__WEBPACK_IMPORTED_MODULE_1__isPlaceholder__.a)(a) ? f2 : Object(__WEBPACK_IMPORTED_MODULE_0__curry1__.a)(function(_b) { - return fn(a, _b); - }); - - default: - return Object(__WEBPACK_IMPORTED_MODULE_1__isPlaceholder__.a)(a) && Object(__WEBPACK_IMPORTED_MODULE_1__isPlaceholder__.a)(b) ? f2 : Object(__WEBPACK_IMPORTED_MODULE_1__isPlaceholder__.a)(a) ? Object(__WEBPACK_IMPORTED_MODULE_0__curry1__.a)(function(_a) { - return fn(_a, b); - }) : Object(__WEBPACK_IMPORTED_MODULE_1__isPlaceholder__.a)(b) ? Object(__WEBPACK_IMPORTED_MODULE_0__curry1__.a)(function(_b) { - return fn(a, _b); - }) : fn(a, b); - } - }; - } - __webpack_exports__.a = _curry2; - var __WEBPACK_IMPORTED_MODULE_0__curry1__ = __webpack_require__(4), __WEBPACK_IMPORTED_MODULE_1__isPlaceholder__ = __webpack_require__(133); -}, function(module, exports, __webpack_require__) { + }, __webpack_require__.p = "", __webpack_require__(__webpack_require__.s = 336); +}([ function(module, exports, __webpack_require__) { "use strict"; (function(process) { - "production" === process.env.NODE_ENV ? module.exports = __webpack_require__(454) : module.exports = __webpack_require__(455); - }).call(exports, __webpack_require__(3)); + "production" === process.env.NODE_ENV ? module.exports = __webpack_require__(337) : module.exports = __webpack_require__(338); + }).call(exports, __webpack_require__(2)); }, function(module, exports, __webpack_require__) { (function(process) { if ("production" !== process.env.NODE_ENV) { var REACT_ELEMENT_TYPE = "function" == typeof Symbol && Symbol.for && Symbol.for("react.element") || 60103, isValidElement = function(object) { return "object" == typeof object && null !== object && object.$$typeof === REACT_ELEMENT_TYPE; }; - module.exports = __webpack_require__(496)(isValidElement, !0); - } else module.exports = __webpack_require__(497)(); - }).call(exports, __webpack_require__(3)); + module.exports = __webpack_require__(379)(isValidElement, !0); + } else module.exports = __webpack_require__(380)(); + }).call(exports, __webpack_require__(2)); }, function(module, exports) { function defaultSetTimout() { throw new Error("setTimeout has not been defined"); @@ -201,56 +218,6 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }, process.umask = function() { return 0; }; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - function _curry1(fn) { - return function f1(a) { - return 0 === arguments.length || Object(__WEBPACK_IMPORTED_MODULE_0__isPlaceholder__.a)(a) ? f1 : fn.apply(this, arguments); - }; - } - __webpack_exports__.a = _curry1; - var __WEBPACK_IMPORTED_MODULE_0__isPlaceholder__ = __webpack_require__(133); -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - function _curry3(fn) { - return function f3(a, b, c) { - switch (arguments.length) { - case 0: - return f3; - - case 1: - return Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(a) ? f3 : Object(__WEBPACK_IMPORTED_MODULE_1__curry2__.a)(function(_b, _c) { - return fn(a, _b, _c); - }); - - case 2: - return Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(a) && Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(b) ? f3 : Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(a) ? Object(__WEBPACK_IMPORTED_MODULE_1__curry2__.a)(function(_a, _c) { - return fn(_a, b, _c); - }) : Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(b) ? Object(__WEBPACK_IMPORTED_MODULE_1__curry2__.a)(function(_b, _c) { - return fn(a, _b, _c); - }) : Object(__WEBPACK_IMPORTED_MODULE_0__curry1__.a)(function(_c) { - return fn(a, b, _c); - }); - - default: - return Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(a) && Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(b) && Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(c) ? f3 : Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(a) && Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(b) ? Object(__WEBPACK_IMPORTED_MODULE_1__curry2__.a)(function(_a, _b) { - return fn(_a, _b, c); - }) : Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(a) && Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(c) ? Object(__WEBPACK_IMPORTED_MODULE_1__curry2__.a)(function(_a, _c) { - return fn(_a, b, _c); - }) : Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(b) && Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(c) ? Object(__WEBPACK_IMPORTED_MODULE_1__curry2__.a)(function(_b, _c) { - return fn(a, _b, _c); - }) : Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(a) ? Object(__WEBPACK_IMPORTED_MODULE_0__curry1__.a)(function(_a) { - return fn(_a, b, c); - }) : Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(b) ? Object(__WEBPACK_IMPORTED_MODULE_0__curry1__.a)(function(_b) { - return fn(a, _b, c); - }) : Object(__WEBPACK_IMPORTED_MODULE_2__isPlaceholder__.a)(c) ? Object(__WEBPACK_IMPORTED_MODULE_0__curry1__.a)(function(_c) { - return fn(a, b, _c); - }) : fn(a, b, c); - } - }; - } - __webpack_exports__.a = _curry3; - var __WEBPACK_IMPORTED_MODULE_0__curry1__ = __webpack_require__(4), __WEBPACK_IMPORTED_MODULE_1__curry2__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_2__isPlaceholder__ = __webpack_require__(133); }, function(module, exports, __webpack_require__) { var __WEBPACK_AMD_DEFINE_ARRAY__, __WEBPACK_AMD_DEFINE_RESULT__; !function() { @@ -315,7 +282,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }), __webpack_require__.d(__webpack_exports__, "o", function() { return parseChildIndex; }); - var __WEBPACK_IMPORTED_MODULE_0_lodash_isNil__ = __webpack_require__(28), __WEBPACK_IMPORTED_MODULE_0_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_1_lodash_isString__ = __webpack_require__(227), __WEBPACK_IMPORTED_MODULE_1_lodash_isString___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_isString__), __WEBPACK_IMPORTED_MODULE_2_lodash_isObject__ = __webpack_require__(47), __WEBPACK_IMPORTED_MODULE_2_lodash_isObject___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_lodash_isObject__), __WEBPACK_IMPORTED_MODULE_3_lodash_isFunction__ = __webpack_require__(11), __WEBPACK_IMPORTED_MODULE_3_lodash_isFunction___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_lodash_isFunction__), __WEBPACK_IMPORTED_MODULE_4_lodash_isArray__ = __webpack_require__(16), __WEBPACK_IMPORTED_MODULE_4_lodash_isArray___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_lodash_isArray__), __WEBPACK_IMPORTED_MODULE_5_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_5_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_react__), __WEBPACK_IMPORTED_MODULE_6_prop_types__ = __webpack_require__(2), __WEBPACK_IMPORTED_MODULE_6_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_6_prop_types__), __WEBPACK_IMPORTED_MODULE_7__DataUtils__ = __webpack_require__(12), __WEBPACK_IMPORTED_MODULE_8__PureRender__ = __webpack_require__(8), PRESENTATION_ATTRIBUTES = { + var __WEBPACK_IMPORTED_MODULE_0_lodash_isNil__ = __webpack_require__(20), __WEBPACK_IMPORTED_MODULE_0_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_1_lodash_isString__ = __webpack_require__(165), __WEBPACK_IMPORTED_MODULE_1_lodash_isString___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_isString__), __WEBPACK_IMPORTED_MODULE_2_lodash_isObject__ = __webpack_require__(32), __WEBPACK_IMPORTED_MODULE_2_lodash_isObject___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_lodash_isObject__), __WEBPACK_IMPORTED_MODULE_3_lodash_isFunction__ = __webpack_require__(8), __WEBPACK_IMPORTED_MODULE_3_lodash_isFunction___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_lodash_isFunction__), __WEBPACK_IMPORTED_MODULE_4_lodash_isArray__ = __webpack_require__(12), __WEBPACK_IMPORTED_MODULE_4_lodash_isArray___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_lodash_isArray__), __WEBPACK_IMPORTED_MODULE_5_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_5_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_react__), __WEBPACK_IMPORTED_MODULE_6_prop_types__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_6_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_6_prop_types__), __WEBPACK_IMPORTED_MODULE_7__DataUtils__ = __webpack_require__(9), __WEBPACK_IMPORTED_MODULE_8__PureRender__ = __webpack_require__(5), PRESENTATION_ATTRIBUTES = { alignmentBaseline: __WEBPACK_IMPORTED_MODULE_6_prop_types___default.a.string, angle: __WEBPACK_IMPORTED_MODULE_6_prop_types___default.a.number, baselineShift: __WEBPACK_IMPORTED_MODULE_6_prop_types___default.a.string, @@ -530,7 +497,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }, function(module, exports, __webpack_require__) { "use strict"; exports.__esModule = !0; - var _assign = __webpack_require__(268), _assign2 = function(obj) { + var _assign = __webpack_require__(206), _assign2 = function(obj) { return obj && obj.__esModule ? obj : { default: obj }; @@ -548,7 +515,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { var tag = baseGetTag(value); return tag == funcTag || tag == genTag || tag == asyncTag || tag == proxyTag; } - var baseGetTag = __webpack_require__(59), isObject = __webpack_require__(47), asyncTag = "[object AsyncFunction]", funcTag = "[object Function]", genTag = "[object GeneratorFunction]", proxyTag = "[object Proxy]"; + var baseGetTag = __webpack_require__(42), isObject = __webpack_require__(32), asyncTag = "[object AsyncFunction]", funcTag = "[object Function]", genTag = "[object GeneratorFunction]", proxyTag = "[object Proxy]"; module.exports = isFunction; }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; @@ -573,7 +540,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }), __webpack_require__.d(__webpack_exports__, "a", function() { return findEntryInArray; }); - var __WEBPACK_IMPORTED_MODULE_0_lodash_get__ = __webpack_require__(152), __WEBPACK_IMPORTED_MODULE_0_lodash_get___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_get__), __WEBPACK_IMPORTED_MODULE_1_lodash_isArray__ = __webpack_require__(16), __WEBPACK_IMPORTED_MODULE_1_lodash_isArray___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_isArray__), __WEBPACK_IMPORTED_MODULE_2_lodash_isNaN__ = __webpack_require__(159), __WEBPACK_IMPORTED_MODULE_2_lodash_isNaN___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_lodash_isNaN__), __WEBPACK_IMPORTED_MODULE_3_lodash_isNumber__ = __webpack_require__(232), __WEBPACK_IMPORTED_MODULE_3_lodash_isNumber___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_lodash_isNumber__), __WEBPACK_IMPORTED_MODULE_4_lodash_isString__ = __webpack_require__(227), __WEBPACK_IMPORTED_MODULE_4_lodash_isString___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_lodash_isString__), mathSign = function(value) { + var __WEBPACK_IMPORTED_MODULE_0_lodash_get__ = __webpack_require__(109), __WEBPACK_IMPORTED_MODULE_0_lodash_get___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_get__), __WEBPACK_IMPORTED_MODULE_1_lodash_isArray__ = __webpack_require__(12), __WEBPACK_IMPORTED_MODULE_1_lodash_isArray___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_isArray__), __WEBPACK_IMPORTED_MODULE_2_lodash_isNaN__ = __webpack_require__(116), __WEBPACK_IMPORTED_MODULE_2_lodash_isNaN___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_lodash_isNaN__), __WEBPACK_IMPORTED_MODULE_3_lodash_isNumber__ = __webpack_require__(170), __WEBPACK_IMPORTED_MODULE_3_lodash_isNumber___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_lodash_isNumber__), __WEBPACK_IMPORTED_MODULE_4_lodash_isString__ = __webpack_require__(165), __WEBPACK_IMPORTED_MODULE_4_lodash_isString___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_lodash_isString__), mathSign = function(value) { return 0 === value ? 0 : value > 0 ? 1 : -1; }, isPercent = function(value) { return __WEBPACK_IMPORTED_MODULE_4_lodash_isString___default()(value) && value.indexOf("%") === value.length - 1; @@ -630,12 +597,12 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { Object.defineProperty(exports, "__esModule", { value: !0 }), exports.sheetsManager = exports.preset = void 0; - var _keys = __webpack_require__(51), _keys2 = _interopRequireDefault(_keys), _extends2 = __webpack_require__(10), _extends3 = _interopRequireDefault(_extends2), _getPrototypeOf = __webpack_require__(38), _getPrototypeOf2 = _interopRequireDefault(_getPrototypeOf), _classCallCheck2 = __webpack_require__(39), _classCallCheck3 = _interopRequireDefault(_classCallCheck2), _createClass2 = __webpack_require__(40), _createClass3 = _interopRequireDefault(_createClass2), _possibleConstructorReturn2 = __webpack_require__(41), _possibleConstructorReturn3 = _interopRequireDefault(_possibleConstructorReturn2), _inherits2 = __webpack_require__(42), _inherits3 = _interopRequireDefault(_inherits2), _objectWithoutProperties2 = __webpack_require__(9), _objectWithoutProperties3 = _interopRequireDefault(_objectWithoutProperties2), _map = __webpack_require__(519), _map2 = _interopRequireDefault(_map), _minSafeInteger = __webpack_require__(535), _minSafeInteger2 = _interopRequireDefault(_minSafeInteger), _react = __webpack_require__(1), _react2 = _interopRequireDefault(_react), _propTypes = __webpack_require__(2), _propTypes2 = _interopRequireDefault(_propTypes), _warning = __webpack_require__(14), _warning2 = _interopRequireDefault(_warning), _hoistNonReactStatics = __webpack_require__(194), _hoistNonReactStatics2 = _interopRequireDefault(_hoistNonReactStatics), _wrapDisplayName = __webpack_require__(95), _wrapDisplayName2 = _interopRequireDefault(_wrapDisplayName), _getDisplayName = __webpack_require__(289), _getDisplayName2 = _interopRequireDefault(_getDisplayName), _contextTypes = __webpack_require__(538), _contextTypes2 = _interopRequireDefault(_contextTypes), _jss = __webpack_require__(291), _jssGlobal = __webpack_require__(561), _jssGlobal2 = _interopRequireDefault(_jssGlobal), _jssNested = __webpack_require__(562), _jssNested2 = _interopRequireDefault(_jssNested), _jssCamelCase = __webpack_require__(563), _jssCamelCase2 = _interopRequireDefault(_jssCamelCase), _jssDefaultUnit = __webpack_require__(564), _jssDefaultUnit2 = _interopRequireDefault(_jssDefaultUnit), _jssVendorPrefixer = __webpack_require__(566), _jssVendorPrefixer2 = _interopRequireDefault(_jssVendorPrefixer), _jssPropsSort = __webpack_require__(571), _jssPropsSort2 = _interopRequireDefault(_jssPropsSort), _ns = __webpack_require__(290), ns = function(obj) { + var _keys = __webpack_require__(36), _keys2 = _interopRequireDefault(_keys), _extends2 = __webpack_require__(7), _extends3 = _interopRequireDefault(_extends2), _getPrototypeOf = __webpack_require__(26), _getPrototypeOf2 = _interopRequireDefault(_getPrototypeOf), _classCallCheck2 = __webpack_require__(27), _classCallCheck3 = _interopRequireDefault(_classCallCheck2), _createClass2 = __webpack_require__(28), _createClass3 = _interopRequireDefault(_createClass2), _possibleConstructorReturn2 = __webpack_require__(29), _possibleConstructorReturn3 = _interopRequireDefault(_possibleConstructorReturn2), _inherits2 = __webpack_require__(30), _inherits3 = _interopRequireDefault(_inherits2), _objectWithoutProperties2 = __webpack_require__(6), _objectWithoutProperties3 = _interopRequireDefault(_objectWithoutProperties2), _map = __webpack_require__(402), _map2 = _interopRequireDefault(_map), _minSafeInteger = __webpack_require__(418), _minSafeInteger2 = _interopRequireDefault(_minSafeInteger), _react = __webpack_require__(0), _react2 = _interopRequireDefault(_react), _propTypes = __webpack_require__(1), _propTypes2 = _interopRequireDefault(_propTypes), _warning = __webpack_require__(11), _warning2 = _interopRequireDefault(_warning), _hoistNonReactStatics = __webpack_require__(151), _hoistNonReactStatics2 = _interopRequireDefault(_hoistNonReactStatics), _wrapDisplayName = __webpack_require__(74), _wrapDisplayName2 = _interopRequireDefault(_wrapDisplayName), _getDisplayName = __webpack_require__(227), _getDisplayName2 = _interopRequireDefault(_getDisplayName), _contextTypes = __webpack_require__(421), _contextTypes2 = _interopRequireDefault(_contextTypes), _jss = __webpack_require__(229), _jssGlobal = __webpack_require__(444), _jssGlobal2 = _interopRequireDefault(_jssGlobal), _jssNested = __webpack_require__(445), _jssNested2 = _interopRequireDefault(_jssNested), _jssCamelCase = __webpack_require__(446), _jssCamelCase2 = _interopRequireDefault(_jssCamelCase), _jssDefaultUnit = __webpack_require__(447), _jssDefaultUnit2 = _interopRequireDefault(_jssDefaultUnit), _jssVendorPrefixer = __webpack_require__(449), _jssVendorPrefixer2 = _interopRequireDefault(_jssVendorPrefixer), _jssPropsSort = __webpack_require__(454), _jssPropsSort2 = _interopRequireDefault(_jssPropsSort), _ns = __webpack_require__(228), ns = function(obj) { if (obj && obj.__esModule) return obj; var newObj = {}; if (null != obj) for (var key in obj) Object.prototype.hasOwnProperty.call(obj, key) && (newObj[key] = obj[key]); return newObj.default = obj, newObj; - }(_ns), _createMuiTheme = __webpack_require__(193), _createMuiTheme2 = _interopRequireDefault(_createMuiTheme), _themeListener = __webpack_require__(192), _themeListener2 = _interopRequireDefault(_themeListener), _createGenerateClassName = __webpack_require__(572), _createGenerateClassName2 = _interopRequireDefault(_createGenerateClassName), _getStylesCreator = __webpack_require__(573), _getStylesCreator2 = _interopRequireDefault(_getStylesCreator), preset = exports.preset = function() { + }(_ns), _createMuiTheme = __webpack_require__(150), _createMuiTheme2 = _interopRequireDefault(_createMuiTheme), _themeListener = __webpack_require__(149), _themeListener2 = _interopRequireDefault(_themeListener), _createGenerateClassName = __webpack_require__(455), _createGenerateClassName2 = _interopRequireDefault(_createGenerateClassName), _getStylesCreator = __webpack_require__(456), _getStylesCreator2 = _interopRequireDefault(_getStylesCreator), preset = exports.preset = function() { return { plugins: [ (0, _jssGlobal2.default)(), (0, _jssNested2.default)(), (0, _jssCamelCase2.default)(), (0, _jssDefaultUnit2.default)(), (0, _jssVendorPrefixer2.default)(), (0, _jssPropsSort2.default)() ] @@ -770,7 +737,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }; }; exports.default = withStyles; - }).call(exports, __webpack_require__(3)); + }).call(exports, __webpack_require__(2)); }, function(module, exports, __webpack_require__) { "use strict"; (function(process) { @@ -791,34 +758,14 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } catch (x) {} } }), module.exports = warning; - }).call(exports, __webpack_require__(3)); -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - function _dispatchable(methodNames, xf, fn) { - return function() { - if (0 === arguments.length) return fn(); - var args = Array.prototype.slice.call(arguments, 0), obj = args.pop(); - if (!Object(__WEBPACK_IMPORTED_MODULE_0__isArray__.a)(obj)) { - for (var idx = 0; idx < methodNames.length; ) { - if ("function" == typeof obj[methodNames[idx]]) return obj[methodNames[idx]].apply(obj, args); - idx += 1; - } - if (Object(__WEBPACK_IMPORTED_MODULE_1__isTransformer__.a)(obj)) { - return xf.apply(null, args)(obj); - } - } - return fn.apply(this, arguments); - }; - } - __webpack_exports__.a = _dispatchable; - var __WEBPACK_IMPORTED_MODULE_0__isArray__ = __webpack_require__(57), __WEBPACK_IMPORTED_MODULE_1__isTransformer__ = __webpack_require__(200); + }).call(exports, __webpack_require__(2)); }, function(module, exports) { var isArray = Array.isArray; module.exports = isArray; }, function(module, exports, __webpack_require__) { "use strict"; exports.__esModule = !0; - var _defineProperty = __webpack_require__(185), _defineProperty2 = function(obj) { + var _defineProperty = __webpack_require__(142), _defineProperty2 = function(obj) { return obj && obj.__esModule ? obj : { default: obj }; @@ -844,7 +791,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { className: layerClass }, others), children); } - var __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_0_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = __webpack_require__(2), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2_classnames__ = __webpack_require__(6), __WEBPACK_IMPORTED_MODULE_2_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_classnames__), _extends = Object.assign || function(target) { + var __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_0_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2_classnames__ = __webpack_require__(3), __WEBPACK_IMPORTED_MODULE_2_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_classnames__), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -855,18 +802,8 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { children: __WEBPACK_IMPORTED_MODULE_1_prop_types___default.a.oneOfType([ __WEBPACK_IMPORTED_MODULE_1_prop_types___default.a.arrayOf(__WEBPACK_IMPORTED_MODULE_1_prop_types___default.a.node), __WEBPACK_IMPORTED_MODULE_1_prop_types___default.a.node ]) }; Layer.propTypes = propTypes, __webpack_exports__.a = Layer; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - __webpack_exports__.a = { - init: function() { - return this.xf["@@transducer/init"](); - }, - result: function(result) { - return this.xf["@@transducer/result"](result); - } - }; }, function(module, exports, __webpack_require__) { - var global = __webpack_require__(221), core = __webpack_require__(222), hide = __webpack_require__(363), redefine = __webpack_require__(839), ctx = __webpack_require__(842), $export = function(type, name, source) { + var global = __webpack_require__(159), core = __webpack_require__(160), hide = __webpack_require__(246), redefine = __webpack_require__(521), ctx = __webpack_require__(524), $export = function(type, name, source) { var key, own, out, exp, IS_FORCED = type & $export.F, IS_GLOBAL = type & $export.G, IS_STATIC = type & $export.S, IS_PROTO = type & $export.P, IS_BIND = type & $export.B, target = IS_GLOBAL ? global : IS_STATIC ? global[name] || (global[name] = {}) : (global[name] || {}).prototype, exports = IS_GLOBAL ? core : core[name] || (core[name] = {}), expProto = exports.prototype || (exports.prototype = {}); IS_GLOBAL && (source = name); for (key in source) own = !IS_FORCED && target && void 0 !== target[key], out = (own ? target : source)[key], @@ -954,8 +891,8 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }), __webpack_require__.d(__webpack_exports__, "y", function() { return parseDomainOfCategoryAxis; }); - var __WEBPACK_IMPORTED_MODULE_0_lodash_isEqual__ = __webpack_require__(49), __WEBPACK_IMPORTED_MODULE_0_lodash_isEqual___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isEqual__), __WEBPACK_IMPORTED_MODULE_1_lodash_sortBy__ = __webpack_require__(402), __WEBPACK_IMPORTED_MODULE_1_lodash_sortBy___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_sortBy__), __WEBPACK_IMPORTED_MODULE_2_lodash_isNaN__ = __webpack_require__(159), __WEBPACK_IMPORTED_MODULE_2_lodash_isNaN___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_lodash_isNaN__), __WEBPACK_IMPORTED_MODULE_3_lodash_isString__ = __webpack_require__(227), __WEBPACK_IMPORTED_MODULE_3_lodash_isString___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_lodash_isString__), __WEBPACK_IMPORTED_MODULE_4_lodash_max__ = __webpack_require__(1010), __WEBPACK_IMPORTED_MODULE_4_lodash_max___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_lodash_max__), __WEBPACK_IMPORTED_MODULE_5_lodash_min__ = __webpack_require__(405), __WEBPACK_IMPORTED_MODULE_5_lodash_min___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_lodash_min__), __WEBPACK_IMPORTED_MODULE_6_lodash_isArray__ = __webpack_require__(16), __WEBPACK_IMPORTED_MODULE_6_lodash_isArray___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_6_lodash_isArray__), __WEBPACK_IMPORTED_MODULE_7_lodash_isFunction__ = __webpack_require__(11), __WEBPACK_IMPORTED_MODULE_7_lodash_isFunction___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_7_lodash_isFunction__), __WEBPACK_IMPORTED_MODULE_8_lodash_get__ = __webpack_require__(152), __WEBPACK_IMPORTED_MODULE_8_lodash_get___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_8_lodash_get__), __WEBPACK_IMPORTED_MODULE_9_lodash_isNil__ = __webpack_require__(28), __WEBPACK_IMPORTED_MODULE_9_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_9_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_10_recharts_scale__ = __webpack_require__(1011), __WEBPACK_IMPORTED_MODULE_11_d3_scale__ = (__webpack_require__.n(__WEBPACK_IMPORTED_MODULE_10_recharts_scale__), - __webpack_require__(408)), __WEBPACK_IMPORTED_MODULE_12_d3_shape__ = __webpack_require__(235), __WEBPACK_IMPORTED_MODULE_13__DataUtils__ = __webpack_require__(12), __WEBPACK_IMPORTED_MODULE_14__cartesian_ReferenceDot__ = __webpack_require__(441), __WEBPACK_IMPORTED_MODULE_15__cartesian_ReferenceLine__ = __webpack_require__(442), __WEBPACK_IMPORTED_MODULE_16__cartesian_ReferenceArea__ = __webpack_require__(443), __WEBPACK_IMPORTED_MODULE_17__cartesian_ErrorBar__ = __webpack_require__(117), __WEBPACK_IMPORTED_MODULE_18__component_Legend__ = __webpack_require__(233), __WEBPACK_IMPORTED_MODULE_19__ReactUtils__ = __webpack_require__(7), _extends = Object.assign || function(target) { + var __WEBPACK_IMPORTED_MODULE_0_lodash_isEqual__ = __webpack_require__(34), __WEBPACK_IMPORTED_MODULE_0_lodash_isEqual___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isEqual__), __WEBPACK_IMPORTED_MODULE_1_lodash_sortBy__ = __webpack_require__(285), __WEBPACK_IMPORTED_MODULE_1_lodash_sortBy___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_sortBy__), __WEBPACK_IMPORTED_MODULE_2_lodash_isNaN__ = __webpack_require__(116), __WEBPACK_IMPORTED_MODULE_2_lodash_isNaN___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_lodash_isNaN__), __WEBPACK_IMPORTED_MODULE_3_lodash_isString__ = __webpack_require__(165), __WEBPACK_IMPORTED_MODULE_3_lodash_isString___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_lodash_isString__), __WEBPACK_IMPORTED_MODULE_4_lodash_max__ = __webpack_require__(692), __WEBPACK_IMPORTED_MODULE_4_lodash_max___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_lodash_max__), __WEBPACK_IMPORTED_MODULE_5_lodash_min__ = __webpack_require__(288), __WEBPACK_IMPORTED_MODULE_5_lodash_min___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_lodash_min__), __WEBPACK_IMPORTED_MODULE_6_lodash_isArray__ = __webpack_require__(12), __WEBPACK_IMPORTED_MODULE_6_lodash_isArray___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_6_lodash_isArray__), __WEBPACK_IMPORTED_MODULE_7_lodash_isFunction__ = __webpack_require__(8), __WEBPACK_IMPORTED_MODULE_7_lodash_isFunction___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_7_lodash_isFunction__), __WEBPACK_IMPORTED_MODULE_8_lodash_get__ = __webpack_require__(109), __WEBPACK_IMPORTED_MODULE_8_lodash_get___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_8_lodash_get__), __WEBPACK_IMPORTED_MODULE_9_lodash_isNil__ = __webpack_require__(20), __WEBPACK_IMPORTED_MODULE_9_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_9_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_10_recharts_scale__ = __webpack_require__(693), __WEBPACK_IMPORTED_MODULE_11_d3_scale__ = (__webpack_require__.n(__WEBPACK_IMPORTED_MODULE_10_recharts_scale__), + __webpack_require__(291)), __WEBPACK_IMPORTED_MODULE_12_d3_shape__ = __webpack_require__(173), __WEBPACK_IMPORTED_MODULE_13__DataUtils__ = __webpack_require__(9), __WEBPACK_IMPORTED_MODULE_14__cartesian_ReferenceDot__ = __webpack_require__(324), __WEBPACK_IMPORTED_MODULE_15__cartesian_ReferenceLine__ = __webpack_require__(325), __WEBPACK_IMPORTED_MODULE_16__cartesian_ReferenceArea__ = __webpack_require__(326), __WEBPACK_IMPORTED_MODULE_17__cartesian_ErrorBar__ = __webpack_require__(90), __WEBPACK_IMPORTED_MODULE_18__component_Legend__ = __webpack_require__(171), __WEBPACK_IMPORTED_MODULE_19__ReactUtils__ = __webpack_require__(4), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -1450,12 +1387,6 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { version: "2.5.3" }; "number" == typeof __e && (__e = core); -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_arity__ = __webpack_require__(43), __WEBPACK_IMPORTED_MODULE_1__internal_curry1__ = __webpack_require__(4), __WEBPACK_IMPORTED_MODULE_2__internal_curry2__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_3__internal_curryN__ = __webpack_require__(135), curryN = Object(__WEBPACK_IMPORTED_MODULE_2__internal_curry2__.a)(function(length, fn) { - return 1 === length ? Object(__WEBPACK_IMPORTED_MODULE_1__internal_curry1__.a)(fn) : Object(__WEBPACK_IMPORTED_MODULE_0__internal_arity__.a)(length, Object(__WEBPACK_IMPORTED_MODULE_3__internal_curryN__.a)(length, [], fn)); - }); - __webpack_exports__.a = curryN; }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; function newInterval(floori, offseti, count, field) { @@ -1496,7 +1427,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { __webpack_exports__.a = newInterval; var t0 = new Date(), t1 = new Date(); }, function(module, exports, __webpack_require__) { - var global = __webpack_require__(36), core = __webpack_require__(22), ctx = __webpack_require__(64), hide = __webpack_require__(56), $export = function(type, name, source) { + var global = __webpack_require__(24), core = __webpack_require__(17), ctx = __webpack_require__(47), hide = __webpack_require__(41), $export = function(type, name, source) { var key, own, out, IS_FORCED = type & $export.F, IS_GLOBAL = type & $export.G, IS_STATIC = type & $export.S, IS_PROTO = type & $export.P, IS_BIND = type & $export.B, IS_WRAP = type & $export.W, exports = IS_GLOBAL ? core : core[name] || (core[name] = {}), expProto = exports.prototype, target = IS_GLOBAL ? global : IS_STATIC ? global[name] : (global[name] || {}).prototype; IS_GLOBAL && (source = name); for (key in source) (own = !IS_FORCED && target && void 0 !== target[key]) && key in exports || (out = own ? target[key] : source[key], @@ -1523,108 +1454,25 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }; $export.F = 1, $export.G = 2, $export.S = 4, $export.P = 8, $export.B = 16, $export.W = 32, $export.U = 64, $export.R = 128, module.exports = $export; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - function _has(prop, obj) { - return Object.prototype.hasOwnProperty.call(obj, prop); - } - __webpack_exports__.a = _has; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_curry2__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_1__internal_dispatchable__ = __webpack_require__(15), __WEBPACK_IMPORTED_MODULE_2__internal_map__ = __webpack_require__(136), __WEBPACK_IMPORTED_MODULE_3__internal_reduce__ = __webpack_require__(30), __WEBPACK_IMPORTED_MODULE_4__internal_xmap__ = __webpack_require__(582), __WEBPACK_IMPORTED_MODULE_5__curryN__ = __webpack_require__(23), __WEBPACK_IMPORTED_MODULE_6__keys__ = __webpack_require__(44), map = Object(__WEBPACK_IMPORTED_MODULE_0__internal_curry2__.a)(Object(__WEBPACK_IMPORTED_MODULE_1__internal_dispatchable__.a)([ "fantasy-land/map", "map" ], __WEBPACK_IMPORTED_MODULE_4__internal_xmap__.a, function(fn, functor) { - switch (Object.prototype.toString.call(functor)) { - case "[object Function]": - return Object(__WEBPACK_IMPORTED_MODULE_5__curryN__.a)(functor.length, function() { - return fn.call(this, functor.apply(this, arguments)); - }); - - case "[object Object]": - return Object(__WEBPACK_IMPORTED_MODULE_3__internal_reduce__.a)(function(acc, key) { - return acc[key] = fn(functor[key]), acc; - }, {}, Object(__WEBPACK_IMPORTED_MODULE_6__keys__.a)(functor)); - - default: - return Object(__WEBPACK_IMPORTED_MODULE_2__internal_map__.a)(fn, functor); - } - })); - __webpack_exports__.a = map; }, function(module, exports) { function isNil(value) { return null == value; } module.exports = isNil; }, function(module, exports, __webpack_require__) { - var store = __webpack_require__(182)("wks"), uid = __webpack_require__(124), Symbol = __webpack_require__(36).Symbol, USE_SYMBOL = "function" == typeof Symbol; + var store = __webpack_require__(139)("wks"), uid = __webpack_require__(97), Symbol = __webpack_require__(24).Symbol, USE_SYMBOL = "function" == typeof Symbol; (module.exports = function(name) { return store[name] || (store[name] = USE_SYMBOL && Symbol[name] || (USE_SYMBOL ? Symbol : uid)("Symbol." + name)); }).store = store; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - function _arrayReduce(xf, acc, list) { - for (var idx = 0, len = list.length; idx < len; ) { - if ((acc = xf["@@transducer/step"](acc, list[idx])) && acc["@@transducer/reduced"]) { - acc = acc["@@transducer/value"]; - break; - } - idx += 1; - } - return xf["@@transducer/result"](acc); - } - function _iterableReduce(xf, acc, iter) { - for (var step = iter.next(); !step.done; ) { - if ((acc = xf["@@transducer/step"](acc, step.value)) && acc["@@transducer/reduced"]) { - acc = acc["@@transducer/value"]; - break; - } - step = iter.next(); - } - return xf["@@transducer/result"](acc); - } - function _methodReduce(xf, acc, obj, methodName) { - return xf["@@transducer/result"](obj[methodName](Object(__WEBPACK_IMPORTED_MODULE_2__bind__.a)(xf["@@transducer/step"], xf), acc)); - } - function _reduce(fn, acc, list) { - if ("function" == typeof fn && (fn = Object(__WEBPACK_IMPORTED_MODULE_1__xwrap__.a)(fn)), - Object(__WEBPACK_IMPORTED_MODULE_0__isArrayLike__.a)(list)) return _arrayReduce(fn, acc, list); - if ("function" == typeof list["fantasy-land/reduce"]) return _methodReduce(fn, acc, list, "fantasy-land/reduce"); - if (null != list[symIterator]) return _iterableReduce(fn, acc, list[symIterator]()); - if ("function" == typeof list.next) return _iterableReduce(fn, acc, list); - if ("function" == typeof list.reduce) return _methodReduce(fn, acc, list, "reduce"); - throw new TypeError("reduce: list must be array or iterable"); - } - __webpack_exports__.a = _reduce; - var __WEBPACK_IMPORTED_MODULE_0__isArrayLike__ = __webpack_require__(137), __WEBPACK_IMPORTED_MODULE_1__xwrap__ = __webpack_require__(298), __WEBPACK_IMPORTED_MODULE_2__bind__ = __webpack_require__(299), symIterator = "undefined" != typeof Symbol ? Symbol.iterator : "@@iterator"; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_curry2__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_1__internal_equals__ = __webpack_require__(605), equals = Object(__WEBPACK_IMPORTED_MODULE_0__internal_curry2__.a)(function(a, b) { - return Object(__WEBPACK_IMPORTED_MODULE_1__internal_equals__.a)(a, b, [], []); - }); - __webpack_exports__.a = equals; }, function(module, exports, __webpack_require__) { - var anObject = __webpack_require__(65), IE8_DOM_DEFINE = __webpack_require__(270), toPrimitive = __webpack_require__(176), dP = Object.defineProperty; - exports.f = __webpack_require__(37) ? Object.defineProperty : function(O, P, Attributes) { + var anObject = __webpack_require__(48), IE8_DOM_DEFINE = __webpack_require__(208), toPrimitive = __webpack_require__(133), dP = Object.defineProperty; + exports.f = __webpack_require__(25) ? Object.defineProperty : function(O, P, Attributes) { if (anObject(O), P = toPrimitive(P, !0), anObject(Attributes), IE8_DOM_DEFINE) try { return dP(O, P, Attributes); } catch (e) {} if ("get" in Attributes || "set" in Attributes) throw TypeError("Accessors not supported!"); return "value" in Attributes && (O[P] = Attributes.value), O; }; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - function _concat(set1, set2) { - set1 = set1 || [], set2 = set2 || []; - var idx, len1 = set1.length, len2 = set2.length, result = []; - for (idx = 0; idx < len1; ) result[result.length] = set1[idx], idx += 1; - for (idx = 0; idx < len2; ) result[result.length] = set2[idx], idx += 1; - return result; - } - __webpack_exports__.a = _concat; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_checkForMethod__ = __webpack_require__(99), __WEBPACK_IMPORTED_MODULE_1__internal_curry3__ = __webpack_require__(5), slice = Object(__WEBPACK_IMPORTED_MODULE_1__internal_curry3__.a)(Object(__WEBPACK_IMPORTED_MODULE_0__internal_checkForMethod__.a)("slice", function(fromIndex, toIndex, list) { - return Array.prototype.slice.call(list, fromIndex, toIndex); - })); - __webpack_exports__.a = slice; }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; function _defineProperty(obj, key, value) { @@ -1646,7 +1494,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }), __webpack_require__.d(__webpack_exports__, "d", function() { return inRangeOfSector; }); - var __WEBPACK_IMPORTED_MODULE_0_lodash_isNil__ = __webpack_require__(28), __WEBPACK_IMPORTED_MODULE_0_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_1__DataUtils__ = __webpack_require__(12), __WEBPACK_IMPORTED_MODULE_2__ChartUtils__ = __webpack_require__(21), _extends = Object.assign || function(target) { + var __WEBPACK_IMPORTED_MODULE_0_lodash_isNil__ = __webpack_require__(20), __WEBPACK_IMPORTED_MODULE_0_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_1__DataUtils__ = __webpack_require__(9), __WEBPACK_IMPORTED_MODULE_2__ChartUtils__ = __webpack_require__(16), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -1747,7 +1595,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { var global = module.exports = "undefined" != typeof window && window.Math == Math ? window : "undefined" != typeof self && self.Math == Math ? self : Function("return this")(); "number" == typeof __g && (__g = global); }, function(module, exports, __webpack_require__) { - module.exports = !__webpack_require__(66)(function() { + module.exports = !__webpack_require__(49)(function() { return 7 != Object.defineProperty({}, "a", { get: function() { return 7; @@ -1756,7 +1604,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }); }, function(module, exports, __webpack_require__) { module.exports = { - default: __webpack_require__(472), + default: __webpack_require__(355), __esModule: !0 }; }, function(module, exports, __webpack_require__) { @@ -1767,7 +1615,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }, function(module, exports, __webpack_require__) { "use strict"; exports.__esModule = !0; - var _defineProperty = __webpack_require__(185), _defineProperty2 = function(obj) { + var _defineProperty = __webpack_require__(142), _defineProperty2 = function(obj) { return obj && obj.__esModule ? obj : { default: obj }; @@ -1788,7 +1636,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }, function(module, exports, __webpack_require__) { "use strict"; exports.__esModule = !0; - var _typeof2 = __webpack_require__(126), _typeof3 = function(obj) { + var _typeof2 = __webpack_require__(99), _typeof3 = function(obj) { return obj && obj.__esModule ? obj : { default: obj }; @@ -1805,7 +1653,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }; } exports.__esModule = !0; - var _setPrototypeOf = __webpack_require__(489), _setPrototypeOf2 = _interopRequireDefault(_setPrototypeOf), _create = __webpack_require__(493), _create2 = _interopRequireDefault(_create), _typeof2 = __webpack_require__(126), _typeof3 = _interopRequireDefault(_typeof2); + var _setPrototypeOf = __webpack_require__(372), _setPrototypeOf2 = _interopRequireDefault(_setPrototypeOf), _create = __webpack_require__(376), _create2 = _interopRequireDefault(_create), _typeof2 = __webpack_require__(99), _typeof3 = _interopRequireDefault(_typeof2); exports.default = function(subClass, superClass) { if ("function" != typeof superClass && null !== superClass) throw new TypeError("Super expression must either be null or a function, not " + (void 0 === superClass ? "undefined" : (0, _typeof3.default)(superClass))); @@ -1818,100 +1666,8 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } }), superClass && (_setPrototypeOf2.default ? (0, _setPrototypeOf2.default)(subClass, superClass) : subClass.__proto__ = superClass); }; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - function _arity(n, fn) { - switch (n) { - case 0: - return function() { - return fn.apply(this, arguments); - }; - - case 1: - return function(a0) { - return fn.apply(this, arguments); - }; - - case 2: - return function(a0, a1) { - return fn.apply(this, arguments); - }; - - case 3: - return function(a0, a1, a2) { - return fn.apply(this, arguments); - }; - - case 4: - return function(a0, a1, a2, a3) { - return fn.apply(this, arguments); - }; - - case 5: - return function(a0, a1, a2, a3, a4) { - return fn.apply(this, arguments); - }; - - case 6: - return function(a0, a1, a2, a3, a4, a5) { - return fn.apply(this, arguments); - }; - - case 7: - return function(a0, a1, a2, a3, a4, a5, a6) { - return fn.apply(this, arguments); - }; - - case 8: - return function(a0, a1, a2, a3, a4, a5, a6, a7) { - return fn.apply(this, arguments); - }; - - case 9: - return function(a0, a1, a2, a3, a4, a5, a6, a7, a8) { - return fn.apply(this, arguments); - }; - - case 10: - return function(a0, a1, a2, a3, a4, a5, a6, a7, a8, a9) { - return fn.apply(this, arguments); - }; - - default: - throw new Error("First argument to _arity must be a non-negative integer no greater than ten"); - } - } - __webpack_exports__.a = _arity; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_curry1__ = __webpack_require__(4), __WEBPACK_IMPORTED_MODULE_1__internal_has__ = __webpack_require__(26), __WEBPACK_IMPORTED_MODULE_2__internal_isArguments__ = __webpack_require__(300), hasEnumBug = !{ - toString: null - }.propertyIsEnumerable("toString"), nonEnumerableProps = [ "constructor", "valueOf", "isPrototypeOf", "toString", "propertyIsEnumerable", "hasOwnProperty", "toLocaleString" ], hasArgsEnumBug = function() { - return arguments.propertyIsEnumerable("length"); - }(), contains = function(list, item) { - for (var idx = 0; idx < list.length; ) { - if (list[idx] === item) return !0; - idx += 1; - } - return !1; - }, _keys = "function" != typeof Object.keys || hasArgsEnumBug ? function(obj) { - if (Object(obj) !== obj) return []; - var prop, nIdx, ks = [], checkArgsLength = hasArgsEnumBug && Object(__WEBPACK_IMPORTED_MODULE_2__internal_isArguments__.a)(obj); - for (prop in obj) !Object(__WEBPACK_IMPORTED_MODULE_1__internal_has__.a)(prop, obj) || checkArgsLength && "length" === prop || (ks[ks.length] = prop); - if (hasEnumBug) for (nIdx = nonEnumerableProps.length - 1; nIdx >= 0; ) prop = nonEnumerableProps[nIdx], - Object(__WEBPACK_IMPORTED_MODULE_1__internal_has__.a)(prop, obj) && !contains(ks, prop) && (ks[ks.length] = prop), - nIdx -= 1; - return ks; - } : function(obj) { - return Object(obj) !== obj ? [] : Object.keys(obj); - }, keys = Object(__WEBPACK_IMPORTED_MODULE_0__internal_curry1__.a)(_keys); - __webpack_exports__.a = keys; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_curry3__ = __webpack_require__(5), __WEBPACK_IMPORTED_MODULE_1__internal_reduce__ = __webpack_require__(30), reduce = Object(__WEBPACK_IMPORTED_MODULE_0__internal_curry3__.a)(__WEBPACK_IMPORTED_MODULE_1__internal_reduce__.a); - __webpack_exports__.a = reduce; }, function(module, exports, __webpack_require__) { - var freeGlobal = __webpack_require__(365), freeSelf = "object" == typeof self && self && self.Object === Object && self, root = freeGlobal || freeSelf || Function("return this")(); + var freeGlobal = __webpack_require__(248), freeSelf = "object" == typeof self && self && self.Object === Object && self, root = freeGlobal || freeSelf || Function("return this")(); module.exports = root; }, function(module, exports) { function isObject(value) { @@ -1929,7 +1685,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { Object.defineProperty(exports, "__esModule", { value: !0 }), exports.translateStyle = exports.AnimateGroup = exports.configBezier = exports.configSpring = void 0; - var _Animate = __webpack_require__(383), _Animate2 = _interopRequireDefault(_Animate), _easing = __webpack_require__(395), _util = __webpack_require__(165), _AnimateGroup = __webpack_require__(986), _AnimateGroup2 = _interopRequireDefault(_AnimateGroup); + var _Animate = __webpack_require__(266), _Animate2 = _interopRequireDefault(_Animate), _easing = __webpack_require__(278), _util = __webpack_require__(122), _AnimateGroup = __webpack_require__(668), _AnimateGroup2 = _interopRequireDefault(_AnimateGroup); exports.configSpring = _easing.configSpring, exports.configBezier = _easing.configBezier, exports.AnimateGroup = _AnimateGroup2.default, exports.translateStyle = _util.translateStyle, exports.default = _Animate2.default; @@ -1937,7 +1693,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { function isEqual(value, other) { return baseIsEqual(value, other); } - var baseIsEqual = __webpack_require__(240); + var baseIsEqual = __webpack_require__(178); module.exports = isEqual; }, function(module, exports) { module.exports = function(it) { @@ -1945,7 +1701,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }; }, function(module, exports, __webpack_require__) { module.exports = { - default: __webpack_require__(500), + default: __webpack_require__(383), __esModule: !0 }; }, function(module, exports) { @@ -1955,32 +1711,32 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { module.exports = isObjectLike; }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__src_bisect__ = __webpack_require__(409); + var __WEBPACK_IMPORTED_MODULE_0__src_bisect__ = __webpack_require__(292); __webpack_require__.d(__webpack_exports__, "b", function() { return __WEBPACK_IMPORTED_MODULE_0__src_bisect__.a; }); - var __WEBPACK_IMPORTED_MODULE_1__src_ascending__ = __webpack_require__(84); + var __WEBPACK_IMPORTED_MODULE_1__src_ascending__ = __webpack_require__(63); __webpack_require__.d(__webpack_exports__, "a", function() { return __WEBPACK_IMPORTED_MODULE_1__src_ascending__.a; }); - var __WEBPACK_IMPORTED_MODULE_2__src_bisector__ = __webpack_require__(410); + var __WEBPACK_IMPORTED_MODULE_2__src_bisector__ = __webpack_require__(293); __webpack_require__.d(__webpack_exports__, "c", function() { return __WEBPACK_IMPORTED_MODULE_2__src_bisector__.a; }); - var __WEBPACK_IMPORTED_MODULE_18__src_quantile__ = (__webpack_require__(1015), __webpack_require__(1016), - __webpack_require__(412), __webpack_require__(414), __webpack_require__(1017), __webpack_require__(1020), - __webpack_require__(1021), __webpack_require__(418), __webpack_require__(1022), - __webpack_require__(1023), __webpack_require__(1024), __webpack_require__(1025), - __webpack_require__(419), __webpack_require__(411), __webpack_require__(1026), __webpack_require__(248)); + var __WEBPACK_IMPORTED_MODULE_18__src_quantile__ = (__webpack_require__(697), __webpack_require__(698), + __webpack_require__(295), __webpack_require__(297), __webpack_require__(699), __webpack_require__(702), + __webpack_require__(703), __webpack_require__(301), __webpack_require__(704), __webpack_require__(705), + __webpack_require__(706), __webpack_require__(707), __webpack_require__(302), __webpack_require__(294), + __webpack_require__(708), __webpack_require__(186)); __webpack_require__.d(__webpack_exports__, "d", function() { return __WEBPACK_IMPORTED_MODULE_18__src_quantile__.a; }); - var __WEBPACK_IMPORTED_MODULE_19__src_range__ = __webpack_require__(416); + var __WEBPACK_IMPORTED_MODULE_19__src_range__ = __webpack_require__(299); __webpack_require__.d(__webpack_exports__, "e", function() { return __WEBPACK_IMPORTED_MODULE_19__src_range__.a; }); - var __WEBPACK_IMPORTED_MODULE_23__src_ticks__ = (__webpack_require__(1027), __webpack_require__(1028), - __webpack_require__(1029), __webpack_require__(417)); + var __WEBPACK_IMPORTED_MODULE_23__src_ticks__ = (__webpack_require__(709), __webpack_require__(710), + __webpack_require__(711), __webpack_require__(300)); __webpack_require__.d(__webpack_exports__, "h", function() { return __WEBPACK_IMPORTED_MODULE_23__src_ticks__.a; }), __webpack_require__.d(__webpack_exports__, "f", function() { @@ -1988,7 +1744,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }), __webpack_require__.d(__webpack_exports__, "g", function() { return __WEBPACK_IMPORTED_MODULE_23__src_ticks__.c; }); - __webpack_require__(420), __webpack_require__(413), __webpack_require__(1030); + __webpack_require__(303), __webpack_require__(296), __webpack_require__(712); }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; __webpack_require__.d(__webpack_exports__, "d", function() { @@ -2019,31 +1775,17 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { return arg; }, module.exports = emptyFunction; }, function(module, exports, __webpack_require__) { - var dP = __webpack_require__(32), createDesc = __webpack_require__(91); - module.exports = __webpack_require__(37) ? function(object, key, value) { + var dP = __webpack_require__(22), createDesc = __webpack_require__(70); + module.exports = __webpack_require__(25) ? function(object, key, value) { return dP.f(object, key, createDesc(1, value)); } : function(object, key, value) { return object[key] = value, object; }; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - __webpack_exports__.a = Array.isArray || function(val) { - return null != val && val.length >= 0 && "[object Array]" === Object.prototype.toString.call(val); - }; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - function _reduced(x) { - return x && x["@@transducer/reduced"] ? x : { - "@@transducer/value": x, - "@@transducer/reduced": !0 - }; - } - __webpack_exports__.a = _reduced; }, function(module, exports, __webpack_require__) { function baseGetTag(value) { return null == value ? void 0 === value ? undefinedTag : nullTag : symToStringTag && symToStringTag in Object(value) ? getRawTag(value) : objectToString(value); } - var Symbol = __webpack_require__(104), getRawTag = __webpack_require__(861), objectToString = __webpack_require__(862), nullTag = "[object Null]", undefinedTag = "[object Undefined]", symToStringTag = Symbol ? Symbol.toStringTag : void 0; + var Symbol = __webpack_require__(77), getRawTag = __webpack_require__(543), objectToString = __webpack_require__(544), nullTag = "[object Null]", undefinedTag = "[object Undefined]", symToStringTag = Symbol ? Symbol.toStringTag : void 0; module.exports = baseGetTag; }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; @@ -2069,7 +1811,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { className: __WEBPACK_IMPORTED_MODULE_5_classnames___default()("recharts-label", className) }, attrs, positionAttrs), label); } - var __WEBPACK_IMPORTED_MODULE_0_lodash_isObject__ = __webpack_require__(47), __WEBPACK_IMPORTED_MODULE_0_lodash_isObject___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isObject__), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__ = __webpack_require__(11), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__), __WEBPACK_IMPORTED_MODULE_2_lodash_isNil__ = __webpack_require__(28), __WEBPACK_IMPORTED_MODULE_2_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_3_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_3_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_react__), __WEBPACK_IMPORTED_MODULE_4_prop_types__ = __webpack_require__(2), __WEBPACK_IMPORTED_MODULE_4_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_prop_types__), __WEBPACK_IMPORTED_MODULE_5_classnames__ = __webpack_require__(6), __WEBPACK_IMPORTED_MODULE_5_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_classnames__), __WEBPACK_IMPORTED_MODULE_6__Text__ = __webpack_require__(72), __WEBPACK_IMPORTED_MODULE_7__util_ReactUtils__ = __webpack_require__(7), __WEBPACK_IMPORTED_MODULE_8__util_DataUtils__ = __webpack_require__(12), __WEBPACK_IMPORTED_MODULE_9__util_PolarUtils__ = __webpack_require__(35), _extends = Object.assign || function(target) { + var __WEBPACK_IMPORTED_MODULE_0_lodash_isObject__ = __webpack_require__(32), __WEBPACK_IMPORTED_MODULE_0_lodash_isObject___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isObject__), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__ = __webpack_require__(8), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__), __WEBPACK_IMPORTED_MODULE_2_lodash_isNil__ = __webpack_require__(20), __WEBPACK_IMPORTED_MODULE_2_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_3_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_3_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_react__), __WEBPACK_IMPORTED_MODULE_4_prop_types__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_4_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_prop_types__), __WEBPACK_IMPORTED_MODULE_5_classnames__ = __webpack_require__(3), __WEBPACK_IMPORTED_MODULE_5_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_classnames__), __WEBPACK_IMPORTED_MODULE_6__Text__ = __webpack_require__(55), __WEBPACK_IMPORTED_MODULE_7__util_ReactUtils__ = __webpack_require__(4), __WEBPACK_IMPORTED_MODULE_8__util_DataUtils__ = __webpack_require__(9), __WEBPACK_IMPORTED_MODULE_9__util_PolarUtils__ = __webpack_require__(23), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -2281,7 +2023,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { __webpack_exports__.a = Label; }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__src_color__ = __webpack_require__(251); + var __WEBPACK_IMPORTED_MODULE_0__src_color__ = __webpack_require__(189); __webpack_require__.d(__webpack_exports__, "a", function() { return __WEBPACK_IMPORTED_MODULE_0__src_color__.e; }), __webpack_require__.d(__webpack_exports__, "f", function() { @@ -2289,13 +2031,13 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }), __webpack_require__.d(__webpack_exports__, "d", function() { return __WEBPACK_IMPORTED_MODULE_0__src_color__.f; }); - var __WEBPACK_IMPORTED_MODULE_1__src_lab__ = __webpack_require__(1038); + var __WEBPACK_IMPORTED_MODULE_1__src_lab__ = __webpack_require__(720); __webpack_require__.d(__webpack_exports__, "e", function() { return __WEBPACK_IMPORTED_MODULE_1__src_lab__.a; }), __webpack_require__.d(__webpack_exports__, "c", function() { return __WEBPACK_IMPORTED_MODULE_1__src_lab__.b; }); - var __WEBPACK_IMPORTED_MODULE_2__src_cubehelix__ = __webpack_require__(1039); + var __WEBPACK_IMPORTED_MODULE_2__src_cubehelix__ = __webpack_require__(721); __webpack_require__.d(__webpack_exports__, "b", function() { return __WEBPACK_IMPORTED_MODULE_2__src_cubehelix__.a; }); @@ -2331,7 +2073,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { })); })) : null; } - var __WEBPACK_IMPORTED_MODULE_0_lodash_isObject__ = __webpack_require__(47), __WEBPACK_IMPORTED_MODULE_0_lodash_isObject___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isObject__), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__ = __webpack_require__(11), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__), __WEBPACK_IMPORTED_MODULE_2_lodash_isNil__ = __webpack_require__(28), __WEBPACK_IMPORTED_MODULE_2_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_3_lodash_last__ = __webpack_require__(1089), __WEBPACK_IMPORTED_MODULE_3_lodash_last___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_lodash_last__), __WEBPACK_IMPORTED_MODULE_4_lodash_isArray__ = __webpack_require__(16), __WEBPACK_IMPORTED_MODULE_4_lodash_isArray___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_lodash_isArray__), __WEBPACK_IMPORTED_MODULE_5_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_5_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_react__), __WEBPACK_IMPORTED_MODULE_6_prop_types__ = __webpack_require__(2), __WEBPACK_IMPORTED_MODULE_6_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_6_prop_types__), __WEBPACK_IMPORTED_MODULE_7__Label__ = __webpack_require__(60), __WEBPACK_IMPORTED_MODULE_8__container_Layer__ = __webpack_require__(18), __WEBPACK_IMPORTED_MODULE_9__util_ReactUtils__ = __webpack_require__(7), __WEBPACK_IMPORTED_MODULE_10__util_ChartUtils__ = __webpack_require__(21), _extends = Object.assign || function(target) { + var __WEBPACK_IMPORTED_MODULE_0_lodash_isObject__ = __webpack_require__(32), __WEBPACK_IMPORTED_MODULE_0_lodash_isObject___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isObject__), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__ = __webpack_require__(8), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__), __WEBPACK_IMPORTED_MODULE_2_lodash_isNil__ = __webpack_require__(20), __WEBPACK_IMPORTED_MODULE_2_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_3_lodash_last__ = __webpack_require__(771), __WEBPACK_IMPORTED_MODULE_3_lodash_last___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_lodash_last__), __WEBPACK_IMPORTED_MODULE_4_lodash_isArray__ = __webpack_require__(12), __WEBPACK_IMPORTED_MODULE_4_lodash_isArray___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_lodash_isArray__), __WEBPACK_IMPORTED_MODULE_5_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_5_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_react__), __WEBPACK_IMPORTED_MODULE_6_prop_types__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_6_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_6_prop_types__), __WEBPACK_IMPORTED_MODULE_7__Label__ = __webpack_require__(43), __WEBPACK_IMPORTED_MODULE_8__container_Layer__ = __webpack_require__(14), __WEBPACK_IMPORTED_MODULE_9__util_ReactUtils__ = __webpack_require__(4), __WEBPACK_IMPORTED_MODULE_10__util_ChartUtils__ = __webpack_require__(16), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -2415,7 +2157,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } }), superClass && (Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass); } - var __WEBPACK_IMPORTED_MODULE_0_lodash_sortBy__ = __webpack_require__(402), __WEBPACK_IMPORTED_MODULE_0_lodash_sortBy___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_sortBy__), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__ = __webpack_require__(11), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__), __WEBPACK_IMPORTED_MODULE_2_lodash_get__ = __webpack_require__(152), __WEBPACK_IMPORTED_MODULE_2_lodash_get___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_lodash_get__), __WEBPACK_IMPORTED_MODULE_3_lodash_range__ = __webpack_require__(450), __WEBPACK_IMPORTED_MODULE_3_lodash_range___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_lodash_range__), __WEBPACK_IMPORTED_MODULE_4_lodash_throttle__ = __webpack_require__(1097), __WEBPACK_IMPORTED_MODULE_4_lodash_throttle___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_lodash_throttle__), __WEBPACK_IMPORTED_MODULE_5_lodash_isNil__ = __webpack_require__(28), __WEBPACK_IMPORTED_MODULE_5_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_6_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_6_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_6_react__), __WEBPACK_IMPORTED_MODULE_7_prop_types__ = __webpack_require__(2), __WEBPACK_IMPORTED_MODULE_7_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_7_prop_types__), __WEBPACK_IMPORTED_MODULE_8_classnames__ = __webpack_require__(6), __WEBPACK_IMPORTED_MODULE_8_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_8_classnames__), __WEBPACK_IMPORTED_MODULE_9__container_Surface__ = __webpack_require__(103), __WEBPACK_IMPORTED_MODULE_10__container_Layer__ = __webpack_require__(18), __WEBPACK_IMPORTED_MODULE_11__component_Tooltip__ = __webpack_require__(164), __WEBPACK_IMPORTED_MODULE_12__component_Legend__ = __webpack_require__(233), __WEBPACK_IMPORTED_MODULE_13__shape_Curve__ = __webpack_require__(86), __WEBPACK_IMPORTED_MODULE_14__shape_Cross__ = __webpack_require__(444), __WEBPACK_IMPORTED_MODULE_15__shape_Sector__ = __webpack_require__(170), __WEBPACK_IMPORTED_MODULE_16__shape_Dot__ = __webpack_require__(74), __WEBPACK_IMPORTED_MODULE_17__shape_Rectangle__ = __webpack_require__(85), __WEBPACK_IMPORTED_MODULE_18__util_ReactUtils__ = __webpack_require__(7), __WEBPACK_IMPORTED_MODULE_19__cartesian_CartesianAxis__ = __webpack_require__(451), __WEBPACK_IMPORTED_MODULE_20__cartesian_Brush__ = __webpack_require__(449), __WEBPACK_IMPORTED_MODULE_21__util_DOMUtils__ = __webpack_require__(247), __WEBPACK_IMPORTED_MODULE_22__util_DataUtils__ = __webpack_require__(12), __WEBPACK_IMPORTED_MODULE_23__util_ChartUtils__ = __webpack_require__(21), __WEBPACK_IMPORTED_MODULE_24__util_PolarUtils__ = __webpack_require__(35), __WEBPACK_IMPORTED_MODULE_25__util_PureRender__ = __webpack_require__(8), __WEBPACK_IMPORTED_MODULE_26__util_Events__ = __webpack_require__(1098), _extends = Object.assign || function(target) { + var __WEBPACK_IMPORTED_MODULE_0_lodash_sortBy__ = __webpack_require__(285), __WEBPACK_IMPORTED_MODULE_0_lodash_sortBy___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_sortBy__), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__ = __webpack_require__(8), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__), __WEBPACK_IMPORTED_MODULE_2_lodash_get__ = __webpack_require__(109), __WEBPACK_IMPORTED_MODULE_2_lodash_get___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_lodash_get__), __WEBPACK_IMPORTED_MODULE_3_lodash_range__ = __webpack_require__(333), __WEBPACK_IMPORTED_MODULE_3_lodash_range___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_lodash_range__), __WEBPACK_IMPORTED_MODULE_4_lodash_throttle__ = __webpack_require__(779), __WEBPACK_IMPORTED_MODULE_4_lodash_throttle___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_lodash_throttle__), __WEBPACK_IMPORTED_MODULE_5_lodash_isNil__ = __webpack_require__(20), __WEBPACK_IMPORTED_MODULE_5_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_6_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_6_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_6_react__), __WEBPACK_IMPORTED_MODULE_7_prop_types__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_7_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_7_prop_types__), __WEBPACK_IMPORTED_MODULE_8_classnames__ = __webpack_require__(3), __WEBPACK_IMPORTED_MODULE_8_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_8_classnames__), __WEBPACK_IMPORTED_MODULE_9__container_Surface__ = __webpack_require__(76), __WEBPACK_IMPORTED_MODULE_10__container_Layer__ = __webpack_require__(14), __WEBPACK_IMPORTED_MODULE_11__component_Tooltip__ = __webpack_require__(121), __WEBPACK_IMPORTED_MODULE_12__component_Legend__ = __webpack_require__(171), __WEBPACK_IMPORTED_MODULE_13__shape_Curve__ = __webpack_require__(65), __WEBPACK_IMPORTED_MODULE_14__shape_Cross__ = __webpack_require__(327), __WEBPACK_IMPORTED_MODULE_15__shape_Sector__ = __webpack_require__(127), __WEBPACK_IMPORTED_MODULE_16__shape_Dot__ = __webpack_require__(57), __WEBPACK_IMPORTED_MODULE_17__shape_Rectangle__ = __webpack_require__(64), __WEBPACK_IMPORTED_MODULE_18__util_ReactUtils__ = __webpack_require__(4), __WEBPACK_IMPORTED_MODULE_19__cartesian_CartesianAxis__ = __webpack_require__(334), __WEBPACK_IMPORTED_MODULE_20__cartesian_Brush__ = __webpack_require__(332), __WEBPACK_IMPORTED_MODULE_21__util_DOMUtils__ = __webpack_require__(185), __WEBPACK_IMPORTED_MODULE_22__util_DataUtils__ = __webpack_require__(9), __WEBPACK_IMPORTED_MODULE_23__util_ChartUtils__ = __webpack_require__(16), __WEBPACK_IMPORTED_MODULE_24__util_PolarUtils__ = __webpack_require__(23), __WEBPACK_IMPORTED_MODULE_25__util_PureRender__ = __webpack_require__(5), __WEBPACK_IMPORTED_MODULE_26__util_Events__ = __webpack_require__(780), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -3429,7 +3171,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }; __webpack_exports__.a = generateCategoricalChart; }, function(module, exports, __webpack_require__) { - var aFunction = __webpack_require__(269); + var aFunction = __webpack_require__(207); module.exports = function(fn, that, length) { if (aFunction(fn), void 0 === that) return fn; switch (length) { @@ -3453,7 +3195,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }; }; }, function(module, exports, __webpack_require__) { - var isObject = __webpack_require__(50); + var isObject = __webpack_require__(35); module.exports = function(it) { if (!isObject(it)) throw TypeError(it + " is not an object!"); return it; @@ -3526,17 +3268,17 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { Object.defineProperty(exports, "__esModule", { value: !0 }); - var _typeof2 = __webpack_require__(126), _typeof3 = _interopRequireDefault(_typeof2), _keys = __webpack_require__(51), _keys2 = _interopRequireDefault(_keys); + var _typeof2 = __webpack_require__(99), _typeof3 = _interopRequireDefault(_typeof2), _keys = __webpack_require__(36), _keys2 = _interopRequireDefault(_keys); exports.capitalizeFirstLetter = capitalizeFirstLetter, exports.contains = contains, exports.findIndex = findIndex, exports.find = find, exports.createChainedFunction = createChainedFunction; - var _warning = __webpack_require__(14), _warning2 = _interopRequireDefault(_warning); - }).call(exports, __webpack_require__(3)); + var _warning = __webpack_require__(11), _warning2 = _interopRequireDefault(_warning); + }).call(exports, __webpack_require__(2)); }, function(module, exports, __webpack_require__) { function getNative(object, key) { var value = getValue(object, key); return baseIsNative(value) ? value : void 0; } - var baseIsNative = __webpack_require__(869), getValue = __webpack_require__(872); + var baseIsNative = __webpack_require__(551), getValue = __webpack_require__(554); module.exports = getNative; }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; @@ -3570,7 +3312,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } }), superClass && (Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass); } - var _class, _temp2, __WEBPACK_IMPORTED_MODULE_0_lodash_isNil__ = __webpack_require__(28), __WEBPACK_IMPORTED_MODULE_0_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_1_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_1_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_react__), __WEBPACK_IMPORTED_MODULE_2_prop_types__ = __webpack_require__(2), __WEBPACK_IMPORTED_MODULE_2_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_prop_types__), __WEBPACK_IMPORTED_MODULE_3_reduce_css_calc__ = __webpack_require__(994), __WEBPACK_IMPORTED_MODULE_3_reduce_css_calc___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_reduce_css_calc__), __WEBPACK_IMPORTED_MODULE_4_classnames__ = __webpack_require__(6), __WEBPACK_IMPORTED_MODULE_4_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_classnames__), __WEBPACK_IMPORTED_MODULE_5__util_DataUtils__ = __webpack_require__(12), __WEBPACK_IMPORTED_MODULE_6__util_ReactUtils__ = __webpack_require__(7), __WEBPACK_IMPORTED_MODULE_7__util_DOMUtils__ = __webpack_require__(247), _extends = Object.assign || function(target) { + var _class, _temp2, __WEBPACK_IMPORTED_MODULE_0_lodash_isNil__ = __webpack_require__(20), __WEBPACK_IMPORTED_MODULE_0_lodash_isNil___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isNil__), __WEBPACK_IMPORTED_MODULE_1_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_1_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_react__), __WEBPACK_IMPORTED_MODULE_2_prop_types__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_2_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_prop_types__), __WEBPACK_IMPORTED_MODULE_3_reduce_css_calc__ = __webpack_require__(676), __WEBPACK_IMPORTED_MODULE_3_reduce_css_calc___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_reduce_css_calc__), __WEBPACK_IMPORTED_MODULE_4_classnames__ = __webpack_require__(3), __WEBPACK_IMPORTED_MODULE_4_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_4_classnames__), __WEBPACK_IMPORTED_MODULE_5__util_DataUtils__ = __webpack_require__(9), __WEBPACK_IMPORTED_MODULE_6__util_ReactUtils__ = __webpack_require__(4), __WEBPACK_IMPORTED_MODULE_7__util_DOMUtils__ = __webpack_require__(185), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -3748,7 +3490,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } }), superClass && (Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass); } - var _class, _class2, _temp, __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_0_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = __webpack_require__(2), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2_classnames__ = __webpack_require__(6), __WEBPACK_IMPORTED_MODULE_2_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_classnames__), __WEBPACK_IMPORTED_MODULE_3__util_PureRender__ = __webpack_require__(8), __WEBPACK_IMPORTED_MODULE_4__util_ReactUtils__ = __webpack_require__(7), _extends = Object.assign || function(target) { + var _class, _class2, _temp, __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_0_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2_classnames__ = __webpack_require__(3), __WEBPACK_IMPORTED_MODULE_2_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_classnames__), __WEBPACK_IMPORTED_MODULE_3__util_PureRender__ = __webpack_require__(5), __WEBPACK_IMPORTED_MODULE_4__util_ReactUtils__ = __webpack_require__(4), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -3790,12 +3532,12 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }, _class = _temp)) || _class; __webpack_exports__.a = Dot; }, function(module, exports, __webpack_require__) { - var IObject = __webpack_require__(177), defined = __webpack_require__(179); + var IObject = __webpack_require__(134), defined = __webpack_require__(136); module.exports = function(it) { return IObject(defined(it)); }; }, function(module, exports, __webpack_require__) { - var defined = __webpack_require__(179); + var defined = __webpack_require__(136); module.exports = function(it) { return Object(defined(it)); }; @@ -3834,7 +3576,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { return protoProps && defineProperties(Constructor.prototype, protoProps), staticProps && defineProperties(Constructor, staticProps), Constructor; }; - }(), _warning = __webpack_require__(14), _warning2 = _interopRequireDefault(_warning), _toCss = __webpack_require__(195), _toCss2 = _interopRequireDefault(_toCss), _toCssValue = __webpack_require__(196), _toCssValue2 = _interopRequireDefault(_toCssValue), StyleRule = function() { + }(), _warning = __webpack_require__(11), _warning2 = _interopRequireDefault(_warning), _toCss = __webpack_require__(152), _toCss2 = _interopRequireDefault(_toCss), _toCssValue = __webpack_require__(153), _toCssValue2 = _interopRequireDefault(_toCssValue), StyleRule = function() { function StyleRule(key, style, options) { _classCallCheck(this, StyleRule), this.type = "style", this.isProcessed = !1; var sheet = options.sheet, Renderer = options.Renderer, selector = options.selector; @@ -3896,42 +3638,11 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } ]), StyleRule; }(); exports.default = StyleRule; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_curry1__ = __webpack_require__(4), always = Object(__WEBPACK_IMPORTED_MODULE_0__internal_curry1__.a)(function(val) { - return function() { - return val; - }; - }); - __webpack_exports__.a = always; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_curry2__ = __webpack_require__(0), max = Object(__WEBPACK_IMPORTED_MODULE_0__internal_curry2__.a)(function(a, b) { - return b > a ? b : a; - }); - __webpack_exports__.a = max; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_curry2__ = __webpack_require__(0), path = Object(__WEBPACK_IMPORTED_MODULE_0__internal_curry2__.a)(function(paths, obj) { - for (var val = obj, idx = 0; idx < paths.length; ) { - if (null == val) return; - val = val[paths[idx]], idx += 1; - } - return val; - }); - __webpack_exports__.a = path; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - function _contains(a, list) { - return Object(__WEBPACK_IMPORTED_MODULE_0__indexOf__.a)(list, a, 0) >= 0; - } - __webpack_exports__.a = _contains; - var __WEBPACK_IMPORTED_MODULE_0__indexOf__ = __webpack_require__(316); }, function(module, exports, __webpack_require__) { function isSymbol(value) { return "symbol" == typeof value || isObjectLike(value) && baseGetTag(value) == symbolTag; } - var baseGetTag = __webpack_require__(59), isObjectLike = __webpack_require__(52), symbolTag = "[object Symbol]"; + var baseGetTag = __webpack_require__(42), isObjectLike = __webpack_require__(37), symbolTag = "[object Symbol]"; module.exports = isSymbol; }, function(module, exports) { function identity(value) { @@ -3963,7 +3674,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } }), superClass && (Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass); } - var _class, _class2, _temp2, __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_0_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = __webpack_require__(2), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2_classnames__ = __webpack_require__(6), __WEBPACK_IMPORTED_MODULE_2_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_classnames__), __WEBPACK_IMPORTED_MODULE_3_react_smooth__ = __webpack_require__(48), __WEBPACK_IMPORTED_MODULE_3_react_smooth___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_react_smooth__), __WEBPACK_IMPORTED_MODULE_4__util_PureRender__ = __webpack_require__(8), __WEBPACK_IMPORTED_MODULE_5__util_ReactUtils__ = __webpack_require__(7), _extends = Object.assign || function(target) { + var _class, _class2, _temp2, __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_0_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2_classnames__ = __webpack_require__(3), __WEBPACK_IMPORTED_MODULE_2_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_classnames__), __WEBPACK_IMPORTED_MODULE_3_react_smooth__ = __webpack_require__(33), __WEBPACK_IMPORTED_MODULE_3_react_smooth___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_react_smooth__), __WEBPACK_IMPORTED_MODULE_4__util_PureRender__ = __webpack_require__(5), __WEBPACK_IMPORTED_MODULE_5__util_ReactUtils__ = __webpack_require__(4), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -4108,7 +3819,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } }), superClass && (Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass); } - var _class, _class2, _temp, __WEBPACK_IMPORTED_MODULE_0_lodash_isArray__ = __webpack_require__(16), __WEBPACK_IMPORTED_MODULE_0_lodash_isArray___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isArray__), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__ = __webpack_require__(11), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__), __WEBPACK_IMPORTED_MODULE_2_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_2_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_react__), __WEBPACK_IMPORTED_MODULE_3_prop_types__ = __webpack_require__(2), __WEBPACK_IMPORTED_MODULE_3_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_prop_types__), __WEBPACK_IMPORTED_MODULE_4_d3_shape__ = __webpack_require__(235), __WEBPACK_IMPORTED_MODULE_5_classnames__ = __webpack_require__(6), __WEBPACK_IMPORTED_MODULE_5_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_classnames__), __WEBPACK_IMPORTED_MODULE_6__util_PureRender__ = __webpack_require__(8), __WEBPACK_IMPORTED_MODULE_7__util_ReactUtils__ = __webpack_require__(7), __WEBPACK_IMPORTED_MODULE_8__util_DataUtils__ = __webpack_require__(12), _extends = Object.assign || function(target) { + var _class, _class2, _temp, __WEBPACK_IMPORTED_MODULE_0_lodash_isArray__ = __webpack_require__(12), __WEBPACK_IMPORTED_MODULE_0_lodash_isArray___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_lodash_isArray__), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__ = __webpack_require__(8), __WEBPACK_IMPORTED_MODULE_1_lodash_isFunction___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_lodash_isFunction__), __WEBPACK_IMPORTED_MODULE_2_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_2_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_react__), __WEBPACK_IMPORTED_MODULE_3_prop_types__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_3_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_3_prop_types__), __WEBPACK_IMPORTED_MODULE_4_d3_shape__ = __webpack_require__(173), __WEBPACK_IMPORTED_MODULE_5_classnames__ = __webpack_require__(3), __WEBPACK_IMPORTED_MODULE_5_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_5_classnames__), __WEBPACK_IMPORTED_MODULE_6__util_PureRender__ = __webpack_require__(5), __WEBPACK_IMPORTED_MODULE_7__util_ReactUtils__ = __webpack_require__(4), __WEBPACK_IMPORTED_MODULE_8__util_DataUtils__ = __webpack_require__(9), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -4222,8 +3933,8 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } }), superClass && (Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass); } - var _class, _class2, _temp, __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = (__webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), - __webpack_require__(2)), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2__util_PureRender__ = __webpack_require__(8), __WEBPACK_IMPORTED_MODULE_3__util_ReactUtils__ = __webpack_require__(7), _createClass = function() { + var _class, _class2, _temp, __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = (__webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), + __webpack_require__(1)), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2__util_PureRender__ = __webpack_require__(5), __WEBPACK_IMPORTED_MODULE_3__util_ReactUtils__ = __webpack_require__(4), _createClass = function() { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; @@ -4317,8 +4028,8 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } }), superClass && (Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass); } - var _class, _class2, _temp, __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = (__webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), - __webpack_require__(2)), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2__util_PureRender__ = __webpack_require__(8), _createClass = function() { + var _class, _class2, _temp, __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = (__webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), + __webpack_require__(1)), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2__util_PureRender__ = __webpack_require__(5), _createClass = function() { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; @@ -4445,7 +4156,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { "production" !== process.env.NODE_ENV && (validateFormat = function(format) { if (void 0 === format) throw new Error("invariant requires an error message argument"); }), module.exports = invariant; - }).call(exports, __webpack_require__(3)); + }).call(exports, __webpack_require__(2)); }, function(module, exports) { module.exports = function(bitmap, value) { return { @@ -4456,7 +4167,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }; }; }, function(module, exports, __webpack_require__) { - var $keys = __webpack_require__(272), enumBugKeys = __webpack_require__(183); + var $keys = __webpack_require__(210), enumBugKeys = __webpack_require__(140); module.exports = Object.keys || function(O) { return $keys(O, enumBugKeys); }; @@ -4507,13 +4218,13 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { Object.defineProperty(exports, "__esModule", { value: !0 }), exports.keys = void 0; - var _extends2 = __webpack_require__(10), _extends3 = _interopRequireDefault(_extends2), _objectWithoutProperties2 = __webpack_require__(9), _objectWithoutProperties3 = _interopRequireDefault(_objectWithoutProperties2); + var _extends2 = __webpack_require__(7), _extends3 = _interopRequireDefault(_extends2), _objectWithoutProperties2 = __webpack_require__(6), _objectWithoutProperties3 = _interopRequireDefault(_objectWithoutProperties2); exports.default = createBreakpoints; var keys = exports.keys = [ "xs", "sm", "md", "lg", "xl" ]; }, function(module, exports, __webpack_require__) { "use strict"; exports.__esModule = !0; - var _getDisplayName = __webpack_require__(289), _getDisplayName2 = function(obj) { + var _getDisplayName = __webpack_require__(227), _getDisplayName2 = function(obj) { return obj && obj.__esModule ? obj : { default: obj }; @@ -4552,7 +4263,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { return protoProps && defineProperties(Constructor.prototype, protoProps), staticProps && defineProperties(Constructor, staticProps), Constructor; }; - }(), _createRule = __webpack_require__(131), _createRule2 = _interopRequireDefault(_createRule), _linkRule = __webpack_require__(294), _linkRule2 = _interopRequireDefault(_linkRule), _StyleRule = __webpack_require__(77), _StyleRule2 = _interopRequireDefault(_StyleRule), _escape = __webpack_require__(546), _escape2 = _interopRequireDefault(_escape), RuleList = function() { + }(), _createRule = __webpack_require__(104), _createRule2 = _interopRequireDefault(_createRule), _linkRule = __webpack_require__(232), _linkRule2 = _interopRequireDefault(_linkRule), _StyleRule = __webpack_require__(60), _StyleRule2 = _interopRequireDefault(_StyleRule), _escape = __webpack_require__(429), _escape2 = _interopRequireDefault(_escape), RuleList = function() { function RuleList(options) { _classCallCheck(this, RuleList), this.map = {}, this.raw = {}, this.index = [], this.options = options, this.classes = options.classes; @@ -4638,53 +4349,6 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } ]), RuleList; }(); exports.default = RuleList; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_curry2__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_1__map__ = __webpack_require__(27), __WEBPACK_IMPORTED_MODULE_2__prop__ = __webpack_require__(201), pluck = Object(__WEBPACK_IMPORTED_MODULE_0__internal_curry2__.a)(function(p, list) { - return Object(__WEBPACK_IMPORTED_MODULE_1__map__.a)(Object(__WEBPACK_IMPORTED_MODULE_2__prop__.a)(p), list); - }); - __webpack_exports__.a = pluck; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - function _isString(x) { - return "[object String]" === Object.prototype.toString.call(x); - } - __webpack_exports__.a = _isString; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - function _checkForMethod(methodname, fn) { - return function() { - var length = arguments.length; - if (0 === length) return fn(); - var obj = arguments[length - 1]; - return Object(__WEBPACK_IMPORTED_MODULE_0__isArray__.a)(obj) || "function" != typeof obj[methodname] ? fn.apply(this, arguments) : obj[methodname].apply(obj, Array.prototype.slice.call(arguments, 0, length - 1)); - }; - } - __webpack_exports__.a = _checkForMethod; - var __WEBPACK_IMPORTED_MODULE_0__isArray__ = __webpack_require__(57); -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_curry1__ = __webpack_require__(4), __WEBPACK_IMPORTED_MODULE_1__internal_toString__ = __webpack_require__(604), toString = Object(__WEBPACK_IMPORTED_MODULE_0__internal_curry1__.a)(function(val) { - return Object(__WEBPACK_IMPORTED_MODULE_1__internal_toString__.a)(val, []); - }); - __webpack_exports__.a = toString; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_curry2__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_1__internal_isString__ = __webpack_require__(98), nth = Object(__WEBPACK_IMPORTED_MODULE_0__internal_curry2__.a)(function(offset, list) { - var idx = offset < 0 ? list.length + offset : offset; - return Object(__WEBPACK_IMPORTED_MODULE_1__internal_isString__.a)(list) ? list.charAt(idx) : list[idx]; - }); - __webpack_exports__.a = nth; -}, function(module, __webpack_exports__, __webpack_require__) { - "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__internal_curry2__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_1__internal_isFunction__ = __webpack_require__(140), __WEBPACK_IMPORTED_MODULE_2__curryN__ = __webpack_require__(23), __WEBPACK_IMPORTED_MODULE_3__toString__ = __webpack_require__(100), invoker = Object(__WEBPACK_IMPORTED_MODULE_0__internal_curry2__.a)(function(arity, method) { - return Object(__WEBPACK_IMPORTED_MODULE_2__curryN__.a)(arity + 1, function() { - var target = arguments[arity]; - if (null != target && Object(__WEBPACK_IMPORTED_MODULE_1__internal_isFunction__.a)(target[method])) return target[method].apply(target, Array.prototype.slice.call(arguments, 0, arity)); - throw new TypeError(Object(__WEBPACK_IMPORTED_MODULE_3__toString__.a)(target) + ' does not have a method named "' + method + '"'); - }); - }); - __webpack_exports__.a = invoker; }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; function _objectWithoutProperties(obj, keys) { @@ -4708,7 +4372,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { version: "1.1" }), children); } - var __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_0_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = __webpack_require__(2), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2_classnames__ = __webpack_require__(6), __WEBPACK_IMPORTED_MODULE_2_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_classnames__), __WEBPACK_IMPORTED_MODULE_3__util_ReactUtils__ = __webpack_require__(7), _extends = Object.assign || function(target) { + var __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_0_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2_classnames__ = __webpack_require__(3), __WEBPACK_IMPORTED_MODULE_2_classnames___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_2_classnames__), __WEBPACK_IMPORTED_MODULE_3__util_ReactUtils__ = __webpack_require__(4), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -4729,11 +4393,11 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }; Surface.propTypes = propTypes, __webpack_exports__.a = Surface; }, function(module, exports, __webpack_require__) { - var root = __webpack_require__(46), Symbol = root.Symbol; + var root = __webpack_require__(31), Symbol = root.Symbol; module.exports = Symbol; }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__src_path__ = __webpack_require__(891); + var __WEBPACK_IMPORTED_MODULE_0__src_path__ = __webpack_require__(573); __webpack_require__.d(__webpack_exports__, "a", function() { return __WEBPACK_IMPORTED_MODULE_0__src_path__.a; }); @@ -4785,21 +4449,21 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { function isArrayLike(value) { return null != value && isLength(value.length) && !isFunction(value); } - var isFunction = __webpack_require__(11), isLength = __webpack_require__(244); + var isFunction = __webpack_require__(8), isLength = __webpack_require__(182); module.exports = isArrayLike; }, function(module, exports, __webpack_require__) { function baseIteratee(value) { return "function" == typeof value ? value : null == value ? identity : "object" == typeof value ? isArray(value) ? baseMatchesProperty(value[0], value[1]) : baseMatches(value) : property(value); } - var baseMatches = __webpack_require__(976), baseMatchesProperty = __webpack_require__(979), identity = __webpack_require__(83), isArray = __webpack_require__(16), property = __webpack_require__(983); + var baseMatches = __webpack_require__(658), baseMatchesProperty = __webpack_require__(661), identity = __webpack_require__(62), isArray = __webpack_require__(12), property = __webpack_require__(665); module.exports = baseIteratee; }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; function Cell() { return null; } - var __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_1__util_ReactUtils__ = (__webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), - __webpack_require__(7)), _extends = Object.assign || function(target) { + var __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_1__util_ReactUtils__ = (__webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), + __webpack_require__(4)), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -4842,29 +4506,29 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }, linearish(scale); } __webpack_exports__.b = linearish, __webpack_exports__.a = linear; - var __WEBPACK_IMPORTED_MODULE_0_d3_array__ = __webpack_require__(53), __WEBPACK_IMPORTED_MODULE_1_d3_interpolate__ = __webpack_require__(114), __WEBPACK_IMPORTED_MODULE_2__continuous__ = __webpack_require__(168), __WEBPACK_IMPORTED_MODULE_3__tickFormat__ = __webpack_require__(1050); + var __WEBPACK_IMPORTED_MODULE_0_d3_array__ = __webpack_require__(38), __WEBPACK_IMPORTED_MODULE_1_d3_interpolate__ = __webpack_require__(87), __WEBPACK_IMPORTED_MODULE_2__continuous__ = __webpack_require__(125), __WEBPACK_IMPORTED_MODULE_3__tickFormat__ = __webpack_require__(732); }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; - var __WEBPACK_IMPORTED_MODULE_0__src_value__ = __webpack_require__(250); + var __WEBPACK_IMPORTED_MODULE_0__src_value__ = __webpack_require__(188); __webpack_require__.d(__webpack_exports__, "a", function() { return __WEBPACK_IMPORTED_MODULE_0__src_value__.a; }); - var __WEBPACK_IMPORTED_MODULE_5__src_number__ = (__webpack_require__(426), __webpack_require__(253), - __webpack_require__(424), __webpack_require__(427), __webpack_require__(167)); + var __WEBPACK_IMPORTED_MODULE_5__src_number__ = (__webpack_require__(309), __webpack_require__(191), + __webpack_require__(307), __webpack_require__(310), __webpack_require__(124)); __webpack_require__.d(__webpack_exports__, "c", function() { return __WEBPACK_IMPORTED_MODULE_5__src_number__.a; }); - var __WEBPACK_IMPORTED_MODULE_7__src_round__ = (__webpack_require__(428), __webpack_require__(1040)); + var __WEBPACK_IMPORTED_MODULE_7__src_round__ = (__webpack_require__(311), __webpack_require__(722)); __webpack_require__.d(__webpack_exports__, "d", function() { return __WEBPACK_IMPORTED_MODULE_7__src_round__.a; }); - var __WEBPACK_IMPORTED_MODULE_15__src_cubehelix__ = (__webpack_require__(429), __webpack_require__(1041), - __webpack_require__(1044), __webpack_require__(423), __webpack_require__(1045), - __webpack_require__(1046), __webpack_require__(1047), __webpack_require__(1048)); + var __WEBPACK_IMPORTED_MODULE_15__src_cubehelix__ = (__webpack_require__(312), __webpack_require__(723), + __webpack_require__(726), __webpack_require__(306), __webpack_require__(727), __webpack_require__(728), + __webpack_require__(729), __webpack_require__(730)); __webpack_require__.d(__webpack_exports__, "b", function() { return __WEBPACK_IMPORTED_MODULE_15__src_cubehelix__.a; }); - __webpack_require__(1049); + __webpack_require__(731); }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; function linear(a, d) { @@ -4891,7 +4555,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { return d ? linear(a, d) : Object(__WEBPACK_IMPORTED_MODULE_0__constant__.a)(isNaN(a) ? b : a); } __webpack_exports__.c = hue, __webpack_exports__.b = gamma, __webpack_exports__.a = nogamma; - var __WEBPACK_IMPORTED_MODULE_0__constant__ = __webpack_require__(425); + var __WEBPACK_IMPORTED_MODULE_0__constant__ = __webpack_require__(308); }, function(module, __webpack_exports__, __webpack_require__) { "use strict"; __webpack_exports__.a = function(s) { @@ -4924,7 +4588,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } }), superClass && (Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass); } - var _class, _temp, __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_0_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = __webpack_require__(2), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2__container_Layer__ = __webpack_require__(18), __WEBPACK_IMPORTED_MODULE_3__util_ReactUtils__ = __webpack_require__(7), _extends = Object.assign || function(target) { + var _class, _temp, __WEBPACK_IMPORTED_MODULE_0_react__ = __webpack_require__(0), __WEBPACK_IMPORTED_MODULE_0_react___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_0_react__), __WEBPACK_IMPORTED_MODULE_1_prop_types__ = __webpack_require__(1), __WEBPACK_IMPORTED_MODULE_1_prop_types___default = __webpack_require__.n(__WEBPACK_IMPORTED_MODULE_1_prop_types__), __WEBPACK_IMPORTED_MODULE_2__container_Layer__ = __webpack_require__(14), __WEBPACK_IMPORTED_MODULE_3__util_ReactUtils__ = __webpack_require__(4), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -5035,7 +4699,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { __webpack_require__.d(__webpack_exports__, "a", function() { return formatAxisMap; }); - var __WEBPACK_IMPORTED_MODULE_0__ChartUtils__ = __webpack_require__(21), _extends = Object.assign || function(target) { + var __WEBPACK_IMPORTED_MODULE_0__ChartUtils__ = __webpack_require__(16), _extends = Object.assign || function(target) { for (var i = 1; i < arguments.length; i++) { var source = arguments[i]; for (var key in source) Object.prototype.hasOwnProperty.call(source, key) && (target[key] = source[key]); @@ -5082,11 +4746,11 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { (function(process) { var emptyObject = {}; "production" !== process.env.NODE_ENV && Object.freeze(emptyObject), module.exports = emptyObject; - }).call(exports, __webpack_require__(3)); + }).call(exports, __webpack_require__(2)); }, function(module, exports, __webpack_require__) { "use strict"; (function(process) { - var emptyFunction = __webpack_require__(55), warning = emptyFunction; + var emptyFunction = __webpack_require__(40), warning = emptyFunction; if ("production" !== process.env.NODE_ENV) { var printWarning = function(format) { for (var _len = arguments.length, args = Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) args[_key - 1] = arguments[_key]; @@ -5107,7 +4771,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }; } module.exports = warning; - }).call(exports, __webpack_require__(3)); + }).call(exports, __webpack_require__(2)); }, function(module, exports, __webpack_require__) { "use strict"; (function(process) { @@ -5121,8 +4785,8 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { } } } - "production" === process.env.NODE_ENV ? (checkDCE(), module.exports = __webpack_require__(456)) : module.exports = __webpack_require__(459); - }).call(exports, __webpack_require__(3)); + "production" === process.env.NODE_ENV ? (checkDCE(), module.exports = __webpack_require__(339)) : module.exports = __webpack_require__(342); + }).call(exports, __webpack_require__(2)); }, function(module, exports, __webpack_require__) { "use strict"; function is(x, y) { @@ -5139,7 +4803,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { var hasOwnProperty = Object.prototype.hasOwnProperty; module.exports = shallowEqual; }, function(module, exports, __webpack_require__) { - var toInteger = __webpack_require__(180), min = Math.min; + var toInteger = __webpack_require__(137), min = Math.min; module.exports = function(it) { return it > 0 ? min(toInteger(it), 9007199254740991) : 0; }; @@ -5158,7 +4822,7 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { }; } exports.__esModule = !0; - var _iterator = __webpack_require__(474), _iterator2 = _interopRequireDefault(_iterator), _symbol = __webpack_require__(482), _symbol2 = _interopRequireDefault(_symbol), _typeof = "function" == typeof _symbol2.default && "symbol" == typeof _iterator2.default ? function(obj) { + var _iterator = __webpack_require__(357), _iterator2 = _interopRequireDefault(_iterator), _symbol = __webpack_require__(365), _symbol2 = _interopRequireDefault(_symbol), _typeof = "function" == typeof _symbol2.default && "symbol" == typeof _iterator2.default ? function(obj) { return typeof obj; } : function(obj) { return obj && "function" == typeof _symbol2.default && obj.constructor === _symbol2.default && obj !== _symbol2.default.prototype ? "symbol" : typeof obj; @@ -5169,9 +4833,9 @@ var _publicBundleJs = []byte((((((((((`!function(modules) { return obj && "function" == typeof _symbol2.default && obj.constructor === _symbol2.default && obj !== _symbol2.default.prototype ? "symbol" : void 0 === obj ? "undefined" : _typeof(obj); }; }, function(module, exports, __webpack_require__) { - var anObject = __webpack_require__(65), dPs = __webpack_require__(478), enumBugKeys = __webpack_require__(183), IE_PROTO = __webpack_require__(181)("IE_PROTO"), Empty = function() {}, createDict = function() { - var iframeDocument, iframe = __webpack_require__(271)("iframe"), i = enumBugKeys.length; - for (iframe.style.display = "none", __webpack_require__(479).appendChild(iframe), + var anObject = __webpack_require__(48), dPs = __webpack_require__(361), enumBugKeys = __webpack_require__(140), IE_PROTO = __webpack_require__(138)("IE_PROTO"), Empty = function() {}, createDict = function() { + var iframeDocument, iframe = __webpack_require__(209)("iframe"), i = enumBugKeys.length; + for (iframe.style.display = "none", __webpack_require__(362).appendChild(iframe), iframe.src = "javascript:", iframeDocument = iframe.contentWindow.document, iframeDocument.open(), iframeDocument.write(" - -
- - - -`) + } + return function(Constructor, protoProps, staticProps) { + return protoProps && defineProperties(Constructor.prototype, protoProps), staticProps && defineProperties(Constructor, staticProps), + Constructor; + }; + }(), _react = __webpack_require__(0), _react2 = _interopRequireDefault(_react), _withStyles = __webpack_require__(10), _withStyles2 = _interopRequireDefault(_withStyles), _AppBar = __webpack_require__(235), _AppBar2 = _interopRequireDefault(_AppBar), _Toolbar = __webpack_require__(236), _Toolbar2 = _interopRequireDefault(_Toolbar), _Typography = __webpack_require__(158), _Typography2 = _interopRequireDefault(_Typography), styles = function(theme) { + return { + footer: { + backgroundColor: theme.palette.background.appBar, + color: theme.palette.getContrastText(theme.palette.background.appBar), + zIndex: theme.zIndex.appBar + }, + toolbar: { + paddingLeft: theme.spacing.unit, + paddingRight: theme.spacing.unit, + display: "flex", + justifyContent: "flex-end" + }, + light: { + color: "rgba(255, 255, 255, 0.54)" + } + }; + }, Footer = function(_Component) { + function Footer() { + var _ref, _temp, _this, _ret; + _classCallCheck(this, Footer); + for (var _len = arguments.length, args = Array(_len), _key = 0; _key < _len; _key++) args[_key] = arguments[_key]; + return _temp = _this = _possibleConstructorReturn(this, (_ref = Footer.__proto__ || Object.getPrototypeOf(Footer)).call.apply(_ref, [ this ].concat(args))), + _this.info = function(about, data) { + return _react2.default.createElement(_Typography2.default, { + type: "caption", + color: "inherit" + }, _react2.default.createElement("span", { + className: _this.props.classes.light + }, about), " ", data); + }, _ret = _temp, _possibleConstructorReturn(_this, _ret); + } + return _inherits(Footer, _Component), _createClass(Footer, [ { + key: "shouldComponentUpdate", + value: function(nextProps) { + return void 0 !== nextProps.shouldUpdate.logs; + } + }, { + key: "render", + value: function() { + var _props = this.props, classes = _props.classes, general = _props.general, geth = general.version ? this.info("Geth", general.version) : null, commit = general.commit ? this.info("Commit", general.commit.substring(0, 7)) : null; + return _react2.default.createElement(_AppBar2.default, { + position: "static", + className: classes.footer + }, _react2.default.createElement(_Toolbar2.default, { + className: classes.toolbar + }, _react2.default.createElement("div", null, geth, commit))); + } + } ]), Footer; + }(_react.Component); + exports.default = (0, _withStyles2.default)(styles)(Footer); +} ]);`))))))))))) -func publicDashboardHtmlBytes() ([]byte, error) { - return _publicDashboardHtml, nil +func bundleJsBytes() ([]byte, error) { + return _bundleJs, nil } -func publicDashboardHtml() (*asset, error) { - bytes, err := publicDashboardHtmlBytes() +func bundleJs() (*asset, error) { + bytes, err := bundleJsBytes() if err != nil { return nil, err } - info := bindataFileInfo{name: "public/dashboard.html", size: 0, mode: os.FileMode(0), modTime: time.Unix(0, 0)} + info := bindataFileInfo{name: "bundle.js", size: 0, mode: os.FileMode(0), modTime: time.Unix(0, 0)} a := &asset{bytes: bytes, info: info} return a, nil } @@ -42207,9 +38271,9 @@ func AssetNames() []string { // _bindata is a table, holding each asset generator, mapped to its name. var _bindata = map[string]func() (*asset, error){ - "public/bundle.js": publicBundleJs, + "dashboard.html": dashboardHtml, - "public/dashboard.html": publicDashboardHtml, + "bundle.js": bundleJs, } // AssetDir returns the file names below a certain @@ -42253,10 +38317,8 @@ type bintree struct { } var _bintree = &bintree{nil, map[string]*bintree{ - "public": {nil, map[string]*bintree{ - "bundle.js": {publicBundleJs, map[string]*bintree{}}, - "dashboard.html": {publicDashboardHtml, map[string]*bintree{}}, - }}, + "bundle.js": {bundleJs, map[string]*bintree{}}, + "dashboard.html": {dashboardHtml, map[string]*bintree{}}, }} // RestoreAsset restores an asset under the given directory diff --git a/dashboard/assets/components/Common.jsx b/dashboard/assets/components/Common.jsx index d8723830e9a3..256a3e66120e 100644 --- a/dashboard/assets/components/Common.jsx +++ b/dashboard/assets/components/Common.jsx @@ -62,32 +62,4 @@ export type MenuProp = {|...ProvidedMenuProp, id: string|}; // This way the mistyping is prevented. export const MENU: Map = new Map(menuSkeletons.map(({id, menu}) => ([id, {id, ...menu}]))); -type ProvidedSampleProp = {|limit: number|}; -const sampleSkeletons: Array<{|id: string, sample: ProvidedSampleProp|}> = [ - { - id: 'memory', - sample: { - limit: 200, - }, - }, { - id: 'traffic', - sample: { - limit: 200, - }, - }, { - id: 'logs', - sample: { - limit: 200, - }, - }, -]; -export type SampleProp = {|...ProvidedSampleProp, id: string|}; -export const SAMPLE: Map = new Map(sampleSkeletons.map(({id, sample}) => ([id, {id, ...sample}]))); - export const DURATION = 200; - -export const LENS: Map = new Map([ - 'content', - ...menuSkeletons.map(({id}) => id), - ...sampleSkeletons.map(({id}) => id), -].map(lens => [lens, lens])); diff --git a/dashboard/assets/components/Dashboard.jsx b/dashboard/assets/components/Dashboard.jsx index b60736d8c037..036dd050b816 100644 --- a/dashboard/assets/components/Dashboard.jsx +++ b/dashboard/assets/components/Dashboard.jsx @@ -19,37 +19,99 @@ import React, {Component} from 'react'; import withStyles from 'material-ui/styles/withStyles'; -import {lensPath, view, set} from 'ramda'; import Header from './Header'; import Body from './Body'; -import {MENU, SAMPLE} from './Common'; -import type {Message, HomeMessage, LogsMessage, Chart} from '../types/message'; +import Footer from './Footer'; +import {MENU} from './Common'; import type {Content} from '../types/content'; -// appender appends an array (A) to the end of another array (B) in the state. -// lens is the path of B in the state, samples is A, and limit is the maximum size of the changed array. +// deepUpdate updates an object corresponding to the given update data, which has +// the shape of the same structure as the original object. updater also has the same +// structure, except that it contains functions where the original data needs to be +// updated. These functions are used to handle the update. // -// appender retrieves a function, which overrides the state's value at lens, and returns with the overridden state. -const appender = (lens, samples, limit) => (state) => { - const newSamples = [ - ...view(lens, state), // retrieves a specific value of the state at the given path (lens). - ...samples, - ]; - // set is a function of ramda.js, which needs the path, the new value, the original state, and retrieves - // the altered state. - return set( - lens, - newSamples.slice(newSamples.length > limit ? newSamples.length - limit : 0), - state - ); +// Since the messages have the same shape as the state content, this approach allows +// the generalization of the message handling. The only necessary thing is to set a +// handler function for every path of the state in order to maximize the flexibility +// of the update. +const deepUpdate = (prev: Object, update: Object, updater: Object) => { + if (typeof update === 'undefined') { + // TODO (kurkomisi): originally this was deep copy, investigate it. + return prev; + } + if (typeof updater === 'function') { + return updater(prev, update); + } + const updated = {}; + Object.keys(prev).forEach((key) => { + updated[key] = deepUpdate(prev[key], update[key], updater[key]); + }); + + return updated; +}; + +// shouldUpdate returns the structure of a message. It is used to prevent unnecessary render +// method triggerings. In the affected component's shouldComponentUpdate method it can be checked +// whether the involved data was changed or not by checking the message structure. +// +// We could return the message itself too, but it's safer not to give access to it. +const shouldUpdate = (msg: Object, updater: Object) => { + const su = {}; + Object.keys(msg).forEach((key) => { + su[key] = typeof updater[key] !== 'function' ? shouldUpdate(msg[key], updater[key]) : true; + }); + + return su; }; -// Lenses for specific data fields in the state, used for a clearer deep update. -// NOTE: This solution will be changed very likely. -const memoryLens = lensPath(['content', 'home', 'memory']); -const trafficLens = lensPath(['content', 'home', 'traffic']); -const logLens = lensPath(['content', 'logs', 'log']); -// styles retrieves the styles for the Dashboard component. + +// appender is a state update generalization function, which appends the update data +// to the existing data. limit defines the maximum allowed size of the created array. +const appender = (limit: number) => (prev: Array, update: Array) => [...prev, ...update].slice(-limit); + +// replacer is a state update generalization function, which replaces the original data. +const replacer = (prev: T, update: T) => update; + +// defaultContent is the initial value of the state content. +const defaultContent: Content = { + general: { + version: null, + commit: null, + }, + home: { + memory: [], + traffic: [], + }, + chain: {}, + txpool: {}, + network: {}, + system: {}, + logs: { + log: [], + }, +}; + +// updaters contains the state update generalization functions for each path of the state. +// TODO (kurkomisi): Define a tricky type which embraces the content and the handlers. +const updaters = { + general: { + version: replacer, + commit: replacer, + }, + home: { + memory: appender(200), + traffic: appender(200), + }, + chain: null, + txpool: null, + network: null, + system: null, + logs: { + log: appender(200), + }, +}; + +// styles returns the styles for the Dashboard component. const styles = theme => ({ dashboard: { display: 'flex', @@ -61,15 +123,18 @@ const styles = theme => ({ overflow: 'hidden', }, }); + export type Props = { classes: Object, }; + type State = { active: string, // active menu sideBar: boolean, // true if the sidebar is opened - content: $Shape, // the visualized data - shouldUpdate: Set // labels for the components, which need to rerender based on the incoming message + content: Content, // the visualized data + shouldUpdate: Object // labels for the components, which need to rerender based on the incoming message }; + // Dashboard is the main component, which renders the whole page, makes connection with the server and // listens for messages. When there is an incoming message, updates the page's content correspondingly. class Dashboard extends Component { @@ -78,8 +143,8 @@ class Dashboard extends Component { this.state = { active: MENU.get('home').id, sideBar: true, - content: {home: {memory: [], traffic: []}, logs: {log: []}}, - shouldUpdate: new Set(), + content: defaultContent, + shouldUpdate: {}, }; } @@ -91,13 +156,14 @@ class Dashboard extends Component { // reconnect establishes a websocket connection with the server, listens for incoming messages // and tries to reconnect on connection loss. reconnect = () => { - this.setState({ - content: {home: {memory: [], traffic: []}, logs: {log: []}}, - }); const server = new WebSocket(`${((window.location.protocol === 'https:') ? 'wss://' : 'ws://') + window.location.host}/api`); + server.onopen = () => { + this.setState({content: defaultContent, shouldUpdate: {}}); + }; server.onmessage = (event) => { - const msg: Message = JSON.parse(event.data); + const msg: $Shape = JSON.parse(event.data); if (!msg) { + console.error(`Incoming message is ${msg}`); return; } this.update(msg); @@ -107,56 +173,12 @@ class Dashboard extends Component { }; }; - // samples retrieves the raw data of a chart field from the incoming message. - samples = (chart: Chart) => { - let s = []; - if (chart.history) { - s = chart.history.map(({value}) => (value || 0)); // traffic comes without value at the beginning - } - if (chart.new) { - s = [...s, chart.new.value || 0]; - } - return s; - }; - - // handleHome changes the home-menu related part of the state. - handleHome = (home: HomeMessage) => { - this.setState((prevState) => { - let newState = prevState; - newState.shouldUpdate = new Set(); - if (home.memory) { - newState = appender(memoryLens, this.samples(home.memory), SAMPLE.get('memory').limit)(newState); - newState.shouldUpdate.add('memory'); - } - if (home.traffic) { - newState = appender(trafficLens, this.samples(home.traffic), SAMPLE.get('traffic').limit)(newState); - newState.shouldUpdate.add('traffic'); - } - return newState; - }); - }; - - // handleLogs changes the logs-menu related part of the state. - handleLogs = (logs: LogsMessage) => { - this.setState((prevState) => { - let newState = prevState; - newState.shouldUpdate = new Set(); - if (logs.log) { - newState = appender(logLens, [logs.log], SAMPLE.get('logs').limit)(newState); - newState.shouldUpdate.add('logs'); - } - return newState; - }); - }; - - // update analyzes the incoming message, and updates the charts' content correspondingly. - update = (msg: Message) => { - if (msg.home) { - this.handleHome(msg.home); - } - if (msg.logs) { - this.handleLogs(msg.logs); - } + // update updates the content corresponding to the incoming message. + update = (msg: $Shape) => { + this.setState(prevState => ({ + content: deepUpdate(prevState.content, msg, updaters), + shouldUpdate: shouldUpdate(msg, updaters), + })); }; // changeContent sets the active label, which is used at the content rendering. @@ -191,6 +213,13 @@ class Dashboard extends Component { content={this.state.content} shouldUpdate={this.state.shouldUpdate} /> +