Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
G
Geth-Modification
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
张蕾
Geth-Modification
Commits
a59bb053
Commit
a59bb053
authored
Mar 20, 2015
by
obscuren
Browse files
Options
Browse Files
Download
Plain Diff
merge
parents
deee9cb1
28e19712
Changes
11
Expand all
Hide whitespace changes
Inline
Side-by-side
Showing
11 changed files
with
635 additions
and
730 deletions
+635
-730
filter.go
core/filter.go
+2
-2
eth_filter.go
event/filter/eth_filter.go
+7
-4
api.go
rpc/api.go
+177
-558
api_test.go
rpc/api_test.go
+32
-32
args.go
rpc/args.go
+18
-8
args_test.go
rpc/args_test.go
+16
-16
http.go
rpc/http.go
+8
-8
messages_test.go
rpc/messages_test.go
+41
-0
responses.go
rpc/responses.go
+26
-0
util.go
rpc/util.go
+0
-86
xeth.go
xeth/xeth.go
+308
-16
No files found.
core/filter.go
View file @
a59bb053
...
...
@@ -34,7 +34,7 @@ type Filter struct {
topics
[][]
common
.
Hash
BlockCallback
func
(
*
types
.
Block
,
state
.
Logs
)
PendingCallback
func
(
*
types
.
Block
,
state
.
Logs
)
PendingCallback
func
(
*
types
.
Transaction
)
LogsCallback
func
(
state
.
Logs
)
}
...
...
@@ -46,7 +46,7 @@ func NewFilter(eth Backend) *Filter {
// SetOptions copies the filter options to the filter it self. The reason for this "silly" copy
// is simply because named arguments in this case is extremely nice and readable.
func
(
self
*
Filter
)
SetOptions
(
options
FilterOptions
)
{
func
(
self
*
Filter
)
SetOptions
(
options
*
FilterOptions
)
{
self
.
earliest
=
options
.
Earliest
self
.
latest
=
options
.
Latest
self
.
skip
=
options
.
Skip
...
...
event/filter/eth_filter.go
View file @
a59bb053
...
...
@@ -48,7 +48,9 @@ func (self *FilterManager) InstallFilter(filter *core.Filter) (id int) {
func
(
self
*
FilterManager
)
UninstallFilter
(
id
int
)
{
self
.
filterMu
.
Lock
()
defer
self
.
filterMu
.
Unlock
()
delete
(
self
.
filters
,
id
)
if
_
,
ok
:=
self
.
filters
[
id
];
ok
{
delete
(
self
.
filters
,
id
)
}
}
// GetFilter retrieves a filter installed using InstallFilter.
...
...
@@ -62,8 +64,9 @@ func (self *FilterManager) GetFilter(id int) *core.Filter {
func
(
self
*
FilterManager
)
filterLoop
()
{
// Subscribe to events
events
:=
self
.
eventMux
.
Subscribe
(
core
.
PendingBlockEvent
{},
//
core.PendingBlockEvent{},
core
.
ChainEvent
{},
core
.
TxPreEvent
{},
state
.
Logs
(
nil
))
out
:
...
...
@@ -82,11 +85,11 @@ out:
}
self
.
filterMu
.
RUnlock
()
case
core
.
PendingBlock
Event
:
case
core
.
TxPre
Event
:
self
.
filterMu
.
RLock
()
for
_
,
filter
:=
range
self
.
filters
{
if
filter
.
PendingCallback
!=
nil
{
filter
.
PendingCallback
(
event
.
Block
,
event
.
Logs
)
filter
.
PendingCallback
(
event
.
Tx
)
}
}
self
.
filterMu
.
RUnlock
()
...
...
rpc/api.go
View file @
a59bb053
This diff is collapsed.
Click to expand it.
rpc/api_test.go
View file @
a59bb053
...
...
@@ -2,9 +2,9 @@ package rpc
import
(
"encoding/json"
"sync"
//
"sync"
"testing"
"time"
//
"time"
)
func
TestWeb3Sha3
(
t
*
testing
.
T
)
{
...
...
@@ -24,33 +24,33 @@ func TestWeb3Sha3(t *testing.T) {
}
}
func
TestFilterClose
(
t
*
testing
.
T
)
{
t
.
Skip
()
api
:=
&
EthereumApi
{
logs
:
make
(
map
[
int
]
*
logFilter
),
messages
:
make
(
map
[
int
]
*
whisperFilter
),
quit
:
make
(
chan
struct
{}),
}
filterTickerTime
=
1
api
.
logs
[
0
]
=
&
logFilter
{}
api
.
messages
[
0
]
=
&
whisperFilter
{}
var
wg
sync
.
WaitGroup
wg
.
Add
(
1
)
go
api
.
start
()
go
func
()
{
select
{
case
<-
time
.
After
(
500
*
time
.
Millisecond
)
:
api
.
stop
()
wg
.
Done
()
}
}()
wg
.
Wait
()
if
len
(
api
.
logs
)
!=
0
{
t
.
Error
(
"expected logs to be empty"
)
}
if
len
(
api
.
messages
)
!=
0
{
t
.
Error
(
"expected messages to be empty"
)
}
}
//
func TestFilterClose(t *testing.T) {
//
t.Skip()
//
api := &EthereumApi{
//
logs: make(map[int]*logFilter),
//
messages: make(map[int]*whisperFilter),
//
quit: make(chan struct{}),
//
}
//
filterTickerTime = 1
//
api.logs[0] = &logFilter{}
//
api.messages[0] = &whisperFilter{}
//
var wg sync.WaitGroup
//
wg.Add(1)
//
go api.start()
//
go func() {
//
select {
//
case <-time.After(500 * time.Millisecond):
//
api.stop()
//
wg.Done()
//
}
//
}()
//
wg.Wait()
//
if len(api.logs) != 0 {
//
t.Error("expected logs to be empty")
//
}
//
if len(api.messages) != 0 {
//
t.Error("expected messages to be empty")
//
}
//
}
rpc/args.go
View file @
a59bb053
...
...
@@ -35,8 +35,8 @@ func blockAge(raw interface{}, number *int64) (err error) {
}
type
GetBlockByHashArgs
struct
{
BlockHash
string
Transaction
s
bool
BlockHash
string
IncludeTx
s
bool
}
func
(
args
*
GetBlockByHashArgs
)
UnmarshalJSON
(
b
[]
byte
)
(
err
error
)
{
...
...
@@ -57,15 +57,15 @@ func (args *GetBlockByHashArgs) UnmarshalJSON(b []byte) (err error) {
args
.
BlockHash
=
argstr
if
len
(
obj
)
>
1
{
args
.
Transaction
s
=
obj
[
1
]
.
(
bool
)
args
.
IncludeTx
s
=
obj
[
1
]
.
(
bool
)
}
return
nil
}
type
GetBlockByNumberArgs
struct
{
BlockNumber
int64
Transactions
bool
BlockNumber
int64
IncludeTxs
bool
}
func
(
args
*
GetBlockByNumberArgs
)
UnmarshalJSON
(
b
[]
byte
)
(
err
error
)
{
...
...
@@ -86,7 +86,7 @@ func (args *GetBlockByNumberArgs) UnmarshalJSON(b []byte) (err error) {
}
if
len
(
obj
)
>
1
{
args
.
Transaction
s
=
obj
[
1
]
.
(
bool
)
args
.
IncludeTx
s
=
obj
[
1
]
.
(
bool
)
}
return
nil
...
...
@@ -433,7 +433,7 @@ func (args *Sha3Args) UnmarshalJSON(b []byte) (err error) {
return
nil
}
type
FilterOption
s
struct
{
type
BlockFilterArg
s
struct
{
Earliest
int64
Latest
int64
Address
interface
{}
...
...
@@ -442,7 +442,7 @@ type FilterOptions struct {
Max
int
}
func
(
args
*
FilterOption
s
)
UnmarshalJSON
(
b
[]
byte
)
(
err
error
)
{
func
(
args
*
BlockFilterArg
s
)
UnmarshalJSON
(
b
[]
byte
)
(
err
error
)
{
var
obj
[]
struct
{
FromBlock
interface
{}
`json:"fromBlock"`
ToBlock
interface
{}
`json:"toBlock"`
...
...
@@ -609,6 +609,16 @@ func (args *FilterStringArgs) UnmarshalJSON(b []byte) (err error) {
return
nil
}
func
(
args
*
FilterStringArgs
)
requirements
()
error
{
switch
args
.
Word
{
case
"latest"
,
"pending"
:
break
default
:
return
NewValidationError
(
"Word"
,
"Must be `latest` or `pending`"
)
}
return
nil
}
type
FilterIdArgs
struct
{
Id
int
}
...
...
rpc/args_test.go
View file @
a59bb053
...
...
@@ -82,7 +82,7 @@ func TestGetBlockByHashArgs(t *testing.T) {
input
:=
`["0xe670ec64341771606e55d6b4ca35a1a6b75ee3d5145a99d05921026d1527331", true]`
expected
:=
new
(
GetBlockByHashArgs
)
expected
.
BlockHash
=
"0xe670ec64341771606e55d6b4ca35a1a6b75ee3d5145a99d05921026d1527331"
expected
.
Transaction
s
=
true
expected
.
IncludeTx
s
=
true
args
:=
new
(
GetBlockByHashArgs
)
if
err
:=
json
.
Unmarshal
([]
byte
(
input
),
&
args
);
err
!=
nil
{
...
...
@@ -93,8 +93,8 @@ func TestGetBlockByHashArgs(t *testing.T) {
t
.
Errorf
(
"BlockHash should be %v but is %v"
,
expected
.
BlockHash
,
args
.
BlockHash
)
}
if
args
.
Transactions
!=
expected
.
Transaction
s
{
t
.
Errorf
(
"
Transactions should be %v but is %v"
,
expected
.
Transactions
,
args
.
Transaction
s
)
if
args
.
IncludeTxs
!=
expected
.
IncludeTx
s
{
t
.
Errorf
(
"
IncludeTxs should be %v but is %v"
,
expected
.
IncludeTxs
,
args
.
IncludeTx
s
)
}
}
...
...
@@ -112,7 +112,7 @@ func TestGetBlockByNumberArgs(t *testing.T) {
input
:=
`["0x1b4", false]`
expected
:=
new
(
GetBlockByNumberArgs
)
expected
.
BlockNumber
=
436
expected
.
Transaction
s
=
false
expected
.
IncludeTx
s
=
false
args
:=
new
(
GetBlockByNumberArgs
)
if
err
:=
json
.
Unmarshal
([]
byte
(
input
),
&
args
);
err
!=
nil
{
...
...
@@ -123,8 +123,8 @@ func TestGetBlockByNumberArgs(t *testing.T) {
t
.
Errorf
(
"BlockHash should be %v but is %v"
,
expected
.
BlockNumber
,
args
.
BlockNumber
)
}
if
args
.
Transactions
!=
expected
.
Transaction
s
{
t
.
Errorf
(
"
Transactions should be %v but is %v"
,
expected
.
Transactions
,
args
.
Transaction
s
)
if
args
.
IncludeTxs
!=
expected
.
IncludeTx
s
{
t
.
Errorf
(
"
IncludeTxs should be %v but is %v"
,
expected
.
IncludeTxs
,
args
.
IncludeTx
s
)
}
}
...
...
@@ -388,7 +388,7 @@ func TestGetDataEmptyArgs(t *testing.T) {
}
}
func
Test
FilterOption
s
(
t
*
testing
.
T
)
{
func
Test
BlockFilterArg
s
(
t
*
testing
.
T
)
{
input
:=
`[{
"fromBlock": "0x1",
"toBlock": "0x2",
...
...
@@ -396,7 +396,7 @@ func TestFilterOptions(t *testing.T) {
"offset": "0x0",
"address": "0xd5677cf67b5aa051bb40496e68ad359eb97cfbf8",
"topics": ["0x12341234"]}]`
expected
:=
new
(
FilterOption
s
)
expected
:=
new
(
BlockFilterArg
s
)
expected
.
Earliest
=
1
expected
.
Latest
=
2
expected
.
Max
=
3
...
...
@@ -404,7 +404,7 @@ func TestFilterOptions(t *testing.T) {
expected
.
Address
=
"0xd5677cf67b5aa051bb40496e68ad359eb97cfbf8"
// expected.Topics = []string{"0x12341234"}
args
:=
new
(
FilterOption
s
)
args
:=
new
(
BlockFilterArg
s
)
if
err
:=
json
.
Unmarshal
([]
byte
(
input
),
&
args
);
err
!=
nil
{
t
.
Error
(
err
)
}
...
...
@@ -434,16 +434,16 @@ func TestFilterOptions(t *testing.T) {
// }
}
func
Test
FilterOption
sWords
(
t
*
testing
.
T
)
{
func
Test
BlockFilterArg
sWords
(
t
*
testing
.
T
)
{
input
:=
`[{
"fromBlock": "latest",
"toBlock": "pending"
}]`
expected
:=
new
(
FilterOption
s
)
expected
:=
new
(
BlockFilterArg
s
)
expected
.
Earliest
=
0
expected
.
Latest
=
-
1
args
:=
new
(
FilterOption
s
)
args
:=
new
(
BlockFilterArg
s
)
if
err
:=
json
.
Unmarshal
([]
byte
(
input
),
&
args
);
err
!=
nil
{
t
.
Error
(
err
)
}
...
...
@@ -457,13 +457,13 @@ func TestFilterOptionsWords(t *testing.T) {
}
}
func
Test
FilterOption
sNums
(
t
*
testing
.
T
)
{
func
Test
BlockFilterArg
sNums
(
t
*
testing
.
T
)
{
input
:=
`[{
"fromBlock": 2,
"toBlock": 3
}]`
args
:=
new
(
FilterOption
s
)
args
:=
new
(
BlockFilterArg
s
)
err
:=
json
.
Unmarshal
([]
byte
(
input
),
&
args
)
switch
err
.
(
type
)
{
case
*
DecodeParamError
:
...
...
@@ -474,10 +474,10 @@ func TestFilterOptionsNums(t *testing.T) {
}
func
Test
FilterOption
sEmptyArgs
(
t
*
testing
.
T
)
{
func
Test
BlockFilterArg
sEmptyArgs
(
t
*
testing
.
T
)
{
input
:=
`[]`
args
:=
new
(
FilterOption
s
)
args
:=
new
(
BlockFilterArg
s
)
err
:=
json
.
Unmarshal
([]
byte
(
input
),
&
args
)
if
err
==
nil
{
t
.
Error
(
"Expected error but didn't get one"
)
...
...
rpc/http.go
View file @
a59bb053
...
...
@@ -10,7 +10,7 @@ import (
"github.com/ethereum/go-ethereum/xeth"
)
var
rpc
httplogger
=
logger
.
NewLogger
(
"RPC-HTTP
"
)
var
rpc
logger
=
logger
.
NewLogger
(
"RPC
"
)
const
(
jsonrpcver
=
"2.0"
...
...
@@ -28,7 +28,7 @@ func JSONRPC(pipe *xeth.XEth, dataDir string) http.Handler {
// Limit request size to resist DoS
if
req
.
ContentLength
>
maxSizeReqLength
{
jsonerr
:=
&
RpcErrorObject
{
-
32700
,
"Request too large"
}
S
end
(
w
,
&
RpcErrorResponse
{
Jsonrpc
:
jsonrpcver
,
Id
:
nil
,
Error
:
jsonerr
})
s
end
(
w
,
&
RpcErrorResponse
{
Jsonrpc
:
jsonrpcver
,
Id
:
nil
,
Error
:
jsonerr
})
return
}
...
...
@@ -37,14 +37,14 @@ func JSONRPC(pipe *xeth.XEth, dataDir string) http.Handler {
body
,
err
:=
ioutil
.
ReadAll
(
req
.
Body
)
if
err
!=
nil
{
jsonerr
:=
&
RpcErrorObject
{
-
32700
,
"Could not read request body"
}
S
end
(
w
,
&
RpcErrorResponse
{
Jsonrpc
:
jsonrpcver
,
Id
:
nil
,
Error
:
jsonerr
})
s
end
(
w
,
&
RpcErrorResponse
{
Jsonrpc
:
jsonrpcver
,
Id
:
nil
,
Error
:
jsonerr
})
}
// Try to parse the request as a single
var
reqSingle
RpcRequest
if
err
:=
json
.
Unmarshal
(
body
,
&
reqSingle
);
err
==
nil
{
response
:=
RpcResponse
(
api
,
&
reqSingle
)
S
end
(
w
,
&
response
)
s
end
(
w
,
&
response
)
return
}
...
...
@@ -57,13 +57,13 @@ func JSONRPC(pipe *xeth.XEth, dataDir string) http.Handler {
response
:=
RpcResponse
(
api
,
&
request
)
resBatch
[
i
]
=
response
}
S
end
(
w
,
resBatch
)
s
end
(
w
,
resBatch
)
return
}
// Not a batch or single request, error
jsonerr
:=
&
RpcErrorObject
{
-
32600
,
"Could not decode request"
}
S
end
(
w
,
&
RpcErrorResponse
{
Jsonrpc
:
jsonrpcver
,
Id
:
nil
,
Error
:
jsonerr
})
s
end
(
w
,
&
RpcErrorResponse
{
Jsonrpc
:
jsonrpcver
,
Id
:
nil
,
Error
:
jsonerr
})
})
}
...
...
@@ -84,11 +84,11 @@ func RpcResponse(api *EthereumApi, request *RpcRequest) *interface{} {
response
=
&
RpcErrorResponse
{
Jsonrpc
:
jsonrpcver
,
Id
:
request
.
Id
,
Error
:
jsonerr
}
}
rpc
http
logger
.
DebugDetailf
(
"Generated response: %T %s"
,
response
,
response
)
rpclogger
.
DebugDetailf
(
"Generated response: %T %s"
,
response
,
response
)
return
&
response
}
func
S
end
(
writer
io
.
Writer
,
v
interface
{})
(
n
int
,
err
error
)
{
func
s
end
(
writer
io
.
Writer
,
v
interface
{})
(
n
int
,
err
error
)
{
var
payload
[]
byte
payload
,
err
=
json
.
MarshalIndent
(
v
,
""
,
"
\t
"
)
if
err
!=
nil
{
...
...
rpc/messages_test.go
0 → 100644
View file @
a59bb053
package
rpc
import
(
"testing"
)
func
TestInsufficientParamsError
(
t
*
testing
.
T
)
{
err
:=
NewInsufficientParamsError
(
0
,
1
)
expected
:=
"insufficient params, want 1 have 0"
if
err
.
Error
()
!=
expected
{
t
.
Error
(
err
.
Error
())
}
}
func
TestNotImplementedError
(
t
*
testing
.
T
)
{
err
:=
NewNotImplementedError
(
"foo"
)
expected
:=
"foo method not implemented"
if
err
.
Error
()
!=
expected
{
t
.
Error
(
err
.
Error
())
}
}
func
TestDecodeParamError
(
t
*
testing
.
T
)
{
err
:=
NewDecodeParamError
(
"foo"
)
expected
:=
"could not decode, foo"
if
err
.
Error
()
!=
expected
{
t
.
Error
(
err
.
Error
())
}
}
func
TestValidationError
(
t
*
testing
.
T
)
{
err
:=
NewValidationError
(
"foo"
,
"should be `bar`"
)
expected
:=
"foo not valid, should be `bar`"
if
err
.
Error
()
!=
expected
{
t
.
Error
(
err
.
Error
())
}
}
rpc/responses.go
View file @
a59bb053
...
...
@@ -7,6 +7,7 @@ import (
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/state"
)
type
BlockRes
struct
{
...
...
@@ -215,3 +216,28 @@ type FilterWhisperRes struct {
Payload
string
`json:"payload"`
WorkProved
string
`json:"workProved"`
}
type
LogRes
struct
{
Address
string
`json:"address"`
Topic
[]
string
`json:"topic"`
Data
string
`json:"data"`
Number
uint64
`json:"number"`
}
func
NewLogsRes
(
logs
state
.
Logs
)
(
ls
[]
LogRes
)
{
ls
=
make
([]
LogRes
,
len
(
logs
))
for
i
,
log
:=
range
logs
{
var
l
LogRes
l
.
Topic
=
make
([]
string
,
len
(
log
.
Topics
()))
l
.
Address
=
log
.
Address
()
.
Hex
()
l
.
Data
=
common
.
ToHex
(
log
.
Data
())
l
.
Number
=
log
.
Number
()
for
j
,
topic
:=
range
log
.
Topics
()
{
l
.
Topic
[
j
]
=
topic
.
Hex
()
}
ls
[
i
]
=
l
}
return
}
rpc/util.go
deleted
100644 → 0
View file @
deee9cb1
/*
This file is part of go-ethereum
go-ethereum is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
go-ethereum is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with go-ethereum. If not, see <http://www.gnu.org/licenses/>.
*/
package
rpc
import
(
"time"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/logger"
"github.com/ethereum/go-ethereum/state"
"github.com/ethereum/go-ethereum/xeth"
)
var
rpclogger
=
logger
.
NewLogger
(
"RPC"
)
type
Log
struct
{
Address
string
`json:"address"`
Topic
[]
string
`json:"topic"`
Data
string
`json:"data"`
Number
uint64
`json:"number"`
}
func
toLogs
(
logs
state
.
Logs
)
(
ls
[]
Log
)
{
ls
=
make
([]
Log
,
len
(
logs
))
for
i
,
log
:=
range
logs
{
var
l
Log
l
.
Topic
=
make
([]
string
,
len
(
log
.
Topics
()))
l
.
Address
=
log
.
Address
()
.
Hex
()
l
.
Data
=
common
.
ToHex
(
log
.
Data
())
l
.
Number
=
log
.
Number
()
for
j
,
topic
:=
range
log
.
Topics
()
{
l
.
Topic
[
j
]
=
topic
.
Hex
()
}
ls
[
i
]
=
l
}
return
}
type
whisperFilter
struct
{
messages
[]
xeth
.
WhisperMessage
timeout
time
.
Time
id
int
}
func
(
w
*
whisperFilter
)
add
(
msgs
...
xeth
.
WhisperMessage
)
{
w
.
messages
=
append
(
w
.
messages
,
msgs
...
)
}
func
(
w
*
whisperFilter
)
get
()
[]
xeth
.
WhisperMessage
{
w
.
timeout
=
time
.
Now
()
tmp
:=
w
.
messages
w
.
messages
=
nil
return
tmp
}
type
logFilter
struct
{
logs
state
.
Logs
timeout
time
.
Time
id
int
}
func
(
l
*
logFilter
)
add
(
logs
...
state
.
Log
)
{
l
.
logs
=
append
(
l
.
logs
,
logs
...
)
}
func
(
l
*
logFilter
)
get
()
state
.
Logs
{
l
.
timeout
=
time
.
Now
()
tmp
:=
l
.
logs
l
.
logs
=
nil
return
tmp
}
xeth/xeth.go
View file @
a59bb053
This diff is collapsed.
Click to expand it.
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment