Skip to content
GitLab
Menu
Projects
Groups
Snippets
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Sign in / Register
Toggle navigation
Menu
Open sidebar
adam.huang
go-libp2p
Commits
d91b419e
Commit
d91b419e
authored
Dec 06, 2015
by
Jeromy
Browse files
WIP
parent
a40ef343
Changes
365
Hide whitespace changes
Inline
Side-by-side
Too many changes to show.
To preserve performance only
365 of 365+
files are displayed.
Plain diff
Email patch
vendor/gx/QmQcFRqZsPJPuQ3V8j5d2cuid8CWHyxNNCFwfhoXSguZCB/go-multiplex/README.md
deleted
100644 → 0
View file @
a40ef343
# go-multiplex
A super simple stream muxing library compatible with
[
multiplex
](
http://github.com/maxogden/multiplex
)
## Usage
```
go
mplex
:=
multiplex
.
NewMultiplex
(
mysocket
)
s
:=
mplex
.
NewStream
()
s
.
Write
([]
byte
(
"Hello World!"
)
s
.
Close
()
mplex
.
Serve
(
func
(
s
*
multiplex
.
Stream
)
{
// echo back everything received
io
.
Copy
(
s
,
s
)
})
```
vendor/gx/QmQcFRqZsPJPuQ3V8j5d2cuid8CWHyxNNCFwfhoXSguZCB/go-multiplex/multiplex.go
deleted
100644 → 0
View file @
a40ef343
package
multiplex
import
(
"bufio"
"encoding/binary"
"errors"
"fmt"
"io"
"io/ioutil"
"sync"
)
const
(
NewStream
=
iota
Receiver
Initiator
Unknown
Close
)
var
_
=
ioutil
.
ReadAll
var
_
=
bufio
.
NewReadWriter
var
_
=
binary
.
MaxVarintLen16
type
msg
struct
{
header
uint64
data
[]
byte
err
chan
<-
error
}
type
Stream
struct
{
id
uint64
name
string
header
uint64
closed
chan
struct
{}
data_in
chan
[]
byte
data_out
chan
<-
msg
extra
[]
byte
}
func
newStream
(
id
uint64
,
name
string
,
initiator
bool
,
send
chan
<-
msg
)
*
Stream
{
var
hfn
uint64
if
initiator
{
hfn
=
2
}
else
{
hfn
=
1
}
return
&
Stream
{
id
:
id
,
name
:
name
,
header
:
(
id
<<
3
)
|
hfn
,
data_in
:
make
(
chan
[]
byte
,
8
),
data_out
:
send
,
closed
:
make
(
chan
struct
{}),
}
}
func
(
s
*
Stream
)
Name
()
string
{
return
s
.
name
}
func
(
s
*
Stream
)
receive
(
b
[]
byte
)
{
select
{
case
s
.
data_in
<-
b
:
case
<-
s
.
closed
:
}
}
func
(
m
*
Multiplex
)
Accept
()
(
*
Stream
,
error
)
{
select
{
case
s
,
ok
:=
<-
m
.
nstreams
:
if
!
ok
{
return
nil
,
errors
.
New
(
"multiplex closed"
)
}
return
s
,
nil
case
err
:=
<-
m
.
errs
:
return
nil
,
err
case
<-
m
.
closed
:
return
nil
,
errors
.
New
(
"multiplex closed"
)
}
}
func
(
s
*
Stream
)
Read
(
b
[]
byte
)
(
int
,
error
)
{
if
s
.
extra
==
nil
{
select
{
case
<-
s
.
closed
:
return
0
,
io
.
EOF
case
read
,
ok
:=
<-
s
.
data_in
:
if
!
ok
{
return
0
,
io
.
EOF
}
s
.
extra
=
read
}
}
n
:=
copy
(
b
,
s
.
extra
)
if
n
<
len
(
s
.
extra
)
{
s
.
extra
=
s
.
extra
[
n
:
]
}
else
{
s
.
extra
=
nil
}
return
n
,
nil
}
func
(
s
*
Stream
)
Write
(
b
[]
byte
)
(
int
,
error
)
{
errs
:=
make
(
chan
error
,
1
)
select
{
case
s
.
data_out
<-
msg
{
header
:
s
.
header
,
data
:
b
,
err
:
errs
}
:
select
{
case
err
:=
<-
errs
:
return
len
(
b
),
err
case
<-
s
.
closed
:
return
0
,
errors
.
New
(
"stream closed"
)
}
case
<-
s
.
closed
:
return
0
,
errors
.
New
(
"stream closed"
)
}
}
func
(
s
*
Stream
)
Close
()
error
{
select
{
case
<-
s
.
closed
:
return
nil
default
:
close
(
s
.
closed
)
select
{
case
s
.
data_out
<-
msg
{
header
:
(
s
.
id
<<
3
)
|
Close
,
err
:
make
(
chan
error
,
1
),
//throw away error, whatever
}
:
default
:
}
close
(
s
.
data_in
)
return
nil
}
}
type
Multiplex
struct
{
con
io
.
ReadWriteCloser
buf
*
bufio
.
Reader
nextID
uint64
outchan
chan
msg
closed
chan
struct
{}
initiator
bool
nstreams
chan
*
Stream
errs
chan
error
channels
map
[
uint64
]
*
Stream
ch_lock
sync
.
Mutex
}
func
NewMultiplex
(
con
io
.
ReadWriteCloser
,
initiator
bool
)
*
Multiplex
{
mp
:=
&
Multiplex
{
con
:
con
,
initiator
:
initiator
,
buf
:
bufio
.
NewReader
(
con
),
channels
:
make
(
map
[
uint64
]
*
Stream
),
outchan
:
make
(
chan
msg
),
closed
:
make
(
chan
struct
{}),
nstreams
:
make
(
chan
*
Stream
,
16
),
errs
:
make
(
chan
error
),
}
go
mp
.
handleOutgoing
()
go
mp
.
handleIncoming
()
return
mp
}
func
(
mp
*
Multiplex
)
Close
()
error
{
if
mp
.
IsClosed
()
{
return
nil
}
close
(
mp
.
closed
)
mp
.
ch_lock
.
Lock
()
defer
mp
.
ch_lock
.
Unlock
()
for
_
,
s
:=
range
mp
.
channels
{
err
:=
s
.
Close
()
if
err
!=
nil
{
return
err
}
}
return
nil
}
func
(
mp
*
Multiplex
)
IsClosed
()
bool
{
select
{
case
<-
mp
.
closed
:
return
true
default
:
return
false
}
}
func
(
mp
*
Multiplex
)
handleOutgoing
()
{
for
{
select
{
case
msg
,
ok
:=
<-
mp
.
outchan
:
if
!
ok
{
return
}
buf
:=
EncodeVarint
(
msg
.
header
)
_
,
err
:=
mp
.
con
.
Write
(
buf
)
if
err
!=
nil
{
msg
.
err
<-
err
continue
}
buf
=
EncodeVarint
(
uint64
(
len
(
msg
.
data
)))
_
,
err
=
mp
.
con
.
Write
(
buf
)
if
err
!=
nil
{
msg
.
err
<-
err
continue
}
_
,
err
=
mp
.
con
.
Write
(
msg
.
data
)
if
err
!=
nil
{
msg
.
err
<-
err
continue
}
msg
.
err
<-
nil
case
<-
mp
.
closed
:
return
}
}
}
func
(
mp
*
Multiplex
)
nextChanID
()
(
out
uint64
)
{
if
mp
.
initiator
{
out
=
mp
.
nextID
+
1
}
else
{
out
=
mp
.
nextID
}
mp
.
nextID
+=
2
return
}
func
(
mp
*
Multiplex
)
NewStream
()
*
Stream
{
return
mp
.
NewNamedStream
(
""
)
}
func
(
mp
*
Multiplex
)
NewNamedStream
(
name
string
)
*
Stream
{
mp
.
ch_lock
.
Lock
()
sid
:=
mp
.
nextChanID
()
header
:=
(
sid
<<
3
)
|
NewStream
if
name
==
""
{
name
=
fmt
.
Sprint
(
sid
)
}
s
:=
newStream
(
sid
,
name
,
true
,
mp
.
outchan
)
mp
.
channels
[
sid
]
=
s
mp
.
ch_lock
.
Unlock
()
mp
.
outchan
<-
msg
{
header
:
header
,
data
:
[]
byte
(
name
),
err
:
make
(
chan
error
,
1
),
//throw away error
}
return
s
}
func
(
mp
*
Multiplex
)
sendErr
(
err
error
)
{
select
{
case
mp
.
errs
<-
err
:
case
<-
mp
.
closed
:
}
}
func
(
mp
*
Multiplex
)
handleIncoming
()
{
defer
mp
.
shutdown
()
for
{
ch
,
tag
,
err
:=
mp
.
readNextHeader
()
if
err
!=
nil
{
mp
.
sendErr
(
err
)
return
}
b
,
err
:=
mp
.
readNext
()
if
err
!=
nil
{
mp
.
sendErr
(
err
)
return
}
mp
.
ch_lock
.
Lock
()
msch
,
ok
:=
mp
.
channels
[
ch
]
if
!
ok
{
var
name
string
if
tag
==
NewStream
{
name
=
string
(
b
)
}
msch
=
newStream
(
ch
,
name
,
false
,
mp
.
outchan
)
mp
.
channels
[
ch
]
=
msch
select
{
case
mp
.
nstreams
<-
msch
:
case
<-
mp
.
closed
:
return
}
if
tag
==
NewStream
{
mp
.
ch_lock
.
Unlock
()
continue
}
}
mp
.
ch_lock
.
Unlock
()
if
tag
==
Close
{
msch
.
Close
()
mp
.
ch_lock
.
Lock
()
delete
(
mp
.
channels
,
ch
)
mp
.
ch_lock
.
Unlock
()
continue
}
msch
.
receive
(
b
)
}
}
func
(
mp
*
Multiplex
)
shutdown
()
{
mp
.
ch_lock
.
Lock
()
defer
mp
.
ch_lock
.
Unlock
()
for
_
,
s
:=
range
mp
.
channels
{
s
.
Close
()
}
}
func
(
mp
*
Multiplex
)
readNextHeader
()
(
uint64
,
uint64
,
error
)
{
h
,
_
,
err
:=
DecodeVarint
(
mp
.
buf
)
if
err
!=
nil
{
return
0
,
0
,
err
}
// get channel ID
ch
:=
h
>>
3
rem
:=
h
&
7
return
ch
,
rem
,
nil
}
func
(
mp
*
Multiplex
)
readNext
()
([]
byte
,
error
)
{
// get length
l
,
_
,
err
:=
DecodeVarint
(
mp
.
buf
)
if
err
!=
nil
{
return
nil
,
err
}
buf
:=
make
([]
byte
,
l
)
n
,
err
:=
io
.
ReadFull
(
mp
.
buf
,
buf
)
if
err
!=
nil
{
return
nil
,
err
}
if
n
!=
int
(
l
)
{
panic
(
"NOT THE SAME"
)
}
return
buf
,
nil
}
func
EncodeVarint
(
x
uint64
)
[]
byte
{
var
buf
[
10
]
byte
var
n
int
for
n
=
0
;
x
>
127
;
n
++
{
buf
[
n
]
=
0x80
|
uint8
(
x
&
0x7F
)
x
>>=
7
}
buf
[
n
]
=
uint8
(
x
)
n
++
return
buf
[
0
:
n
]
}
func
DecodeVarint
(
r
*
bufio
.
Reader
)
(
x
uint64
,
n
int
,
err
error
)
{
// x, n already 0
for
shift
:=
uint
(
0
);
shift
<
64
;
shift
+=
7
{
val
,
err
:=
r
.
ReadByte
()
if
err
!=
nil
{
return
0
,
0
,
err
}
b
:=
uint64
(
val
)
n
++
x
|=
(
b
&
0x7F
)
<<
shift
if
(
b
&
0x80
)
==
0
{
return
x
,
n
,
nil
}
}
// The number is too large to represent in a 64-bit value.
return
0
,
0
,
errors
.
New
(
"Too large of a number!"
)
}
vendor/gx/QmQcFRqZsPJPuQ3V8j5d2cuid8CWHyxNNCFwfhoXSguZCB/go-multiplex/multiplex_test.go
deleted
100644 → 0
View file @
a40ef343
package
multiplex
import
(
"fmt"
"io"
"net"
"testing"
rand
"github.com/dustin/randbo"
)
func
TestBasicStreams
(
t
*
testing
.
T
)
{
a
,
b
:=
net
.
Pipe
()
mpa
:=
NewMultiplex
(
a
,
false
)
mpb
:=
NewMultiplex
(
b
,
true
)
mes
:=
[]
byte
(
"Hello world"
)
go
func
()
{
s
,
err
:=
mpb
.
Accept
()
if
err
!=
nil
{
t
.
Fatal
(
err
)
}
_
,
err
=
s
.
Write
(
mes
)
if
err
!=
nil
{
t
.
Fatal
(
err
)
}
err
=
s
.
Close
()
if
err
!=
nil
{
t
.
Fatal
(
err
)
}
}()
s
:=
mpa
.
NewStream
()
buf
:=
make
([]
byte
,
len
(
mes
))
n
,
err
:=
s
.
Read
(
buf
)
if
err
!=
nil
{
t
.
Fatal
(
err
)
}
if
n
!=
len
(
mes
)
{
t
.
Fatal
(
"read wrong amount"
)
}
if
string
(
buf
)
!=
string
(
mes
)
{
t
.
Fatal
(
"got bad data"
)
}
s
.
Close
()
mpa
.
Close
()
mpb
.
Close
()
}
func
TestEcho
(
t
*
testing
.
T
)
{
a
,
b
:=
net
.
Pipe
()
mpa
:=
NewMultiplex
(
a
,
false
)
mpb
:=
NewMultiplex
(
b
,
true
)
mes
:=
make
([]
byte
,
40960
)
rand
.
New
()
.
Read
(
mes
)
go
func
()
{
s
,
err
:=
mpb
.
Accept
()
if
err
!=
nil
{
t
.
Fatal
(
err
)
}
defer
s
.
Close
()
io
.
Copy
(
s
,
s
)
}()
s
:=
mpa
.
NewStream
()
_
,
err
:=
s
.
Write
(
mes
)
if
err
!=
nil
{
t
.
Fatal
(
err
)
}
buf
:=
make
([]
byte
,
len
(
mes
))
n
,
err
:=
io
.
ReadFull
(
s
,
buf
)
if
err
!=
nil
{
t
.
Fatal
(
err
)
}
if
n
!=
len
(
mes
)
{
t
.
Fatal
(
"read wrong amount"
)
}
if
err
:=
arrComp
(
buf
,
mes
);
err
!=
nil
{
t
.
Fatal
(
err
)
}
s
.
Close
()
mpa
.
Close
()
mpb
.
Close
()
}
func
arrComp
(
a
,
b
[]
byte
)
error
{
msg
:=
""
if
len
(
a
)
!=
len
(
b
)
{
msg
+=
fmt
.
Sprintf
(
"arrays differ in length: %d %d
\n
"
,
len
(
a
),
len
(
b
))
}
for
i
:=
0
;
i
<
len
(
a
)
&&
i
<
len
(
b
);
i
++
{
if
a
[
i
]
!=
b
[
i
]
{
msg
+=
fmt
.
Sprintf
(
"content differs at index %d [%d != %d]"
,
i
,
a
[
i
],
b
[
i
])
return
fmt
.
Errorf
(
msg
)
}
}
if
len
(
msg
)
>
0
{
return
fmt
.
Errorf
(
msg
)
}
return
nil
}
vendor/gx/QmQcFRqZsPJPuQ3V8j5d2cuid8CWHyxNNCFwfhoXSguZCB/go-multiplex/package.json
deleted
100644 → 0
View file @
a40ef343
{
"name"
:
"go-multiplex"
,
"author"
:
"whyrusleeping"
,
"version"
:
"0.0.0"
,
"language"
:
"go"
,
"issues_url"
:
""
,
"gx"
:
{
"dvcsimport"
:
"github.com/whyrusleeping/go-multiplex"
}
}
\ No newline at end of file
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/.gxignore
deleted
100644 → 0
View file @
a40ef343
Godeps/*
\ No newline at end of file
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/.travis.yml
deleted
100644 → 0
View file @
a40ef343
language
:
go
go
:
-
1.0
-
1.1
-
tip
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/CONTRIBUTORS
deleted
100644 → 0
View file @
a40ef343
Alec Thomas <alec@swapoff.org>
Guilhem Lettron <guilhem.lettron@optiflows.com>
Ivan Daniluk <ivan.daniluk@gmail.com>
Nimi Wariboko Jr <nimi@channelmeter.com>
Róbert Selvek <robert.selvek@gmail.com>
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/LICENSE
deleted
100644 → 0
View file @
a40ef343
Copyright (c) 2013 Örjan Persson. All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/README.md
deleted
100644 → 0
View file @
a40ef343
## Golang logging library
[

](https://godoc.org/github.com/op/go-logging)
[

](https://travis-ci.org/op/go-logging)
Package logging implements a logging infrastructure for Go. Its output format
is customizable and supports different logging backends like syslog, file and
memory. Multiple backends can be utilized with different log levels per backend
and logger.
## Example
Let's have a look at an
[
example
](
examples/example.go
)
which demonstrates most
of the features found in this library.
[

](examples/example.go)
```
go
package
main
import
(
"os"
"github.com/op/go-logging"
)
var
log
=
logging
.
MustGetLogger
(
"example"
)
// Example format string. Everything except the message has a custom color
// which is dependent on the log level. Many fields have a custom output
// formatting too, eg. the time returns the hour down to the milli second.
var
format
=
logging
.
MustStringFormatter
(
"%{color}%{time:15:04:05.000} %{shortfunc} ▶ %{level:.4s} %{id:03x}%{color:reset} %{message}"
,
)
// Password is just an example type implementing the Redactor interface. Any
// time this is logged, the Redacted() function will be called.
type
Password
string
func
(
p
Password
)
Redacted
()
interface
{}
{
return
logging
.
Redact
(
string
(
p
))
}
func
main
()
{
// For demo purposes, create two backend for os.Stderr.
backend1
:=
logging
.
NewLogBackend
(
os
.
Stderr
,
""
,
0
)
backend2
:=
logging
.
NewLogBackend
(
os
.
Stderr
,
""
,
0
)
// For messages written to backend2 we want to add some additional
// information to the output, including the used log level and the name of
// the function.
backend2Formatter
:=
logging
.
NewBackendFormatter
(
backend2
,
format
)
// Only errors and more severe messages should be sent to backend1
backend1Leveled
:=
logging
.
AddModuleLevel
(
backend1
)
backend1Leveled
.
SetLevel
(
logging
.
ERROR
,
""
)
// Set the backends to be used.
logging
.
SetBackend
(
backend1Leveled
,
backend2Formatter
)
log
.
Debug
(
"debug %s"
,
Password
(
"secret"
))
log
.
Info
(
"info"
)
log
.
Notice
(
"notice"
)
log
.
Warning
(
"warning"
)
log
.
Error
(
"err"
)
log
.
Critical
(
"crit"
)
}
```
## Installing
### Using *go get*
$ go get github.com/op/go-logging
After this command
*go-logging*
is ready to use. Its source will be in:
$GOROOT/src/pkg/github.com/op/go-logging
You can use
`go get -u`
to update the package.
## Documentation
For docs, see http://godoc.org/github.com/op/go-logging or run:
$ godoc github.com/op/go-logging
## Additional resources
*
[
wslog
](
https://godoc.org/github.com/cryptix/go/logging/wslog
)
-- exposes log messages through a WebSocket.
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/backend.go
deleted
100644 → 0
View file @
a40ef343
// Copyright 2013, Örjan Persson. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package
logging
// defaultBackend is the backend used for all logging calls.
var
defaultBackend
LeveledBackend
// Backend is the interface which a log backend need to implement to be able to
// be used as a logging backend.
type
Backend
interface
{
Log
(
Level
,
int
,
*
Record
)
error
}
// Set backend replaces the backend currently set with the given new logging
// backend.
func
SetBackend
(
backends
...
Backend
)
LeveledBackend
{
var
backend
Backend
if
len
(
backends
)
==
1
{
backend
=
backends
[
0
]
}
else
{
backend
=
MultiLogger
(
backends
...
)
}
defaultBackend
=
AddModuleLevel
(
backend
)
return
defaultBackend
}
// SetLevel sets the logging level for the specified module. The module
// corresponds to the string specified in GetLogger.
func
SetLevel
(
level
Level
,
module
string
)
{
defaultBackend
.
SetLevel
(
level
,
module
)
}
// GetLevel returns the logging level for the specified module.
func
GetLevel
(
module
string
)
Level
{
return
defaultBackend
.
GetLevel
(
module
)
}
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/example_test.go
deleted
100644 → 0
View file @
a40ef343
package
logging
import
"os"
func
Example
()
{
// This call is for testing purposes and will set the time to unix epoch.
InitForTesting
(
DEBUG
)
var
log
=
MustGetLogger
(
"example"
)
// For demo purposes, create two backend for os.Stdout.
//
// os.Stderr should most likely be used in the real world but then the
// "Output:" check in this example would not work.
backend1
:=
NewLogBackend
(
os
.
Stdout
,
""
,
0
)
backend2
:=
NewLogBackend
(
os
.
Stdout
,
""
,
0
)
// For messages written to backend2 we want to add some additional
// information to the output, including the used log level and the name of
// the function.
var
format
=
MustStringFormatter
(
"%{time:15:04:05.000} %{shortfunc} %{level:.1s} %{message}"
,
)
backend2Formatter
:=
NewBackendFormatter
(
backend2
,
format
)
// Only errors and more severe messages should be sent to backend2
backend2Leveled
:=
AddModuleLevel
(
backend2Formatter
)
backend2Leveled
.
SetLevel
(
ERROR
,
""
)
// Set the backends to be used and the default level.
SetBackend
(
backend1
,
backend2Leveled
)
log
.
Debug
(
"debug %s"
,
"arg"
)
log
.
Error
(
"error"
)
// Output:
// debug arg
// error
// 00:00:00.000 Example E error
}
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/examples/example.go
deleted
100644 → 0
View file @
a40ef343
package
main
import
(
"os"
"gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging"
)
var
log
=
logging
.
MustGetLogger
(
"example"
)
// Example format string. Everything except the message has a custom color
// which is dependent on the log level. Many fields have a custom output
// formatting too, eg. the time returns the hour down to the milli second.
var
format
=
logging
.
MustStringFormatter
(
"%{color}%{time:15:04:05.000} %{shortfunc} ▶ %{level:.4s} %{id:03x}%{color:reset} %{message}"
,
)
// Password is just an example type implementing the Redactor interface. Any
// time this is logged, the Redacted() function will be called.
type
Password
string
func
(
p
Password
)
Redacted
()
interface
{}
{
return
logging
.
Redact
(
string
(
p
))
}
func
main
()
{
// For demo purposes, create two backend for os.Stderr.
backend1
:=
logging
.
NewLogBackend
(
os
.
Stderr
,
""
,
0
)
backend2
:=
logging
.
NewLogBackend
(
os
.
Stderr
,
""
,
0
)
// For messages written to backend2 we want to add some additional
// information to the output, including the used log level and the name of
// the function.
backend2Formatter
:=
logging
.
NewBackendFormatter
(
backend2
,
format
)
// Only errors and more severe messages should be sent to backend1
backend1Leveled
:=
logging
.
AddModuleLevel
(
backend1
)
backend1Leveled
.
SetLevel
(
logging
.
ERROR
,
""
)
// Set the backends to be used.
logging
.
SetBackend
(
backend1Leveled
,
backend2Formatter
)
log
.
Debug
(
"debug %s"
,
Password
(
"secret"
))
log
.
Info
(
"info"
)
log
.
Notice
(
"notice"
)
log
.
Warning
(
"warning"
)
log
.
Error
(
"err"
)
log
.
Critical
(
"crit"
)
}
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/examples/example.png
deleted
100644 → 0
View file @
a40ef343
17.3 KB
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/format.go
deleted
100644 → 0
View file @
a40ef343
// Copyright 2013, Örjan Persson. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package
logging
import
(
"bytes"
"errors"
"fmt"
"io"
"os"
"path"
"path/filepath"
"regexp"
"runtime"
"strings"
"sync"
"time"
)
// TODO see Formatter interface in fmt/print.go
// TODO try text/template, maybe it have enough performance
// TODO other template systems?
// TODO make it possible to specify formats per backend?
type
fmtVerb
int
const
(
fmtVerbTime
fmtVerb
=
iota
fmtVerbLevel
fmtVerbId
fmtVerbPid
fmtVerbProgram
fmtVerbModule
fmtVerbMessage
fmtVerbLongfile
fmtVerbShortfile
fmtVerbLongpkg
fmtVerbShortpkg
fmtVerbLongfunc
fmtVerbShortfunc
fmtVerbLevelColor
// Keep last, there are no match for these below.
fmtVerbUnknown
fmtVerbStatic
)
var
fmtVerbs
=
[]
string
{
"time"
,
"level"
,
"id"
,
"pid"
,
"program"
,
"module"
,
"message"
,
"longfile"
,
"shortfile"
,
"longpkg"
,
"shortpkg"
,
"longfunc"
,
"shortfunc"
,
"color"
,
}
const
rfc3339Milli
=
"2006-01-02T15:04:05.999Z07:00"
var
defaultVerbsLayout
=
[]
string
{
rfc3339Milli
,
"s"
,
"d"
,
"d"
,
"s"
,
"s"
,
"s"
,
"s"
,
"s"
,
"s"
,
"s"
,
"s"
,
"s"
,
""
,
}
var
(
pid
=
os
.
Getpid
()
program
=
filepath
.
Base
(
os
.
Args
[
0
])
)
func
getFmtVerbByName
(
name
string
)
fmtVerb
{
for
i
,
verb
:=
range
fmtVerbs
{
if
name
==
verb
{
return
fmtVerb
(
i
)
}
}
return
fmtVerbUnknown
}
// Formatter is the required interface for a custom log record formatter.
type
Formatter
interface
{
Format
(
calldepth
int
,
r
*
Record
,
w
io
.
Writer
)
error
}
// formatter is used by all backends unless otherwise overriden.
var
formatter
struct
{
sync
.
RWMutex
def
Formatter
}
func
getFormatter
()
Formatter
{
formatter
.
RLock
()
defer
formatter
.
RUnlock
()
return
formatter
.
def
}
var
(
// DefaultFormatter is the default formatter used and is only the message.
DefaultFormatter
Formatter
=
MustStringFormatter
(
"%{message}"
)
// Glog format
GlogFormatter
Formatter
=
MustStringFormatter
(
"%{level:.1s}%{time:0102 15:04:05.999999} %{pid} %{shortfile}] %{message}"
)
)
// SetFormatter sets the default formatter for all new backends. A backend will
// fetch this value once it is needed to format a record. Note that backends
// will cache the formatter after the first point. For now, make sure to set
// the formatter before logging.
func
SetFormatter
(
f
Formatter
)
{
formatter
.
Lock
()
defer
formatter
.
Unlock
()
formatter
.
def
=
f
}
var
formatRe
*
regexp
.
Regexp
=
regexp
.
MustCompile
(
`%{([a-z]+)(?::(.*?[^\\]))?}`
)
type
part
struct
{
verb
fmtVerb
layout
string
}
// stringFormatter contains a list of parts which explains how to build the
// formatted string passed on to the logging backend.
type
stringFormatter
struct
{
parts
[]
part
}
// NewStringFormatter returns a new Formatter which outputs the log record as a
// string based on the 'verbs' specified in the format string.
//
// The verbs:
//
// General:
// %{id} Sequence number for log message (uint64).
// %{pid} Process id (int)
// %{time} Time when log occurred (time.Time)
// %{level} Log level (Level)
// %{module} Module (string)
// %{program} Basename of os.Args[0] (string)
// %{message} Message (string)
// %{longfile} Full file name and line number: /a/b/c/d.go:23
// %{shortfile} Final file name element and line number: d.go:23
// %{color} ANSI color based on log level
//
// For normal types, the output can be customized by using the 'verbs' defined
// in the fmt package, eg. '%{id:04d}' to make the id output be '%04d' as the
// format string.
//
// For time.Time, use the same layout as time.Format to change the time format
// when output, eg "2006-01-02T15:04:05.999Z-07:00".
//
// For the 'color' verb, the output can be adjusted to either use bold colors,
// i.e., '%{color:bold}' or to reset the ANSI attributes, i.e.,
// '%{color:reset}' Note that if you use the color verb explicitly, be sure to
// reset it or else the color state will persist past your log message. e.g.,
// "%{color:bold}%{time:15:04:05} %{level:-8s}%{color:reset} %{message}" will
// just colorize the time and level, leaving the message uncolored.
//
// There's also a couple of experimental 'verbs'. These are exposed to get
// feedback and needs a bit of tinkering. Hence, they might change in the
// future.
//
// Experimental:
// %{longpkg} Full package path, eg. github.com/go-logging
// %{shortpkg} Base package path, eg. go-logging
// %{longfunc} Full function name, eg. littleEndian.PutUint32
// %{shortfunc} Base function name, eg. PutUint32
func
NewStringFormatter
(
format
string
)
(
*
stringFormatter
,
error
)
{
var
fmter
=
&
stringFormatter
{}
// Find the boundaries of all %{vars}
matches
:=
formatRe
.
FindAllStringSubmatchIndex
(
format
,
-
1
)
if
matches
==
nil
{
return
nil
,
errors
.
New
(
"logger: invalid log format: "
+
format
)
}
// Collect all variables and static text for the format
prev
:=
0
for
_
,
m
:=
range
matches
{
start
,
end
:=
m
[
0
],
m
[
1
]
if
start
>
prev
{
fmter
.
add
(
fmtVerbStatic
,
format
[
prev
:
start
])
}
name
:=
format
[
m
[
2
]
:
m
[
3
]]
verb
:=
getFmtVerbByName
(
name
)
if
verb
==
fmtVerbUnknown
{
return
nil
,
errors
.
New
(
"logger: unknown variable: "
+
name
)
}
// Handle layout customizations or use the default. If this is not for the
// time or color formatting, we need to prefix with %.
layout
:=
defaultVerbsLayout
[
verb
]
if
m
[
4
]
!=
-
1
{
layout
=
format
[
m
[
4
]
:
m
[
5
]]
}
if
verb
!=
fmtVerbTime
&&
verb
!=
fmtVerbLevelColor
{
layout
=
"%"
+
layout
}
fmter
.
add
(
verb
,
layout
)
prev
=
end
}
end
:=
format
[
prev
:
]
if
end
!=
""
{
fmter
.
add
(
fmtVerbStatic
,
end
)
}
// Make a test run to make sure we can format it correctly.
t
,
err
:=
time
.
Parse
(
time
.
RFC3339
,
"2010-02-04T21:00:57-08:00"
)
if
err
!=
nil
{
panic
(
err
)
}
r
:=
&
Record
{
Id
:
12345
,
Time
:
t
,
Module
:
"logger"
,
fmt
:
"hello %s"
,
args
:
[]
interface
{}{
"go"
},
}
if
err
:=
fmter
.
Format
(
0
,
r
,
&
bytes
.
Buffer
{});
err
!=
nil
{
return
nil
,
err
}
return
fmter
,
nil
}
// MustStringFormatter is equivalent to NewStringFormatter with a call to panic
// on error.
func
MustStringFormatter
(
format
string
)
*
stringFormatter
{
f
,
err
:=
NewStringFormatter
(
format
)
if
err
!=
nil
{
panic
(
"Failed to initialized string formatter: "
+
err
.
Error
())
}
return
f
}
func
(
f
*
stringFormatter
)
add
(
verb
fmtVerb
,
layout
string
)
{
f
.
parts
=
append
(
f
.
parts
,
part
{
verb
,
layout
})
}
func
(
f
*
stringFormatter
)
Format
(
calldepth
int
,
r
*
Record
,
output
io
.
Writer
)
error
{
for
_
,
part
:=
range
f
.
parts
{
if
part
.
verb
==
fmtVerbStatic
{
output
.
Write
([]
byte
(
part
.
layout
))
}
else
if
part
.
verb
==
fmtVerbTime
{
output
.
Write
([]
byte
(
r
.
Time
.
Format
(
part
.
layout
)))
}
else
if
part
.
verb
==
fmtVerbLevelColor
{
if
part
.
layout
==
"bold"
{
output
.
Write
([]
byte
(
boldcolors
[
r
.
Level
]))
}
else
if
part
.
layout
==
"reset"
{
output
.
Write
([]
byte
(
"
\0
33[0m"
))
}
else
{
output
.
Write
([]
byte
(
colors
[
r
.
Level
]))
}
}
else
{
var
v
interface
{}
switch
part
.
verb
{
case
fmtVerbLevel
:
v
=
r
.
Level
break
case
fmtVerbId
:
v
=
r
.
Id
break
case
fmtVerbPid
:
v
=
pid
break
case
fmtVerbProgram
:
v
=
program
break
case
fmtVerbModule
:
v
=
r
.
Module
break
case
fmtVerbMessage
:
v
=
r
.
Message
()
break
case
fmtVerbLongfile
,
fmtVerbShortfile
:
_
,
file
,
line
,
ok
:=
runtime
.
Caller
(
calldepth
+
1
)
if
!
ok
{
file
=
"???"
line
=
0
}
else
if
part
.
verb
==
fmtVerbShortfile
{
file
=
filepath
.
Base
(
file
)
}
v
=
fmt
.
Sprintf
(
"%s:%d"
,
file
,
line
)
case
fmtVerbLongfunc
,
fmtVerbShortfunc
,
fmtVerbLongpkg
,
fmtVerbShortpkg
:
// TODO cache pc
v
=
"???"
if
pc
,
_
,
_
,
ok
:=
runtime
.
Caller
(
calldepth
+
1
);
ok
{
if
f
:=
runtime
.
FuncForPC
(
pc
);
f
!=
nil
{
v
=
formatFuncName
(
part
.
verb
,
f
.
Name
())
}
}
default
:
panic
(
"unhandled format part"
)
}
fmt
.
Fprintf
(
output
,
part
.
layout
,
v
)
}
}
return
nil
}
// formatFuncName tries to extract certain part of the runtime formatted
// function name to some pre-defined variation.
//
// This function is known to not work properly if the package path or name
// contains a dot.
func
formatFuncName
(
v
fmtVerb
,
f
string
)
string
{
i
:=
strings
.
LastIndex
(
f
,
"/"
)
j
:=
strings
.
Index
(
f
[
i
+
1
:
],
"."
)
if
j
<
1
{
return
"???"
}
pkg
,
fun
:=
f
[
:
i
+
j
+
1
],
f
[
i
+
j
+
2
:
]
switch
v
{
case
fmtVerbLongpkg
:
return
pkg
case
fmtVerbShortpkg
:
return
path
.
Base
(
pkg
)
case
fmtVerbLongfunc
:
return
fun
case
fmtVerbShortfunc
:
i
=
strings
.
LastIndex
(
fun
,
"."
)
return
fun
[
i
+
1
:
]
}
panic
(
"unexpected func formatter"
)
}
// backendFormatter combines a backend with a specific formatter making it
// possible to have different log formats for different backends.
type
backendFormatter
struct
{
b
Backend
f
Formatter
}
// NewBackendFormatter creates a new backend which makes all records that
// passes through it beeing formatted by the specific formatter.
func
NewBackendFormatter
(
b
Backend
,
f
Formatter
)
*
backendFormatter
{
return
&
backendFormatter
{
b
,
f
}
}
// Log implements the Log function required by the Backend interface.
func
(
bf
*
backendFormatter
)
Log
(
level
Level
,
calldepth
int
,
r
*
Record
)
error
{
// Make a shallow copy of the record and replace any formatter
r2
:=
*
r
r2
.
formatter
=
bf
.
f
return
bf
.
b
.
Log
(
level
,
calldepth
+
1
,
&
r2
)
}
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/format_test.go
deleted
100644 → 0
View file @
a40ef343
// Copyright 2013, Örjan Persson. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package
logging
import
(
"bytes"
"testing"
)
func
TestFormat
(
t
*
testing
.
T
)
{
backend
:=
InitForTesting
(
DEBUG
)
f
,
err
:=
NewStringFormatter
(
"%{shortfile} %{time:2006-01-02T15:04:05} %{level:.1s} %{id:04d} %{module} %{message}"
)
if
err
!=
nil
{
t
.
Fatalf
(
"failed to set format: %s"
,
err
)
}
SetFormatter
(
f
)
log
:=
MustGetLogger
(
"module"
)
log
.
Debug
(
"hello"
)
line
:=
MemoryRecordN
(
backend
,
0
)
.
Formatted
(
0
)
if
"format_test.go:24 1970-01-01T00:00:00 D 0001 module hello"
!=
line
{
t
.
Errorf
(
"Unexpected format: %s"
,
line
)
}
}
func
logAndGetLine
(
backend
*
MemoryBackend
)
string
{
MustGetLogger
(
"foo"
)
.
Debug
(
"hello"
)
return
MemoryRecordN
(
backend
,
0
)
.
Formatted
(
1
)
}
func
getLastLine
(
backend
*
MemoryBackend
)
string
{
return
MemoryRecordN
(
backend
,
0
)
.
Formatted
(
1
)
}
func
realFunc
(
backend
*
MemoryBackend
)
string
{
return
logAndGetLine
(
backend
)
}
type
structFunc
struct
{}
func
(
structFunc
)
Log
(
backend
*
MemoryBackend
)
string
{
return
logAndGetLine
(
backend
)
}
func
TestRealFuncFormat
(
t
*
testing
.
T
)
{
backend
:=
InitForTesting
(
DEBUG
)
SetFormatter
(
MustStringFormatter
(
"%{shortfunc}"
))
line
:=
realFunc
(
backend
)
if
"realFunc"
!=
line
{
t
.
Errorf
(
"Unexpected format: %s"
,
line
)
}
}
func
TestStructFuncFormat
(
t
*
testing
.
T
)
{
backend
:=
InitForTesting
(
DEBUG
)
SetFormatter
(
MustStringFormatter
(
"%{longfunc}"
))
var
x
structFunc
line
:=
x
.
Log
(
backend
)
if
"structFunc.Log"
!=
line
{
t
.
Errorf
(
"Unexpected format: %s"
,
line
)
}
}
func
TestVarFuncFormat
(
t
*
testing
.
T
)
{
backend
:=
InitForTesting
(
DEBUG
)
SetFormatter
(
MustStringFormatter
(
"%{shortfunc}"
))
var
varFunc
=
func
()
string
{
return
logAndGetLine
(
backend
)
}
line
:=
varFunc
()
if
"???"
==
line
||
"TestVarFuncFormat"
==
line
||
"varFunc"
==
line
{
t
.
Errorf
(
"Unexpected format: %s"
,
line
)
}
}
func
TestFormatFuncName
(
t
*
testing
.
T
)
{
var
tests
=
[]
struct
{
filename
string
longpkg
string
shortpkg
string
longfunc
string
shortfunc
string
}{
{
""
,
"???"
,
"???"
,
"???"
,
"???"
},
{
"main"
,
"???"
,
"???"
,
"???"
,
"???"
},
{
"main."
,
"main"
,
"main"
,
""
,
""
},
{
"main.main"
,
"main"
,
"main"
,
"main"
,
"main"
},
{
"github.com/op/go-logging.func·001"
,
"github.com/op/go-logging"
,
"go-logging"
,
"func·001"
,
"func·001"
},
{
"github.com/op/go-logging.stringFormatter.Format"
,
"github.com/op/go-logging"
,
"go-logging"
,
"stringFormatter.Format"
,
"Format"
},
}
var
v
string
for
_
,
test
:=
range
tests
{
v
=
formatFuncName
(
fmtVerbLongpkg
,
test
.
filename
)
if
test
.
longpkg
!=
v
{
t
.
Errorf
(
"%s != %s"
,
test
.
longpkg
,
v
)
}
v
=
formatFuncName
(
fmtVerbShortpkg
,
test
.
filename
)
if
test
.
shortpkg
!=
v
{
t
.
Errorf
(
"%s != %s"
,
test
.
shortpkg
,
v
)
}
v
=
formatFuncName
(
fmtVerbLongfunc
,
test
.
filename
)
if
test
.
longfunc
!=
v
{
t
.
Errorf
(
"%s != %s"
,
test
.
longfunc
,
v
)
}
v
=
formatFuncName
(
fmtVerbShortfunc
,
test
.
filename
)
if
test
.
shortfunc
!=
v
{
t
.
Errorf
(
"%s != %s"
,
test
.
shortfunc
,
v
)
}
}
}
func
TestBackendFormatter
(
t
*
testing
.
T
)
{
InitForTesting
(
DEBUG
)
// Create two backends and wrap one of the with a backend formatter
b1
:=
NewMemoryBackend
(
1
)
b2
:=
NewMemoryBackend
(
1
)
f
:=
MustStringFormatter
(
"%{level} %{message}"
)
bf
:=
NewBackendFormatter
(
b2
,
f
)
SetBackend
(
b1
,
bf
)
log
:=
MustGetLogger
(
"module"
)
log
.
Info
(
"foo"
)
if
"foo"
!=
getLastLine
(
b1
)
{
t
.
Errorf
(
"Unexpected line: %s"
,
getLastLine
(
b1
))
}
if
"INFO foo"
!=
getLastLine
(
b2
)
{
t
.
Errorf
(
"Unexpected line: %s"
,
getLastLine
(
b2
))
}
}
func
BenchmarkStringFormatter
(
b
*
testing
.
B
)
{
fmt
:=
"%{time:2006-01-02T15:04:05} %{level:.1s} %{id:04d} %{module} %{message}"
f
:=
MustStringFormatter
(
fmt
)
backend
:=
InitForTesting
(
DEBUG
)
buf
:=
&
bytes
.
Buffer
{}
log
:=
MustGetLogger
(
"module"
)
log
.
Debug
(
""
)
record
:=
MemoryRecordN
(
backend
,
0
)
b
.
ResetTimer
()
for
i
:=
0
;
i
<
b
.
N
;
i
++
{
if
err
:=
f
.
Format
(
1
,
record
,
buf
);
err
!=
nil
{
b
.
Fatal
(
err
)
buf
.
Truncate
(
0
)
}
}
}
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/level.go
deleted
100644 → 0
View file @
a40ef343
// Copyright 2013, Örjan Persson. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package
logging
import
(
"errors"
"strings"
"sync"
)
var
ErrInvalidLogLevel
=
errors
.
New
(
"logger: invalid log level"
)
// Level defines all available log levels for log messages.
type
Level
int
const
(
CRITICAL
Level
=
iota
ERROR
WARNING
NOTICE
INFO
DEBUG
)
var
levelNames
=
[]
string
{
"CRITICAL"
,
"ERROR"
,
"WARNING"
,
"NOTICE"
,
"INFO"
,
"DEBUG"
,
}
// String returns the string representation of a logging level.
func
(
p
Level
)
String
()
string
{
return
levelNames
[
p
]
}
// LogLevel returns the log level from a string representation.
func
LogLevel
(
level
string
)
(
Level
,
error
)
{
for
i
,
name
:=
range
levelNames
{
if
strings
.
EqualFold
(
name
,
level
)
{
return
Level
(
i
),
nil
}
}
return
ERROR
,
ErrInvalidLogLevel
}
type
Leveled
interface
{
GetLevel
(
string
)
Level
SetLevel
(
Level
,
string
)
IsEnabledFor
(
Level
,
string
)
bool
}
// LeveledBackend is a log backend with additional knobs for setting levels on
// individual modules to different levels.
type
LeveledBackend
interface
{
Backend
Leveled
}
type
moduleLeveled
struct
{
levels
map
[
string
]
Level
backend
Backend
formatter
Formatter
once
sync
.
Once
}
// AddModuleLevel wraps a log backend with knobs to have different log levels
// for different modules.
func
AddModuleLevel
(
backend
Backend
)
LeveledBackend
{
var
leveled
LeveledBackend
var
ok
bool
if
leveled
,
ok
=
backend
.
(
LeveledBackend
);
!
ok
{
leveled
=
&
moduleLeveled
{
levels
:
make
(
map
[
string
]
Level
),
backend
:
backend
,
}
}
return
leveled
}
// GetLevel returns the log level for the given module.
func
(
l
*
moduleLeveled
)
GetLevel
(
module
string
)
Level
{
level
,
exists
:=
l
.
levels
[
module
]
if
exists
==
false
{
level
,
exists
=
l
.
levels
[
""
]
// no configuration exists, default to debug
if
exists
==
false
{
level
=
DEBUG
}
}
return
level
}
// SetLevel sets the log level for the given module.
func
(
l
*
moduleLeveled
)
SetLevel
(
level
Level
,
module
string
)
{
l
.
levels
[
module
]
=
level
}
// IsEnabledFor will return true if logging is enabled for the given module.
func
(
l
*
moduleLeveled
)
IsEnabledFor
(
level
Level
,
module
string
)
bool
{
return
level
<=
l
.
GetLevel
(
module
)
}
func
(
l
*
moduleLeveled
)
Log
(
level
Level
,
calldepth
int
,
rec
*
Record
)
(
err
error
)
{
if
l
.
IsEnabledFor
(
level
,
rec
.
Module
)
{
// TODO get rid of traces of formatter here. BackendFormatter should be used.
rec
.
formatter
=
l
.
getFormatterAndCacheCurrent
()
err
=
l
.
backend
.
Log
(
level
,
calldepth
+
1
,
rec
)
}
return
}
func
(
l
*
moduleLeveled
)
getFormatterAndCacheCurrent
()
Formatter
{
l
.
once
.
Do
(
func
()
{
if
l
.
formatter
==
nil
{
l
.
formatter
=
getFormatter
()
}
})
return
l
.
formatter
}
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/level_test.go
deleted
100644 → 0
View file @
a40ef343
// Copyright 2013, Örjan Persson. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package
logging
import
"testing"
func
TestLevelString
(
t
*
testing
.
T
)
{
// Make sure all levels can be converted from string -> constant -> string
for
_
,
name
:=
range
levelNames
{
level
,
err
:=
LogLevel
(
name
)
if
err
!=
nil
{
t
.
Errorf
(
"failed to get level: %v"
,
err
)
continue
}
if
level
.
String
()
!=
name
{
t
.
Errorf
(
"invalid level conversion: %v != %v"
,
level
,
name
)
}
}
}
func
TestLevelLogLevel
(
t
*
testing
.
T
)
{
tests
:=
[]
struct
{
expected
Level
level
string
}{
{
-
1
,
"bla"
},
{
INFO
,
"iNfO"
},
{
ERROR
,
"error"
},
{
WARNING
,
"warninG"
},
}
for
_
,
test
:=
range
tests
{
level
,
err
:=
LogLevel
(
test
.
level
)
if
err
!=
nil
{
if
test
.
expected
==
-
1
{
continue
}
else
{
t
.
Errorf
(
"failed to convert %s: %s"
,
test
.
level
,
err
)
}
}
if
test
.
expected
!=
level
{
t
.
Errorf
(
"failed to convert %s to level: %s != %s"
,
test
.
level
,
test
.
expected
,
level
)
}
}
}
func
TestLevelModuleLevel
(
t
*
testing
.
T
)
{
backend
:=
NewMemoryBackend
(
128
)
leveled
:=
AddModuleLevel
(
backend
)
leveled
.
SetLevel
(
NOTICE
,
""
)
leveled
.
SetLevel
(
ERROR
,
"foo"
)
leveled
.
SetLevel
(
INFO
,
"foo.bar"
)
leveled
.
SetLevel
(
WARNING
,
"bar"
)
expected
:=
[]
struct
{
level
Level
module
string
}{
{
NOTICE
,
""
},
{
NOTICE
,
"something"
},
{
ERROR
,
"foo"
},
{
INFO
,
"foo.bar"
},
{
WARNING
,
"bar"
},
}
for
_
,
e
:=
range
expected
{
actual
:=
leveled
.
GetLevel
(
e
.
module
)
if
e
.
level
!=
actual
{
t
.
Errorf
(
"unexpected level in %s: %s != %s"
,
e
.
module
,
e
.
level
,
actual
)
}
}
}
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/log.go
deleted
100644 → 0
View file @
a40ef343
// Copyright 2013, Örjan Persson. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package
logging
import
(
"bytes"
"fmt"
"io"
"log"
)
// TODO initialize here
var
colors
[]
string
var
boldcolors
[]
string
type
color
int
const
(
colorBlack
=
(
iota
+
30
)
colorRed
colorGreen
colorYellow
colorBlue
colorMagenta
colorCyan
colorWhite
)
// LogBackend utilizes the standard log module.
type
LogBackend
struct
{
Logger
*
log
.
Logger
Color
bool
}
// NewLogBackend creates a new LogBackend.
func
NewLogBackend
(
out
io
.
Writer
,
prefix
string
,
flag
int
)
*
LogBackend
{
return
&
LogBackend
{
Logger
:
log
.
New
(
out
,
prefix
,
flag
)}
}
func
(
b
*
LogBackend
)
Log
(
level
Level
,
calldepth
int
,
rec
*
Record
)
error
{
if
b
.
Color
{
buf
:=
&
bytes
.
Buffer
{}
buf
.
Write
([]
byte
(
colors
[
level
]))
buf
.
Write
([]
byte
(
rec
.
Formatted
(
calldepth
+
1
)))
buf
.
Write
([]
byte
(
"
\0
33[0m"
))
// For some reason, the Go logger arbitrarily decided "2" was the correct
// call depth...
return
b
.
Logger
.
Output
(
calldepth
+
2
,
buf
.
String
())
}
else
{
return
b
.
Logger
.
Output
(
calldepth
+
2
,
rec
.
Formatted
(
calldepth
+
1
))
}
panic
(
"should not be reached"
)
}
func
colorSeq
(
color
color
)
string
{
return
fmt
.
Sprintf
(
"
\0
33[%dm"
,
int
(
color
))
}
func
colorSeqBold
(
color
color
)
string
{
return
fmt
.
Sprintf
(
"
\0
33[%d;1m"
,
int
(
color
))
}
func
init
()
{
colors
=
[]
string
{
CRITICAL
:
colorSeq
(
colorMagenta
),
ERROR
:
colorSeq
(
colorRed
),
WARNING
:
colorSeq
(
colorYellow
),
NOTICE
:
colorSeq
(
colorGreen
),
DEBUG
:
colorSeq
(
colorCyan
),
}
boldcolors
=
[]
string
{
CRITICAL
:
colorSeqBold
(
colorMagenta
),
ERROR
:
colorSeqBold
(
colorRed
),
WARNING
:
colorSeqBold
(
colorYellow
),
NOTICE
:
colorSeqBold
(
colorGreen
),
DEBUG
:
colorSeqBold
(
colorCyan
),
}
}
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/log_test.go
deleted
100644 → 0
View file @
a40ef343
// Copyright 2013, Örjan Persson. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package
logging
import
(
"bytes"
"io/ioutil"
"log"
"strings"
"testing"
)
func
TestLogCalldepth
(
t
*
testing
.
T
)
{
buf
:=
&
bytes
.
Buffer
{}
SetBackend
(
NewLogBackend
(
buf
,
""
,
log
.
Lshortfile
))
SetFormatter
(
MustStringFormatter
(
"%{shortfile} %{level} %{message}"
))
log
:=
MustGetLogger
(
"test"
)
log
.
Info
(
"test filename"
)
parts
:=
strings
.
SplitN
(
buf
.
String
(),
" "
,
2
)
// Verify that the correct filename is registered by the stdlib logger
if
!
strings
.
HasPrefix
(
parts
[
0
],
"log_test.go:"
)
{
t
.
Errorf
(
"incorrect filename: %s"
,
parts
[
0
])
}
// Verify that the correct filename is registered by go-logging
if
!
strings
.
HasPrefix
(
parts
[
1
],
"log_test.go:"
)
{
t
.
Errorf
(
"incorrect filename: %s"
,
parts
[
1
])
}
}
func
BenchmarkLogMemoryBackendIgnored
(
b
*
testing
.
B
)
{
backend
:=
SetBackend
(
NewMemoryBackend
(
1024
))
backend
.
SetLevel
(
INFO
,
""
)
RunLogBenchmark
(
b
)
}
func
BenchmarkLogMemoryBackend
(
b
*
testing
.
B
)
{
backend
:=
SetBackend
(
NewMemoryBackend
(
1024
))
backend
.
SetLevel
(
DEBUG
,
""
)
RunLogBenchmark
(
b
)
}
func
BenchmarkLogChannelMemoryBackend
(
b
*
testing
.
B
)
{
channelBackend
:=
NewChannelMemoryBackend
(
1024
)
backend
:=
SetBackend
(
channelBackend
)
backend
.
SetLevel
(
DEBUG
,
""
)
RunLogBenchmark
(
b
)
channelBackend
.
Flush
()
}
func
BenchmarkLogLeveled
(
b
*
testing
.
B
)
{
backend
:=
SetBackend
(
NewLogBackend
(
ioutil
.
Discard
,
""
,
0
))
backend
.
SetLevel
(
INFO
,
""
)
RunLogBenchmark
(
b
)
}
func
BenchmarkLogLogBackend
(
b
*
testing
.
B
)
{
backend
:=
SetBackend
(
NewLogBackend
(
ioutil
.
Discard
,
""
,
0
))
backend
.
SetLevel
(
DEBUG
,
""
)
RunLogBenchmark
(
b
)
}
func
BenchmarkLogLogBackendColor
(
b
*
testing
.
B
)
{
colorizer
:=
NewLogBackend
(
ioutil
.
Discard
,
""
,
0
)
colorizer
.
Color
=
true
backend
:=
SetBackend
(
colorizer
)
backend
.
SetLevel
(
DEBUG
,
""
)
RunLogBenchmark
(
b
)
}
func
BenchmarkLogLogBackendStdFlags
(
b
*
testing
.
B
)
{
backend
:=
SetBackend
(
NewLogBackend
(
ioutil
.
Discard
,
""
,
log
.
LstdFlags
))
backend
.
SetLevel
(
DEBUG
,
""
)
RunLogBenchmark
(
b
)
}
func
BenchmarkLogLogBackendLongFileFlag
(
b
*
testing
.
B
)
{
backend
:=
SetBackend
(
NewLogBackend
(
ioutil
.
Discard
,
""
,
log
.
Llongfile
))
backend
.
SetLevel
(
DEBUG
,
""
)
RunLogBenchmark
(
b
)
}
func
RunLogBenchmark
(
b
*
testing
.
B
)
{
password
:=
Password
(
"foo"
)
log
:=
MustGetLogger
(
"test"
)
b
.
ResetTimer
()
for
i
:=
0
;
i
<
b
.
N
;
i
++
{
log
.
Debug
(
"log line for %d and this is rectified: %s"
,
i
,
password
)
}
}
func
BenchmarkLogFixed
(
b
*
testing
.
B
)
{
backend
:=
SetBackend
(
NewLogBackend
(
ioutil
.
Discard
,
""
,
0
))
backend
.
SetLevel
(
DEBUG
,
""
)
RunLogBenchmarkFixedString
(
b
)
}
func
BenchmarkLogFixedIgnored
(
b
*
testing
.
B
)
{
backend
:=
SetBackend
(
NewLogBackend
(
ioutil
.
Discard
,
""
,
0
))
backend
.
SetLevel
(
INFO
,
""
)
RunLogBenchmarkFixedString
(
b
)
}
func
RunLogBenchmarkFixedString
(
b
*
testing
.
B
)
{
log
:=
MustGetLogger
(
"test"
)
b
.
ResetTimer
()
for
i
:=
0
;
i
<
b
.
N
;
i
++
{
log
.
Debug
(
"some random fixed text"
)
}
}
vendor/gx/QmQvJiADDe7JR4m968MwXobTCCzUqQkP87aRHe29MEBGHV/go-logging/logger.go
deleted
100644 → 0
View file @
a40ef343
// Copyright 2013, Örjan Persson. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// Package logging implements a logging infrastructure for Go. It supports
// different logging backends like syslog, file and memory. Multiple backends
// can be utilized with different log levels per backend and logger.
package
logging
import
(
"bytes"
"fmt"
"log"
"os"
"strings"
"sync/atomic"
"time"
)
// Redactor is an interface for types that may contain sensitive information
// (like passwords), which shouldn't be printed to the log. The idea was found
// in relog as part of the vitness project.
type
Redactor
interface
{
Redacted
()
interface
{}
}
// Redact returns a string of * having the same length as s.
func
Redact
(
s
string
)
string
{
return
strings
.
Repeat
(
"*"
,
len
(
s
))
}
var
(
// Sequence number is incremented and utilized for all log records created.
sequenceNo
uint64
// timeNow is a customizable for testing purposes.
timeNow
=
time
.
Now
)
// Record represents a log record and contains the timestamp when the record
// was created, an increasing id, filename and line and finally the actual
// formatted log line.
type
Record
struct
{
Id
uint64
Time
time
.
Time
Module
string
Level
Level
// message is kept as a pointer to have shallow copies update this once
// needed.
message
*
string
args
[]
interface
{}
fmt
string
formatter
Formatter
formatted
string
}
// Formatted returns the string-formatted version of a record.
func
(
r
*
Record
)
Formatted
(
calldepth
int
)
string
{
if
r
.
formatted
==
""
{
var
buf
bytes
.
Buffer
r
.
formatter
.
Format
(
calldepth
+
1
,
r
,
&
buf
)
r
.
formatted
=
buf
.
String
()
}
return
r
.
formatted
}
// Message returns a string message for outputting. Redacts any record args
// that implement the Redactor interface
func
(
r
*
Record
)
Message
()
string
{
if
r
.
message
==
nil
{
// Redact the arguments that implements the Redactor interface
for
i
,
arg
:=
range
r
.
args
{
if
redactor
,
ok
:=
arg
.
(
Redactor
);
ok
==
true
{
r
.
args
[
i
]
=
redactor
.
Redacted
()
}
}
msg
:=
fmt
.
Sprintf
(
r
.
fmt
,
r
.
args
...
)
r
.
message
=
&
msg
}
return
*
r
.
message
}
// Logger is a logging unit. It controls the flow of messages to a given
// (swappable) backend.
type
Logger
struct
{
Module
string
backend
LeveledBackend
haveBackend
bool
// ExtraCallDepth can be used to add additional call depth when getting the
// calling function. This is normally used when wrapping a logger.
ExtraCalldepth
int
}
// SetBackend changes the backend of the logger.
func
(
l
*
Logger
)
SetBackend
(
backend
LeveledBackend
)
{
l
.
backend
=
backend
l
.
haveBackend
=
true
}
// GetLogger creates and returns a Logger object based on the module name.
// TODO call NewLogger and remove MustGetLogger?
func
GetLogger
(
module
string
)
(
*
Logger
,
error
)
{
return
&
Logger
{
Module
:
module
},
nil
}
// MustGetLogger is like GetLogger but panics if the logger can't be created.
// It simplifies safe initialization of a global logger for eg. a package.
func
MustGetLogger
(
module
string
)
*
Logger
{
logger
,
err
:=
GetLogger
(
module
)
if
err
!=
nil
{
panic
(
"logger: "
+
module
+
": "
+
err
.
Error
())
}
return
logger
}
// Reset restores the internal state of the logging library.
func
Reset
()
{
// TODO make a global Init() method to be less magic? or make it such that
// if there's no backends at all configured, we could use some tricks to
// automatically setup backends based if we have a TTY or not.
sequenceNo
=
0
b
:=
SetBackend
(
NewLogBackend
(
os
.
Stderr
,
""
,
log
.
LstdFlags
))
b
.
SetLevel
(
DEBUG
,
""
)
SetFormatter
(
DefaultFormatter
)
timeNow
=
time
.
Now
}
// InitForTesting is a convenient method when using logging in a test. Once
// called, the time will be frozen to January 1, 1970 UTC.
func
InitForTesting
(
level
Level
)
*
MemoryBackend
{
Reset
()
memoryBackend
:=
NewMemoryBackend
(
10240
)
leveledBackend
:=
AddModuleLevel
(
memoryBackend
)
leveledBackend
.
SetLevel
(
level
,
""
)
SetBackend
(
leveledBackend
)
timeNow
=
func
()
time
.
Time
{
return
time
.
Unix
(
0
,
0
)
.
UTC
()
}
return
memoryBackend
}
// IsEnabledFor returns true if the logger is enabled for the given level.
func
(
l
*
Logger
)
IsEnabledFor
(
level
Level
)
bool
{
return
defaultBackend
.
IsEnabledFor
(
level
,
l
.
Module
)
}
func
(
l
*
Logger
)
log
(
lvl
Level
,
format
string
,
args
...
interface
{})
{
if
!
l
.
IsEnabledFor
(
lvl
)
{
return
}
// Create the logging record and pass it in to the backend
record
:=
&
Record
{
Id
:
atomic
.
AddUint64
(
&
sequenceNo
,
1
),
Time
:
timeNow
(),
Module
:
l
.
Module
,
Level
:
lvl
,
fmt
:
format
,
args
:
args
,
}
// TODO use channels to fan out the records to all backends?
// TODO in case of errors, do something (tricky)
// calldepth=2 brings the stack up to the caller of the level
// methods, Info(), Fatal(), etc.
// ExtraCallDepth allows this to be extended further up the stack in case we
// are wrapping these methods, eg. to expose them package level
if
l
.
haveBackend
{
l
.
backend
.
Log
(
lvl
,
2
+
l
.
ExtraCalldepth
,
record
)
return
}
defaultBackend
.
Log
(
lvl
,
2
+
l
.
ExtraCalldepth
,
record
)
}
// Fatal is equivalent to l.Critical(fmt.Sprint()) followed by a call to os.Exit(1).
func
(
l
*
Logger
)
Fatal
(
args
...
interface
{})
{
s
:=
fmt
.
Sprint
(
args
...
)
l
.
log
(
CRITICAL
,
"%s"
,
s
)
os
.
Exit
(
1
)
}
// Fatalf is equivalent to l.Critical followed by a call to os.Exit(1).
func
(
l
*
Logger
)
Fatalf
(
format
string
,
args
...
interface
{})
{
l
.
log
(
CRITICAL
,
format
,
args
...
)
os
.
Exit
(
1
)
}
// Panic is equivalent to l.Critical(fmt.Sprint()) followed by a call to panic().
func
(
l
*
Logger
)
Panic
(
args
...
interface
{})
{
s
:=
fmt
.
Sprint
(
args
...
)
l
.
log
(
CRITICAL
,
"%s"
,
s
)
panic
(
s
)
}
// Panicf is equivalent to l.Critical followed by a call to panic().
func
(
l
*
Logger
)
Panicf
(
format
string
,
args
...
interface
{})
{
s
:=
fmt
.
Sprintf
(
format
,
args
...
)
l
.
log
(
CRITICAL
,
"%s"
,
s
)
panic
(
s
)
}
// Critical logs a message using CRITICAL as log level. (fmt.Sprint())
func
(
l
*
Logger
)
Critical
(
args
...
interface
{})
{
s
:=
fmt
.
Sprint
(
args
...
)
l
.
log
(
CRITICAL
,
"%s"
,
s
)
}
// Criticalf logs a message using CRITICAL as log level.
func
(
l
*
Logger
)
Criticalf
(
format
string
,
args
...
interface
{})
{
l
.
log
(
CRITICAL
,
format
,
args
...
)
}
// Error logs a message using ERROR as log level. (fmt.Sprint())
func
(
l
*
Logger
)
Error
(
args
...
interface
{})
{
s
:=
fmt
.
Sprint
(
args
...
)
l
.
log
(
ERROR
,
"%s"
,
s
)
}
// Errorf logs a message using ERROR as log level.
func
(
l
*
Logger
)
Errorf
(
format
string
,
args
...
interface
{})
{
l
.
log
(
ERROR
,
format
,
args
...
)
}
// Warning logs a message using WARNING as log level.
func
(
l
*
Logger
)
Warning
(
args
...
interface
{})
{
s
:=
fmt
.
Sprint
(
args
...
)
l
.
log
(
WARNING
,
"%s"
,
s
)
}
// Warningf logs a message using WARNING as log level.
func
(
l
*
Logger
)
Warningf
(
format
string
,
args
...
interface
{})
{
l
.
log
(
WARNING
,
format
,
args
...
)
}
// Notice logs a message using NOTICE as log level.
func
(
l
*
Logger
)
Notice
(
args
...
interface
{})
{
s
:=
fmt
.
Sprint
(
args
...
)
l
.
log
(
NOTICE
,
"%s"
,
s
)
}
// Noticef logs a message using NOTICE as log level.
func
(
l
*
Logger
)
Noticef
(
format
string
,
args
...
interface
{})
{
l
.
log
(
NOTICE
,
format
,
args
...
)
}
// Info logs a message using INFO as log level.
func
(
l
*
Logger
)
Info
(
args
...
interface
{})
{
s
:=
fmt
.
Sprint
(
args
...
)
l
.
log
(
INFO
,
"%s"
,
s
)
}
// Infof logs a message using INFO as log level.
func
(
l
*
Logger
)
Infof
(
format
string
,
args
...
interface
{})
{
l
.
log
(
INFO
,
format
,
args
...
)
}
// Debug logs a message using DEBUG as log level.
func
(
l
*
Logger
)
Debug
(
args
...
interface
{})
{
s
:=
fmt
.
Sprint
(
args
...
)
l
.
log
(
DEBUG
,
"%s"
,
s
)
}
// Debugf logs a message using DEBUG as log level.
func
(
l
*
Logger
)
Debugf
(
format
string
,
args
...
interface
{})
{
l
.
log
(
DEBUG
,
format
,
args
...
)
}
func
init
()
{
Reset
()
}
Prev
1
…
6
7
8
9
10
11
12
13
14
…
19
Next
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