mirror of
https://github.com/minio/minio.git
synced 2025-01-13 16:03:21 -05:00
iodine is part of minio now
This commit is contained in:
parent
879e428596
commit
38155e86ac
8
Godeps/Godeps.json
generated
8
Godeps/Godeps.json
generated
@ -5,6 +5,10 @@
|
|||||||
"./..."
|
"./..."
|
||||||
],
|
],
|
||||||
"Deps": [
|
"Deps": [
|
||||||
|
{
|
||||||
|
"ImportPath": "github.com/dustin/go-humanize",
|
||||||
|
"Rev": "8cc1aaa2d955ee82833337cfb10babc42be6bce6"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"ImportPath": "github.com/gorilla/context",
|
"ImportPath": "github.com/gorilla/context",
|
||||||
"Rev": "50c25fb3b2b3b3cc724e9b6ac75fb44b3bccd0da"
|
"Rev": "50c25fb3b2b3b3cc724e9b6ac75fb44b3bccd0da"
|
||||||
@ -22,10 +26,6 @@
|
|||||||
"Comment": "1.2.0-102-gecb385c",
|
"Comment": "1.2.0-102-gecb385c",
|
||||||
"Rev": "ecb385c3fefd53678e3b6beba6a608fb7c8dfac1"
|
"Rev": "ecb385c3fefd53678e3b6beba6a608fb7c8dfac1"
|
||||||
},
|
},
|
||||||
{
|
|
||||||
"ImportPath": "github.com/minio-io/iodine",
|
|
||||||
"Rev": "9a63d02ce3934e159d00732f15e096e4f86a6dbb"
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
"ImportPath": "github.com/stretchr/objx",
|
"ImportPath": "github.com/stretchr/objx",
|
||||||
"Rev": "cbeaeb16a013161a98496fad62933b1d21786672"
|
"Rev": "cbeaeb16a013161a98496fad62933b1d21786672"
|
||||||
|
6
Godeps/_workspace/src/github.com/dustin/go-humanize/.gitignore
generated
vendored
Normal file
6
Godeps/_workspace/src/github.com/dustin/go-humanize/.gitignore
generated
vendored
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
#*
|
||||||
|
*.[568]
|
||||||
|
*.a
|
||||||
|
*~
|
||||||
|
[568].out
|
||||||
|
_*
|
21
Godeps/_workspace/src/github.com/dustin/go-humanize/LICENSE
generated
vendored
Normal file
21
Godeps/_workspace/src/github.com/dustin/go-humanize/LICENSE
generated
vendored
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
Copyright (c) 2005-2008 Dustin Sallings <dustin@spy.net>
|
||||||
|
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
of this software and associated documentation files (the "Software"), to deal
|
||||||
|
in the Software without restriction, including without limitation the rights
|
||||||
|
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
copies of the Software, and to permit persons to whom the Software is
|
||||||
|
furnished to do so, subject to the following conditions:
|
||||||
|
|
||||||
|
The above copyright notice and this permission notice shall be included in
|
||||||
|
all copies or substantial portions of the Software.
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
SOFTWARE.
|
||||||
|
|
||||||
|
<http://www.opensource.org/licenses/mit-license.php>
|
78
Godeps/_workspace/src/github.com/dustin/go-humanize/README.markdown
generated
vendored
Normal file
78
Godeps/_workspace/src/github.com/dustin/go-humanize/README.markdown
generated
vendored
Normal file
@ -0,0 +1,78 @@
|
|||||||
|
# Humane Units
|
||||||
|
|
||||||
|
Just a few functions for helping humanize times and sizes.
|
||||||
|
|
||||||
|
`go get` it as `github.com/dustin/go-humanize`, import it as
|
||||||
|
`"github.com/dustin/go-humanize"`, use it as `humanize`
|
||||||
|
|
||||||
|
## Sizes
|
||||||
|
|
||||||
|
This lets you take numbers like `82854982` and convert them to useful
|
||||||
|
strings like, `83MB` or `79MiB` (whichever you prefer).
|
||||||
|
|
||||||
|
Example:
|
||||||
|
|
||||||
|
fmt.Printf("That file is %s.", humanize.Bytes(82854982))
|
||||||
|
|
||||||
|
## Times
|
||||||
|
|
||||||
|
This lets you take a `time.Time` and spit it out in relative terms.
|
||||||
|
For example, `12 seconds ago` or `3 days from now`.
|
||||||
|
|
||||||
|
Example:
|
||||||
|
|
||||||
|
fmt.Printf("This was touched %s", humanize.Time(someTimeInstance))
|
||||||
|
|
||||||
|
Thanks to Kyle Lemons for the time implementation from an IRC
|
||||||
|
conversation one day. It's pretty neat.
|
||||||
|
|
||||||
|
## Ordinals
|
||||||
|
|
||||||
|
From a [mailing list discussion][odisc] where a user wanted to be able
|
||||||
|
to label ordinals.
|
||||||
|
|
||||||
|
0 -> 0th
|
||||||
|
1 -> 1st
|
||||||
|
2 -> 2nd
|
||||||
|
3 -> 3rd
|
||||||
|
4 -> 4th
|
||||||
|
[...]
|
||||||
|
|
||||||
|
Example:
|
||||||
|
|
||||||
|
fmt.Printf("You're my %s best friend.", humanize.Ordinal(193))
|
||||||
|
|
||||||
|
## Commas
|
||||||
|
|
||||||
|
Want to shove commas into numbers? Be my guest.
|
||||||
|
|
||||||
|
0 -> 0
|
||||||
|
100 -> 100
|
||||||
|
1000 -> 1,000
|
||||||
|
1000000000 -> 1,000,000,000
|
||||||
|
-100000 -> -100,000
|
||||||
|
|
||||||
|
Example:
|
||||||
|
|
||||||
|
fmt.Printf("You owe $%s.\n", humanize.Comma(6582491))
|
||||||
|
|
||||||
|
## Ftoa
|
||||||
|
|
||||||
|
Nicer float64 formatter that removes trailing zeros.
|
||||||
|
|
||||||
|
fmt.Printf("%f", 2.24) // 2.240000
|
||||||
|
fmt.Printf("%s", humanize.Ftoa(2.24)) // 2.24
|
||||||
|
fmt.Printf("%f", 2.0) // 2.000000
|
||||||
|
fmt.Printf("%s", humanize.Ftoa(2.0)) // 2
|
||||||
|
|
||||||
|
## SI notation
|
||||||
|
|
||||||
|
Format numbers with [SI notation][sinotation].
|
||||||
|
|
||||||
|
Example:
|
||||||
|
|
||||||
|
humanize.SI(0.00000000223, "M") // 2.23nM
|
||||||
|
|
||||||
|
|
||||||
|
[odisc]: https://groups.google.com/d/topic/golang-nuts/l8NhI74jl-4/discussion
|
||||||
|
[sinotation]: http://en.wikipedia.org/wiki/Metric_prefix
|
31
Godeps/_workspace/src/github.com/dustin/go-humanize/big.go
generated
vendored
Normal file
31
Godeps/_workspace/src/github.com/dustin/go-humanize/big.go
generated
vendored
Normal file
@ -0,0 +1,31 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"math/big"
|
||||||
|
)
|
||||||
|
|
||||||
|
// order of magnitude (to a max order)
|
||||||
|
func oomm(n, b *big.Int, maxmag int) (float64, int) {
|
||||||
|
mag := 0
|
||||||
|
m := &big.Int{}
|
||||||
|
for n.Cmp(b) >= 0 {
|
||||||
|
n.DivMod(n, b, m)
|
||||||
|
mag++
|
||||||
|
if mag == maxmag && maxmag >= 0 {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return float64(n.Int64()) + (float64(m.Int64()) / float64(b.Int64())), mag
|
||||||
|
}
|
||||||
|
|
||||||
|
// total order of magnitude
|
||||||
|
// (same as above, but with no upper limit)
|
||||||
|
func oom(n, b *big.Int) (float64, int) {
|
||||||
|
mag := 0
|
||||||
|
m := &big.Int{}
|
||||||
|
for n.Cmp(b) >= 0 {
|
||||||
|
n.DivMod(n, b, m)
|
||||||
|
mag++
|
||||||
|
}
|
||||||
|
return float64(n.Int64()) + (float64(m.Int64()) / float64(b.Int64())), mag
|
||||||
|
}
|
164
Godeps/_workspace/src/github.com/dustin/go-humanize/bigbytes.go
generated
vendored
Normal file
164
Godeps/_workspace/src/github.com/dustin/go-humanize/bigbytes.go
generated
vendored
Normal file
@ -0,0 +1,164 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"math/big"
|
||||||
|
"strings"
|
||||||
|
"unicode"
|
||||||
|
)
|
||||||
|
|
||||||
|
var (
|
||||||
|
bigIECExp = big.NewInt(1024)
|
||||||
|
|
||||||
|
// BigByte is one byte in bit.Ints
|
||||||
|
BigByte = big.NewInt(1)
|
||||||
|
// BigKiByte is 1,024 bytes in bit.Ints
|
||||||
|
BigKiByte = (&big.Int{}).Mul(BigByte, bigIECExp)
|
||||||
|
// BigMiByte is 1,024 k bytes in bit.Ints
|
||||||
|
BigMiByte = (&big.Int{}).Mul(BigKiByte, bigIECExp)
|
||||||
|
// BigGiByte is 1,024 m bytes in bit.Ints
|
||||||
|
BigGiByte = (&big.Int{}).Mul(BigMiByte, bigIECExp)
|
||||||
|
// BigTiByte is 1,024 g bytes in bit.Ints
|
||||||
|
BigTiByte = (&big.Int{}).Mul(BigGiByte, bigIECExp)
|
||||||
|
// BigPiByte is 1,024 t bytes in bit.Ints
|
||||||
|
BigPiByte = (&big.Int{}).Mul(BigTiByte, bigIECExp)
|
||||||
|
// BigEiByte is 1,024 p bytes in bit.Ints
|
||||||
|
BigEiByte = (&big.Int{}).Mul(BigPiByte, bigIECExp)
|
||||||
|
// BigZiByte is 1,024 e bytes in bit.Ints
|
||||||
|
BigZiByte = (&big.Int{}).Mul(BigEiByte, bigIECExp)
|
||||||
|
// BigYiByte is 1,024 z bytes in bit.Ints
|
||||||
|
BigYiByte = (&big.Int{}).Mul(BigZiByte, bigIECExp)
|
||||||
|
)
|
||||||
|
|
||||||
|
var (
|
||||||
|
bigSIExp = big.NewInt(1000)
|
||||||
|
|
||||||
|
// BigSIByte is one SI byte in big.Ints
|
||||||
|
BigSIByte = big.NewInt(1)
|
||||||
|
// BigKByte is 1,000 SI bytes in big.Ints
|
||||||
|
BigKByte = (&big.Int{}).Mul(BigSIByte, bigSIExp)
|
||||||
|
// BigMByte is 1,000 SI k bytes in big.Ints
|
||||||
|
BigMByte = (&big.Int{}).Mul(BigKByte, bigSIExp)
|
||||||
|
// BigGByte is 1,000 SI m bytes in big.Ints
|
||||||
|
BigGByte = (&big.Int{}).Mul(BigMByte, bigSIExp)
|
||||||
|
// BigTByte is 1,000 SI g bytes in big.Ints
|
||||||
|
BigTByte = (&big.Int{}).Mul(BigGByte, bigSIExp)
|
||||||
|
// BigPByte is 1,000 SI t bytes in big.Ints
|
||||||
|
BigPByte = (&big.Int{}).Mul(BigTByte, bigSIExp)
|
||||||
|
// BigEByte is 1,000 SI p bytes in big.Ints
|
||||||
|
BigEByte = (&big.Int{}).Mul(BigPByte, bigSIExp)
|
||||||
|
// BigZByte is 1,000 SI e bytes in big.Ints
|
||||||
|
BigZByte = (&big.Int{}).Mul(BigEByte, bigSIExp)
|
||||||
|
// BigYByte is 1,000 SI z bytes in big.Ints
|
||||||
|
BigYByte = (&big.Int{}).Mul(BigZByte, bigSIExp)
|
||||||
|
)
|
||||||
|
|
||||||
|
var bigBytesSizeTable = map[string]*big.Int{
|
||||||
|
"b": BigByte,
|
||||||
|
"kib": BigKiByte,
|
||||||
|
"kb": BigKByte,
|
||||||
|
"mib": BigMiByte,
|
||||||
|
"mb": BigMByte,
|
||||||
|
"gib": BigGiByte,
|
||||||
|
"gb": BigGByte,
|
||||||
|
"tib": BigTiByte,
|
||||||
|
"tb": BigTByte,
|
||||||
|
"pib": BigPiByte,
|
||||||
|
"pb": BigPByte,
|
||||||
|
"eib": BigEiByte,
|
||||||
|
"eb": BigEByte,
|
||||||
|
"zib": BigZiByte,
|
||||||
|
"zb": BigZByte,
|
||||||
|
"yib": BigYiByte,
|
||||||
|
"yb": BigYByte,
|
||||||
|
// Without suffix
|
||||||
|
"": BigByte,
|
||||||
|
"ki": BigKiByte,
|
||||||
|
"k": BigKByte,
|
||||||
|
"mi": BigMiByte,
|
||||||
|
"m": BigMByte,
|
||||||
|
"gi": BigGiByte,
|
||||||
|
"g": BigGByte,
|
||||||
|
"ti": BigTiByte,
|
||||||
|
"t": BigTByte,
|
||||||
|
"pi": BigPiByte,
|
||||||
|
"p": BigPByte,
|
||||||
|
"ei": BigEiByte,
|
||||||
|
"e": BigEByte,
|
||||||
|
"z": BigZByte,
|
||||||
|
"zi": BigZiByte,
|
||||||
|
"y": BigYByte,
|
||||||
|
"yi": BigYiByte,
|
||||||
|
}
|
||||||
|
|
||||||
|
var ten = big.NewInt(10)
|
||||||
|
|
||||||
|
func humanateBigBytes(s, base *big.Int, sizes []string) string {
|
||||||
|
if s.Cmp(ten) < 0 {
|
||||||
|
return fmt.Sprintf("%dB", s)
|
||||||
|
}
|
||||||
|
c := (&big.Int{}).Set(s)
|
||||||
|
val, mag := oomm(c, base, len(sizes)-1)
|
||||||
|
suffix := sizes[mag]
|
||||||
|
f := "%.0f%s"
|
||||||
|
if val < 10 {
|
||||||
|
f = "%.1f%s"
|
||||||
|
}
|
||||||
|
|
||||||
|
return fmt.Sprintf(f, val, suffix)
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
// BigBytes produces a human readable representation of an SI size.
|
||||||
|
//
|
||||||
|
// See also: ParseBigBytes.
|
||||||
|
//
|
||||||
|
// BigBytes(82854982) -> 83MB
|
||||||
|
func BigBytes(s *big.Int) string {
|
||||||
|
sizes := []string{"B", "KB", "MB", "GB", "TB", "PB", "EB", "ZB", "YB"}
|
||||||
|
return humanateBigBytes(s, bigSIExp, sizes)
|
||||||
|
}
|
||||||
|
|
||||||
|
// BigIBytes produces a human readable representation of an IEC size.
|
||||||
|
//
|
||||||
|
// See also: ParseBigBytes.
|
||||||
|
//
|
||||||
|
// BigIBytes(82854982) -> 79MiB
|
||||||
|
func BigIBytes(s *big.Int) string {
|
||||||
|
sizes := []string{"B", "KiB", "MiB", "GiB", "TiB", "PiB", "EiB", "ZiB", "YiB"}
|
||||||
|
return humanateBigBytes(s, bigIECExp, sizes)
|
||||||
|
}
|
||||||
|
|
||||||
|
// ParseBigBytes parses a string representation of bytes into the number
|
||||||
|
// of bytes it represents.
|
||||||
|
//
|
||||||
|
// See also: BigBytes, BigIBytes.
|
||||||
|
//
|
||||||
|
// ParseBigBytes("42MB") -> 42000000, nil
|
||||||
|
// ParseBigBytes("42mib") -> 44040192, nil
|
||||||
|
func ParseBigBytes(s string) (*big.Int, error) {
|
||||||
|
lastDigit := 0
|
||||||
|
for _, r := range s {
|
||||||
|
if !(unicode.IsDigit(r) || r == '.') {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
lastDigit++
|
||||||
|
}
|
||||||
|
|
||||||
|
val := &big.Rat{}
|
||||||
|
_, err := fmt.Sscanf(s[:lastDigit], "%f", val)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
extra := strings.ToLower(strings.TrimSpace(s[lastDigit:]))
|
||||||
|
if m, ok := bigBytesSizeTable[extra]; ok {
|
||||||
|
mv := (&big.Rat{}).SetInt(m)
|
||||||
|
val.Mul(val, mv)
|
||||||
|
rv := &big.Int{}
|
||||||
|
rv.Div(val.Num(), val.Denom())
|
||||||
|
return rv, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil, fmt.Errorf("unhandled size name: %v", extra)
|
||||||
|
}
|
219
Godeps/_workspace/src/github.com/dustin/go-humanize/bigbytes_test.go
generated
vendored
Normal file
219
Godeps/_workspace/src/github.com/dustin/go-humanize/bigbytes_test.go
generated
vendored
Normal file
@ -0,0 +1,219 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"math/big"
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestBigByteParsing(t *testing.T) {
|
||||||
|
tests := []struct {
|
||||||
|
in string
|
||||||
|
exp uint64
|
||||||
|
}{
|
||||||
|
{"42", 42},
|
||||||
|
{"42MB", 42000000},
|
||||||
|
{"42MiB", 44040192},
|
||||||
|
{"42mb", 42000000},
|
||||||
|
{"42mib", 44040192},
|
||||||
|
{"42MIB", 44040192},
|
||||||
|
{"42 MB", 42000000},
|
||||||
|
{"42 MiB", 44040192},
|
||||||
|
{"42 mb", 42000000},
|
||||||
|
{"42 mib", 44040192},
|
||||||
|
{"42 MIB", 44040192},
|
||||||
|
{"42.5MB", 42500000},
|
||||||
|
{"42.5MiB", 44564480},
|
||||||
|
{"42.5 MB", 42500000},
|
||||||
|
{"42.5 MiB", 44564480},
|
||||||
|
// No need to say B
|
||||||
|
{"42M", 42000000},
|
||||||
|
{"42Mi", 44040192},
|
||||||
|
{"42m", 42000000},
|
||||||
|
{"42mi", 44040192},
|
||||||
|
{"42MI", 44040192},
|
||||||
|
{"42 M", 42000000},
|
||||||
|
{"42 Mi", 44040192},
|
||||||
|
{"42 m", 42000000},
|
||||||
|
{"42 mi", 44040192},
|
||||||
|
{"42 MI", 44040192},
|
||||||
|
{"42.5M", 42500000},
|
||||||
|
{"42.5Mi", 44564480},
|
||||||
|
{"42.5 M", 42500000},
|
||||||
|
{"42.5 Mi", 44564480},
|
||||||
|
// Large testing, breaks when too much larger than
|
||||||
|
// this.
|
||||||
|
{"12.5 EB", uint64(12.5 * float64(EByte))},
|
||||||
|
{"12.5 E", uint64(12.5 * float64(EByte))},
|
||||||
|
{"12.5 EiB", uint64(12.5 * float64(EiByte))},
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, p := range tests {
|
||||||
|
got, err := ParseBigBytes(p.in)
|
||||||
|
if err != nil {
|
||||||
|
t.Errorf("Couldn't parse %v: %v", p.in, err)
|
||||||
|
} else {
|
||||||
|
if got.Uint64() != p.exp {
|
||||||
|
t.Errorf("Expected %v for %v, got %v",
|
||||||
|
p.exp, p.in, got)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestBigByteErrors(t *testing.T) {
|
||||||
|
got, err := ParseBigBytes("84 JB")
|
||||||
|
if err == nil {
|
||||||
|
t.Errorf("Expected error, got %v", got)
|
||||||
|
}
|
||||||
|
got, err = ParseBigBytes("")
|
||||||
|
if err == nil {
|
||||||
|
t.Errorf("Expected error parsing nothing")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func bbyte(in uint64) string {
|
||||||
|
return BigBytes((&big.Int{}).SetUint64(in))
|
||||||
|
}
|
||||||
|
|
||||||
|
func bibyte(in uint64) string {
|
||||||
|
return BigIBytes((&big.Int{}).SetUint64(in))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestBigBytes(t *testing.T) {
|
||||||
|
testList{
|
||||||
|
{"bytes(0)", bbyte(0), "0B"},
|
||||||
|
{"bytes(1)", bbyte(1), "1B"},
|
||||||
|
{"bytes(803)", bbyte(803), "803B"},
|
||||||
|
{"bytes(999)", bbyte(999), "999B"},
|
||||||
|
|
||||||
|
{"bytes(1024)", bbyte(1024), "1.0KB"},
|
||||||
|
{"bytes(1MB - 1)", bbyte(MByte - Byte), "1000KB"},
|
||||||
|
|
||||||
|
{"bytes(1MB)", bbyte(1024 * 1024), "1.0MB"},
|
||||||
|
{"bytes(1GB - 1K)", bbyte(GByte - KByte), "1000MB"},
|
||||||
|
|
||||||
|
{"bytes(1GB)", bbyte(GByte), "1.0GB"},
|
||||||
|
{"bytes(1TB - 1M)", bbyte(TByte - MByte), "1000GB"},
|
||||||
|
|
||||||
|
{"bytes(1TB)", bbyte(TByte), "1.0TB"},
|
||||||
|
{"bytes(1PB - 1T)", bbyte(PByte - TByte), "999TB"},
|
||||||
|
|
||||||
|
{"bytes(1PB)", bbyte(PByte), "1.0PB"},
|
||||||
|
{"bytes(1PB - 1T)", bbyte(EByte - PByte), "999PB"},
|
||||||
|
|
||||||
|
{"bytes(1EB)", bbyte(EByte), "1.0EB"},
|
||||||
|
// Overflows.
|
||||||
|
// {"bytes(1EB - 1P)", Bytes((KByte*EByte)-PByte), "1023EB"},
|
||||||
|
|
||||||
|
{"bytes(0)", bibyte(0), "0B"},
|
||||||
|
{"bytes(1)", bibyte(1), "1B"},
|
||||||
|
{"bytes(803)", bibyte(803), "803B"},
|
||||||
|
{"bytes(1023)", bibyte(1023), "1023B"},
|
||||||
|
|
||||||
|
{"bytes(1024)", bibyte(1024), "1.0KiB"},
|
||||||
|
{"bytes(1MB - 1)", bibyte(MiByte - IByte), "1024KiB"},
|
||||||
|
|
||||||
|
{"bytes(1MB)", bibyte(1024 * 1024), "1.0MiB"},
|
||||||
|
{"bytes(1GB - 1K)", bibyte(GiByte - KiByte), "1024MiB"},
|
||||||
|
|
||||||
|
{"bytes(1GB)", bibyte(GiByte), "1.0GiB"},
|
||||||
|
{"bytes(1TB - 1M)", bibyte(TiByte - MiByte), "1024GiB"},
|
||||||
|
|
||||||
|
{"bytes(1TB)", bibyte(TiByte), "1.0TiB"},
|
||||||
|
{"bytes(1PB - 1T)", bibyte(PiByte - TiByte), "1023TiB"},
|
||||||
|
|
||||||
|
{"bytes(1PB)", bibyte(PiByte), "1.0PiB"},
|
||||||
|
{"bytes(1PB - 1T)", bibyte(EiByte - PiByte), "1023PiB"},
|
||||||
|
|
||||||
|
{"bytes(1EiB)", bibyte(EiByte), "1.0EiB"},
|
||||||
|
// Overflows.
|
||||||
|
// {"bytes(1EB - 1P)", bibyte((KIByte*EIByte)-PiByte), "1023EB"},
|
||||||
|
|
||||||
|
{"bytes(5.5GiB)", bibyte(5.5 * GiByte), "5.5GiB"},
|
||||||
|
|
||||||
|
{"bytes(5.5GB)", bbyte(5.5 * GByte), "5.5GB"},
|
||||||
|
}.validate(t)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestVeryBigBytes(t *testing.T) {
|
||||||
|
b, _ := (&big.Int{}).SetString("15347691069326346944512", 10)
|
||||||
|
s := BigBytes(b)
|
||||||
|
if s != "15ZB" {
|
||||||
|
t.Errorf("Expected 15ZB, got %v", s)
|
||||||
|
}
|
||||||
|
s = BigIBytes(b)
|
||||||
|
if s != "13ZiB" {
|
||||||
|
t.Errorf("Expected 13ZiB, got %v", s)
|
||||||
|
}
|
||||||
|
|
||||||
|
b, _ = (&big.Int{}).SetString("15716035654990179271180288", 10)
|
||||||
|
s = BigBytes(b)
|
||||||
|
if s != "16YB" {
|
||||||
|
t.Errorf("Expected 16YB, got %v", s)
|
||||||
|
}
|
||||||
|
s = BigIBytes(b)
|
||||||
|
if s != "13YiB" {
|
||||||
|
t.Errorf("Expected 13YiB, got %v", s)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestVeryVeryBigBytes(t *testing.T) {
|
||||||
|
b, _ := (&big.Int{}).SetString("16093220510709943573688614912", 10)
|
||||||
|
s := BigBytes(b)
|
||||||
|
if s != "16093YB" {
|
||||||
|
t.Errorf("Expected 16093YB, got %v", s)
|
||||||
|
}
|
||||||
|
s = BigIBytes(b)
|
||||||
|
if s != "13312YiB" {
|
||||||
|
t.Errorf("Expected 13312YiB, got %v", s)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestParseVeryBig(t *testing.T) {
|
||||||
|
tests := []struct {
|
||||||
|
in string
|
||||||
|
out string
|
||||||
|
}{
|
||||||
|
{"16ZB", "16000000000000000000000"},
|
||||||
|
{"16ZiB", "18889465931478580854784"},
|
||||||
|
{"16.5ZB", "16500000000000000000000"},
|
||||||
|
{"16.5ZiB", "19479761741837286506496"},
|
||||||
|
{"16Z", "16000000000000000000000"},
|
||||||
|
{"16Zi", "18889465931478580854784"},
|
||||||
|
{"16.5Z", "16500000000000000000000"},
|
||||||
|
{"16.5Zi", "19479761741837286506496"},
|
||||||
|
|
||||||
|
{"16YB", "16000000000000000000000000"},
|
||||||
|
{"16YiB", "19342813113834066795298816"},
|
||||||
|
{"16.5YB", "16500000000000000000000000"},
|
||||||
|
{"16.5YiB", "19947276023641381382651904"},
|
||||||
|
{"16Y", "16000000000000000000000000"},
|
||||||
|
{"16Yi", "19342813113834066795298816"},
|
||||||
|
{"16.5Y", "16500000000000000000000000"},
|
||||||
|
{"16.5Yi", "19947276023641381382651904"},
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, test := range tests {
|
||||||
|
x, err := ParseBigBytes(test.in)
|
||||||
|
if err != nil {
|
||||||
|
t.Errorf("Error parsing %q: %v", test.in, err)
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
if x.String() != test.out {
|
||||||
|
t.Errorf("Expected %q for %q, got %v", test.out, test.in, x)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func BenchmarkParseBigBytes(b *testing.B) {
|
||||||
|
for i := 0; i < b.N; i++ {
|
||||||
|
ParseBigBytes("16.5Z")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func BenchmarkBigBytes(b *testing.B) {
|
||||||
|
for i := 0; i < b.N; i++ {
|
||||||
|
bibyte(16.5 * GByte)
|
||||||
|
}
|
||||||
|
}
|
134
Godeps/_workspace/src/github.com/dustin/go-humanize/bytes.go
generated
vendored
Normal file
134
Godeps/_workspace/src/github.com/dustin/go-humanize/bytes.go
generated
vendored
Normal file
@ -0,0 +1,134 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"math"
|
||||||
|
"strconv"
|
||||||
|
"strings"
|
||||||
|
"unicode"
|
||||||
|
)
|
||||||
|
|
||||||
|
// IEC Sizes.
|
||||||
|
// kibis of bits
|
||||||
|
const (
|
||||||
|
Byte = 1 << (iota * 10)
|
||||||
|
KiByte
|
||||||
|
MiByte
|
||||||
|
GiByte
|
||||||
|
TiByte
|
||||||
|
PiByte
|
||||||
|
EiByte
|
||||||
|
)
|
||||||
|
|
||||||
|
// SI Sizes.
|
||||||
|
const (
|
||||||
|
IByte = 1
|
||||||
|
KByte = IByte * 1000
|
||||||
|
MByte = KByte * 1000
|
||||||
|
GByte = MByte * 1000
|
||||||
|
TByte = GByte * 1000
|
||||||
|
PByte = TByte * 1000
|
||||||
|
EByte = PByte * 1000
|
||||||
|
)
|
||||||
|
|
||||||
|
var bytesSizeTable = map[string]uint64{
|
||||||
|
"b": Byte,
|
||||||
|
"kib": KiByte,
|
||||||
|
"kb": KByte,
|
||||||
|
"mib": MiByte,
|
||||||
|
"mb": MByte,
|
||||||
|
"gib": GiByte,
|
||||||
|
"gb": GByte,
|
||||||
|
"tib": TiByte,
|
||||||
|
"tb": TByte,
|
||||||
|
"pib": PiByte,
|
||||||
|
"pb": PByte,
|
||||||
|
"eib": EiByte,
|
||||||
|
"eb": EByte,
|
||||||
|
// Without suffix
|
||||||
|
"": Byte,
|
||||||
|
"ki": KiByte,
|
||||||
|
"k": KByte,
|
||||||
|
"mi": MiByte,
|
||||||
|
"m": MByte,
|
||||||
|
"gi": GiByte,
|
||||||
|
"g": GByte,
|
||||||
|
"ti": TiByte,
|
||||||
|
"t": TByte,
|
||||||
|
"pi": PiByte,
|
||||||
|
"p": PByte,
|
||||||
|
"ei": EiByte,
|
||||||
|
"e": EByte,
|
||||||
|
}
|
||||||
|
|
||||||
|
func logn(n, b float64) float64 {
|
||||||
|
return math.Log(n) / math.Log(b)
|
||||||
|
}
|
||||||
|
|
||||||
|
func humanateBytes(s uint64, base float64, sizes []string) string {
|
||||||
|
if s < 10 {
|
||||||
|
return fmt.Sprintf("%dB", s)
|
||||||
|
}
|
||||||
|
e := math.Floor(logn(float64(s), base))
|
||||||
|
suffix := sizes[int(e)]
|
||||||
|
val := math.Floor(float64(s)/math.Pow(base, e)*10+0.5) / 10
|
||||||
|
f := "%.0f%s"
|
||||||
|
if val < 10 {
|
||||||
|
f = "%.1f%s"
|
||||||
|
}
|
||||||
|
|
||||||
|
return fmt.Sprintf(f, val, suffix)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Bytes produces a human readable representation of an SI size.
|
||||||
|
//
|
||||||
|
// See also: ParseBytes.
|
||||||
|
//
|
||||||
|
// Bytes(82854982) -> 83MB
|
||||||
|
func Bytes(s uint64) string {
|
||||||
|
sizes := []string{"B", "KB", "MB", "GB", "TB", "PB", "EB"}
|
||||||
|
return humanateBytes(s, 1000, sizes)
|
||||||
|
}
|
||||||
|
|
||||||
|
// IBytes produces a human readable representation of an IEC size.
|
||||||
|
//
|
||||||
|
// See also: ParseBytes.
|
||||||
|
//
|
||||||
|
// IBytes(82854982) -> 79MiB
|
||||||
|
func IBytes(s uint64) string {
|
||||||
|
sizes := []string{"B", "KiB", "MiB", "GiB", "TiB", "PiB", "EiB"}
|
||||||
|
return humanateBytes(s, 1024, sizes)
|
||||||
|
}
|
||||||
|
|
||||||
|
// ParseBytes parses a string representation of bytes into the number
|
||||||
|
// of bytes it represents.
|
||||||
|
//
|
||||||
|
// See Also: Bytes, IBytes.
|
||||||
|
//
|
||||||
|
// ParseBytes("42MB") -> 42000000, nil
|
||||||
|
// ParseBytes("42mib") -> 44040192, nil
|
||||||
|
func ParseBytes(s string) (uint64, error) {
|
||||||
|
lastDigit := 0
|
||||||
|
for _, r := range s {
|
||||||
|
if !(unicode.IsDigit(r) || r == '.') {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
lastDigit++
|
||||||
|
}
|
||||||
|
|
||||||
|
f, err := strconv.ParseFloat(s[:lastDigit], 64)
|
||||||
|
if err != nil {
|
||||||
|
return 0, err
|
||||||
|
}
|
||||||
|
|
||||||
|
extra := strings.ToLower(strings.TrimSpace(s[lastDigit:]))
|
||||||
|
if m, ok := bytesSizeTable[extra]; ok {
|
||||||
|
f *= float64(m)
|
||||||
|
if f >= math.MaxUint64 {
|
||||||
|
return 0, fmt.Errorf("too large: %v", s)
|
||||||
|
}
|
||||||
|
return uint64(f), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0, fmt.Errorf("unhandled size name: %v", extra)
|
||||||
|
}
|
144
Godeps/_workspace/src/github.com/dustin/go-humanize/bytes_test.go
generated
vendored
Normal file
144
Godeps/_workspace/src/github.com/dustin/go-humanize/bytes_test.go
generated
vendored
Normal file
@ -0,0 +1,144 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestByteParsing(t *testing.T) {
|
||||||
|
tests := []struct {
|
||||||
|
in string
|
||||||
|
exp uint64
|
||||||
|
}{
|
||||||
|
{"42", 42},
|
||||||
|
{"42MB", 42000000},
|
||||||
|
{"42MiB", 44040192},
|
||||||
|
{"42mb", 42000000},
|
||||||
|
{"42mib", 44040192},
|
||||||
|
{"42MIB", 44040192},
|
||||||
|
{"42 MB", 42000000},
|
||||||
|
{"42 MiB", 44040192},
|
||||||
|
{"42 mb", 42000000},
|
||||||
|
{"42 mib", 44040192},
|
||||||
|
{"42 MIB", 44040192},
|
||||||
|
{"42.5MB", 42500000},
|
||||||
|
{"42.5MiB", 44564480},
|
||||||
|
{"42.5 MB", 42500000},
|
||||||
|
{"42.5 MiB", 44564480},
|
||||||
|
// No need to say B
|
||||||
|
{"42M", 42000000},
|
||||||
|
{"42Mi", 44040192},
|
||||||
|
{"42m", 42000000},
|
||||||
|
{"42mi", 44040192},
|
||||||
|
{"42MI", 44040192},
|
||||||
|
{"42 M", 42000000},
|
||||||
|
{"42 Mi", 44040192},
|
||||||
|
{"42 m", 42000000},
|
||||||
|
{"42 mi", 44040192},
|
||||||
|
{"42 MI", 44040192},
|
||||||
|
{"42.5M", 42500000},
|
||||||
|
{"42.5Mi", 44564480},
|
||||||
|
{"42.5 M", 42500000},
|
||||||
|
{"42.5 Mi", 44564480},
|
||||||
|
// Large testing, breaks when too much larger than
|
||||||
|
// this.
|
||||||
|
{"12.5 EB", uint64(12.5 * float64(EByte))},
|
||||||
|
{"12.5 E", uint64(12.5 * float64(EByte))},
|
||||||
|
{"12.5 EiB", uint64(12.5 * float64(EiByte))},
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, p := range tests {
|
||||||
|
got, err := ParseBytes(p.in)
|
||||||
|
if err != nil {
|
||||||
|
t.Errorf("Couldn't parse %v: %v", p.in, err)
|
||||||
|
}
|
||||||
|
if got != p.exp {
|
||||||
|
t.Errorf("Expected %v for %v, got %v",
|
||||||
|
p.exp, p.in, got)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestByteErrors(t *testing.T) {
|
||||||
|
got, err := ParseBytes("84 JB")
|
||||||
|
if err == nil {
|
||||||
|
t.Errorf("Expected error, got %v", got)
|
||||||
|
}
|
||||||
|
got, err = ParseBytes("")
|
||||||
|
if err == nil {
|
||||||
|
t.Errorf("Expected error parsing nothing")
|
||||||
|
}
|
||||||
|
got, err = ParseBytes("16 EiB")
|
||||||
|
if err == nil {
|
||||||
|
t.Errorf("Expected error, got %v", got)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestBytes(t *testing.T) {
|
||||||
|
testList{
|
||||||
|
{"bytes(0)", Bytes(0), "0B"},
|
||||||
|
{"bytes(1)", Bytes(1), "1B"},
|
||||||
|
{"bytes(803)", Bytes(803), "803B"},
|
||||||
|
{"bytes(999)", Bytes(999), "999B"},
|
||||||
|
|
||||||
|
{"bytes(1024)", Bytes(1024), "1.0KB"},
|
||||||
|
{"bytes(9999)", Bytes(9999), "10KB"},
|
||||||
|
{"bytes(1MB - 1)", Bytes(MByte - Byte), "1000KB"},
|
||||||
|
|
||||||
|
{"bytes(1MB)", Bytes(1024 * 1024), "1.0MB"},
|
||||||
|
{"bytes(1GB - 1K)", Bytes(GByte - KByte), "1000MB"},
|
||||||
|
|
||||||
|
{"bytes(1GB)", Bytes(GByte), "1.0GB"},
|
||||||
|
{"bytes(1TB - 1M)", Bytes(TByte - MByte), "1000GB"},
|
||||||
|
{"bytes(10MB)", Bytes(9999 * 1000), "10MB"},
|
||||||
|
|
||||||
|
{"bytes(1TB)", Bytes(TByte), "1.0TB"},
|
||||||
|
{"bytes(1PB - 1T)", Bytes(PByte - TByte), "999TB"},
|
||||||
|
|
||||||
|
{"bytes(1PB)", Bytes(PByte), "1.0PB"},
|
||||||
|
{"bytes(1PB - 1T)", Bytes(EByte - PByte), "999PB"},
|
||||||
|
|
||||||
|
{"bytes(1EB)", Bytes(EByte), "1.0EB"},
|
||||||
|
// Overflows.
|
||||||
|
// {"bytes(1EB - 1P)", Bytes((KByte*EByte)-PByte), "1023EB"},
|
||||||
|
|
||||||
|
{"bytes(0)", IBytes(0), "0B"},
|
||||||
|
{"bytes(1)", IBytes(1), "1B"},
|
||||||
|
{"bytes(803)", IBytes(803), "803B"},
|
||||||
|
{"bytes(1023)", IBytes(1023), "1023B"},
|
||||||
|
|
||||||
|
{"bytes(1024)", IBytes(1024), "1.0KiB"},
|
||||||
|
{"bytes(1MB - 1)", IBytes(MiByte - IByte), "1024KiB"},
|
||||||
|
|
||||||
|
{"bytes(1MB)", IBytes(1024 * 1024), "1.0MiB"},
|
||||||
|
{"bytes(1GB - 1K)", IBytes(GiByte - KiByte), "1024MiB"},
|
||||||
|
|
||||||
|
{"bytes(1GB)", IBytes(GiByte), "1.0GiB"},
|
||||||
|
{"bytes(1TB - 1M)", IBytes(TiByte - MiByte), "1024GiB"},
|
||||||
|
|
||||||
|
{"bytes(1TB)", IBytes(TiByte), "1.0TiB"},
|
||||||
|
{"bytes(1PB - 1T)", IBytes(PiByte - TiByte), "1023TiB"},
|
||||||
|
|
||||||
|
{"bytes(1PB)", IBytes(PiByte), "1.0PiB"},
|
||||||
|
{"bytes(1PB - 1T)", IBytes(EiByte - PiByte), "1023PiB"},
|
||||||
|
|
||||||
|
{"bytes(1EiB)", IBytes(EiByte), "1.0EiB"},
|
||||||
|
// Overflows.
|
||||||
|
// {"bytes(1EB - 1P)", IBytes((KIByte*EIByte)-PiByte), "1023EB"},
|
||||||
|
|
||||||
|
{"bytes(5.5GiB)", IBytes(5.5 * GiByte), "5.5GiB"},
|
||||||
|
|
||||||
|
{"bytes(5.5GB)", Bytes(5.5 * GByte), "5.5GB"},
|
||||||
|
}.validate(t)
|
||||||
|
}
|
||||||
|
|
||||||
|
func BenchmarkParseBytes(b *testing.B) {
|
||||||
|
for i := 0; i < b.N; i++ {
|
||||||
|
ParseBytes("16.5GB")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func BenchmarkBytes(b *testing.B) {
|
||||||
|
for i := 0; i < b.N; i++ {
|
||||||
|
Bytes(16.5 * GByte)
|
||||||
|
}
|
||||||
|
}
|
101
Godeps/_workspace/src/github.com/dustin/go-humanize/comma.go
generated
vendored
Normal file
101
Godeps/_workspace/src/github.com/dustin/go-humanize/comma.go
generated
vendored
Normal file
@ -0,0 +1,101 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bytes"
|
||||||
|
"math/big"
|
||||||
|
"strconv"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Comma produces a string form of the given number in base 10 with
|
||||||
|
// commas after every three orders of magnitude.
|
||||||
|
//
|
||||||
|
// e.g. Comma(834142) -> 834,142
|
||||||
|
func Comma(v int64) string {
|
||||||
|
sign := ""
|
||||||
|
if v < 0 {
|
||||||
|
sign = "-"
|
||||||
|
v = 0 - v
|
||||||
|
}
|
||||||
|
|
||||||
|
parts := []string{"", "", "", "", "", "", "", ""}
|
||||||
|
j := len(parts) - 1
|
||||||
|
|
||||||
|
for v > 999 {
|
||||||
|
parts[j] = strconv.FormatInt(v%1000, 10)
|
||||||
|
switch len(parts[j]) {
|
||||||
|
case 2:
|
||||||
|
parts[j] = "0" + parts[j]
|
||||||
|
case 1:
|
||||||
|
parts[j] = "00" + parts[j]
|
||||||
|
}
|
||||||
|
v = v / 1000
|
||||||
|
j--
|
||||||
|
}
|
||||||
|
parts[j] = strconv.Itoa(int(v))
|
||||||
|
return sign + strings.Join(parts[j:len(parts)], ",")
|
||||||
|
}
|
||||||
|
|
||||||
|
// Commaf produces a string form of the given number in base 10 with
|
||||||
|
// commas after every three orders of magnitude.
|
||||||
|
//
|
||||||
|
// e.g. Comma(834142.32) -> 834,142.32
|
||||||
|
func Commaf(v float64) string {
|
||||||
|
buf := &bytes.Buffer{}
|
||||||
|
if v < 0 {
|
||||||
|
buf.Write([]byte{'-'})
|
||||||
|
v = 0 - v
|
||||||
|
}
|
||||||
|
|
||||||
|
comma := []byte{','}
|
||||||
|
|
||||||
|
parts := strings.Split(strconv.FormatFloat(v, 'f', -1, 64), ".")
|
||||||
|
pos := 0
|
||||||
|
if len(parts[0])%3 != 0 {
|
||||||
|
pos += len(parts[0]) % 3
|
||||||
|
buf.WriteString(parts[0][:pos])
|
||||||
|
buf.Write(comma)
|
||||||
|
}
|
||||||
|
for ; pos < len(parts[0]); pos += 3 {
|
||||||
|
buf.WriteString(parts[0][pos : pos+3])
|
||||||
|
buf.Write(comma)
|
||||||
|
}
|
||||||
|
buf.Truncate(buf.Len() - 1)
|
||||||
|
|
||||||
|
if len(parts) > 1 {
|
||||||
|
buf.Write([]byte{'.'})
|
||||||
|
buf.WriteString(parts[1])
|
||||||
|
}
|
||||||
|
return buf.String()
|
||||||
|
}
|
||||||
|
|
||||||
|
// BigComma produces a string form of the given big.Int in base 10
|
||||||
|
// with commas after every three orders of magnitude.
|
||||||
|
func BigComma(b *big.Int) string {
|
||||||
|
sign := ""
|
||||||
|
if b.Sign() < 0 {
|
||||||
|
sign = "-"
|
||||||
|
b.Abs(b)
|
||||||
|
}
|
||||||
|
|
||||||
|
athousand := big.NewInt(1000)
|
||||||
|
c := (&big.Int{}).Set(b)
|
||||||
|
_, m := oom(c, athousand)
|
||||||
|
parts := make([]string, m+1)
|
||||||
|
j := len(parts) - 1
|
||||||
|
|
||||||
|
mod := &big.Int{}
|
||||||
|
for b.Cmp(athousand) >= 0 {
|
||||||
|
b.DivMod(b, athousand, mod)
|
||||||
|
parts[j] = strconv.FormatInt(mod.Int64(), 10)
|
||||||
|
switch len(parts[j]) {
|
||||||
|
case 2:
|
||||||
|
parts[j] = "0" + parts[j]
|
||||||
|
case 1:
|
||||||
|
parts[j] = "00" + parts[j]
|
||||||
|
}
|
||||||
|
j--
|
||||||
|
}
|
||||||
|
parts[j] = strconv.Itoa(int(b.Int64()))
|
||||||
|
return sign + strings.Join(parts[j:len(parts)], ",")
|
||||||
|
}
|
134
Godeps/_workspace/src/github.com/dustin/go-humanize/comma_test.go
generated
vendored
Normal file
134
Godeps/_workspace/src/github.com/dustin/go-humanize/comma_test.go
generated
vendored
Normal file
@ -0,0 +1,134 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"math"
|
||||||
|
"math/big"
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestCommas(t *testing.T) {
|
||||||
|
testList{
|
||||||
|
{"0", Comma(0), "0"},
|
||||||
|
{"10", Comma(10), "10"},
|
||||||
|
{"100", Comma(100), "100"},
|
||||||
|
{"1,000", Comma(1000), "1,000"},
|
||||||
|
{"10,000", Comma(10000), "10,000"},
|
||||||
|
{"100,000", Comma(100000), "100,000"},
|
||||||
|
{"10,000,000", Comma(10000000), "10,000,000"},
|
||||||
|
{"10,100,000", Comma(10100000), "10,100,000"},
|
||||||
|
{"10,010,000", Comma(10010000), "10,010,000"},
|
||||||
|
{"10,001,000", Comma(10001000), "10,001,000"},
|
||||||
|
{"123,456,789", Comma(123456789), "123,456,789"},
|
||||||
|
{"maxint", Comma(9.223372e+18), "9,223,372,000,000,000,000"},
|
||||||
|
{"minint", Comma(-9.223372e+18), "-9,223,372,000,000,000,000"},
|
||||||
|
{"-123,456,789", Comma(-123456789), "-123,456,789"},
|
||||||
|
{"-10,100,000", Comma(-10100000), "-10,100,000"},
|
||||||
|
{"-10,010,000", Comma(-10010000), "-10,010,000"},
|
||||||
|
{"-10,001,000", Comma(-10001000), "-10,001,000"},
|
||||||
|
{"-10,000,000", Comma(-10000000), "-10,000,000"},
|
||||||
|
{"-100,000", Comma(-100000), "-100,000"},
|
||||||
|
{"-10,000", Comma(-10000), "-10,000"},
|
||||||
|
{"-1,000", Comma(-1000), "-1,000"},
|
||||||
|
{"-100", Comma(-100), "-100"},
|
||||||
|
{"-10", Comma(-10), "-10"},
|
||||||
|
}.validate(t)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestCommafs(t *testing.T) {
|
||||||
|
testList{
|
||||||
|
{"0", Commaf(0), "0"},
|
||||||
|
{"10.11", Commaf(10.11), "10.11"},
|
||||||
|
{"100", Commaf(100), "100"},
|
||||||
|
{"1,000", Commaf(1000), "1,000"},
|
||||||
|
{"10,000", Commaf(10000), "10,000"},
|
||||||
|
{"100,000", Commaf(100000), "100,000"},
|
||||||
|
{"834,142.32", Commaf(834142.32), "834,142.32"},
|
||||||
|
{"10,000,000", Commaf(10000000), "10,000,000"},
|
||||||
|
{"10,100,000", Commaf(10100000), "10,100,000"},
|
||||||
|
{"10,010,000", Commaf(10010000), "10,010,000"},
|
||||||
|
{"10,001,000", Commaf(10001000), "10,001,000"},
|
||||||
|
{"123,456,789", Commaf(123456789), "123,456,789"},
|
||||||
|
{"maxf64", Commaf(math.MaxFloat64), "179,769,313,486,231,570,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000,000"},
|
||||||
|
{"minf64", Commaf(math.SmallestNonzeroFloat64), "0.000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000005"},
|
||||||
|
{"-123,456,789", Commaf(-123456789), "-123,456,789"},
|
||||||
|
{"-10,100,000", Commaf(-10100000), "-10,100,000"},
|
||||||
|
{"-10,010,000", Commaf(-10010000), "-10,010,000"},
|
||||||
|
{"-10,001,000", Commaf(-10001000), "-10,001,000"},
|
||||||
|
{"-10,000,000", Commaf(-10000000), "-10,000,000"},
|
||||||
|
{"-100,000", Commaf(-100000), "-100,000"},
|
||||||
|
{"-10,000", Commaf(-10000), "-10,000"},
|
||||||
|
{"-1,000", Commaf(-1000), "-1,000"},
|
||||||
|
{"-100.11", Commaf(-100.11), "-100.11"},
|
||||||
|
{"-10", Commaf(-10), "-10"},
|
||||||
|
}.validate(t)
|
||||||
|
}
|
||||||
|
|
||||||
|
func BenchmarkCommas(b *testing.B) {
|
||||||
|
for i := 0; i < b.N; i++ {
|
||||||
|
Comma(1234567890)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func BenchmarkCommaf(b *testing.B) {
|
||||||
|
for i := 0; i < b.N; i++ {
|
||||||
|
Commaf(1234567890.83584)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func BenchmarkBigCommas(b *testing.B) {
|
||||||
|
for i := 0; i < b.N; i++ {
|
||||||
|
BigComma(big.NewInt(1234567890))
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func bigComma(i int64) string {
|
||||||
|
return BigComma(big.NewInt(i))
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestBigCommas(t *testing.T) {
|
||||||
|
testList{
|
||||||
|
{"0", bigComma(0), "0"},
|
||||||
|
{"10", bigComma(10), "10"},
|
||||||
|
{"100", bigComma(100), "100"},
|
||||||
|
{"1,000", bigComma(1000), "1,000"},
|
||||||
|
{"10,000", bigComma(10000), "10,000"},
|
||||||
|
{"100,000", bigComma(100000), "100,000"},
|
||||||
|
{"10,000,000", bigComma(10000000), "10,000,000"},
|
||||||
|
{"10,100,000", bigComma(10100000), "10,100,000"},
|
||||||
|
{"10,010,000", bigComma(10010000), "10,010,000"},
|
||||||
|
{"10,001,000", bigComma(10001000), "10,001,000"},
|
||||||
|
{"123,456,789", bigComma(123456789), "123,456,789"},
|
||||||
|
{"maxint", bigComma(9.223372e+18), "9,223,372,000,000,000,000"},
|
||||||
|
{"minint", bigComma(-9.223372e+18), "-9,223,372,000,000,000,000"},
|
||||||
|
{"-123,456,789", bigComma(-123456789), "-123,456,789"},
|
||||||
|
{"-10,100,000", bigComma(-10100000), "-10,100,000"},
|
||||||
|
{"-10,010,000", bigComma(-10010000), "-10,010,000"},
|
||||||
|
{"-10,001,000", bigComma(-10001000), "-10,001,000"},
|
||||||
|
{"-10,000,000", bigComma(-10000000), "-10,000,000"},
|
||||||
|
{"-100,000", bigComma(-100000), "-100,000"},
|
||||||
|
{"-10,000", bigComma(-10000), "-10,000"},
|
||||||
|
{"-1,000", bigComma(-1000), "-1,000"},
|
||||||
|
{"-100", bigComma(-100), "-100"},
|
||||||
|
{"-10", bigComma(-10), "-10"},
|
||||||
|
}.validate(t)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestVeryBigCommas(t *testing.T) {
|
||||||
|
tests := []struct{ in, exp string }{
|
||||||
|
{
|
||||||
|
"84889279597249724975972597249849757294578485",
|
||||||
|
"84,889,279,597,249,724,975,972,597,249,849,757,294,578,485",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"-84889279597249724975972597249849757294578485",
|
||||||
|
"-84,889,279,597,249,724,975,972,597,249,849,757,294,578,485",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
for _, test := range tests {
|
||||||
|
n, _ := (&big.Int{}).SetString(test.in, 10)
|
||||||
|
got := BigComma(n)
|
||||||
|
if test.exp != got {
|
||||||
|
t.Errorf("Expected %q, got %q", test.exp, got)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
18
Godeps/_workspace/src/github.com/dustin/go-humanize/common_test.go
generated
vendored
Normal file
18
Godeps/_workspace/src/github.com/dustin/go-humanize/common_test.go
generated
vendored
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
type testList []struct {
|
||||||
|
name, got, exp string
|
||||||
|
}
|
||||||
|
|
||||||
|
func (tl testList) validate(t *testing.T) {
|
||||||
|
for _, test := range tl {
|
||||||
|
if test.got != test.exp {
|
||||||
|
t.Errorf("On %v, expected '%v', but got '%v'",
|
||||||
|
test.name, test.exp, test.got)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
23
Godeps/_workspace/src/github.com/dustin/go-humanize/ftoa.go
generated
vendored
Normal file
23
Godeps/_workspace/src/github.com/dustin/go-humanize/ftoa.go
generated
vendored
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import "strconv"
|
||||||
|
|
||||||
|
func stripTrailingZeros(s string) string {
|
||||||
|
offset := len(s) - 1
|
||||||
|
for offset > 0 {
|
||||||
|
if s[offset] == '.' {
|
||||||
|
offset--
|
||||||
|
break
|
||||||
|
}
|
||||||
|
if s[offset] != '0' {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
offset--
|
||||||
|
}
|
||||||
|
return s[:offset+1]
|
||||||
|
}
|
||||||
|
|
||||||
|
// Ftoa converts a float to a string with no trailing zeros.
|
||||||
|
func Ftoa(num float64) string {
|
||||||
|
return stripTrailingZeros(strconv.FormatFloat(num, 'f', 6, 64))
|
||||||
|
}
|
55
Godeps/_workspace/src/github.com/dustin/go-humanize/ftoa_test.go
generated
vendored
Normal file
55
Godeps/_workspace/src/github.com/dustin/go-humanize/ftoa_test.go
generated
vendored
Normal file
@ -0,0 +1,55 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"regexp"
|
||||||
|
"strconv"
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestFtoa(t *testing.T) {
|
||||||
|
testList{
|
||||||
|
{"200", Ftoa(200), "200"},
|
||||||
|
{"2", Ftoa(2), "2"},
|
||||||
|
{"2.2", Ftoa(2.2), "2.2"},
|
||||||
|
{"2.02", Ftoa(2.02), "2.02"},
|
||||||
|
{"200.02", Ftoa(200.02), "200.02"},
|
||||||
|
}.validate(t)
|
||||||
|
}
|
||||||
|
|
||||||
|
func BenchmarkFtoaRegexTrailing(b *testing.B) {
|
||||||
|
trailingZerosRegex := regexp.MustCompile(`\.?0+$`)
|
||||||
|
|
||||||
|
b.ResetTimer()
|
||||||
|
for i := 0; i < b.N; i++ {
|
||||||
|
trailingZerosRegex.ReplaceAllString("2.00000", "")
|
||||||
|
trailingZerosRegex.ReplaceAllString("2.0000", "")
|
||||||
|
trailingZerosRegex.ReplaceAllString("2.000", "")
|
||||||
|
trailingZerosRegex.ReplaceAllString("2.00", "")
|
||||||
|
trailingZerosRegex.ReplaceAllString("2.0", "")
|
||||||
|
trailingZerosRegex.ReplaceAllString("2", "")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func BenchmarkFtoaFunc(b *testing.B) {
|
||||||
|
for i := 0; i < b.N; i++ {
|
||||||
|
stripTrailingZeros("2.00000")
|
||||||
|
stripTrailingZeros("2.0000")
|
||||||
|
stripTrailingZeros("2.000")
|
||||||
|
stripTrailingZeros("2.00")
|
||||||
|
stripTrailingZeros("2.0")
|
||||||
|
stripTrailingZeros("2")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func BenchmarkFmtF(b *testing.B) {
|
||||||
|
for i := 0; i < b.N; i++ {
|
||||||
|
fmt.Sprintf("%f", 2.03584)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func BenchmarkStrconvF(b *testing.B) {
|
||||||
|
for i := 0; i < b.N; i++ {
|
||||||
|
strconv.FormatFloat(2.03584, 'f', 6, 64)
|
||||||
|
}
|
||||||
|
}
|
8
Godeps/_workspace/src/github.com/dustin/go-humanize/humanize.go
generated
vendored
Normal file
8
Godeps/_workspace/src/github.com/dustin/go-humanize/humanize.go
generated
vendored
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
/*
|
||||||
|
Package humanize converts boring ugly numbers to human-friendly strings and back.
|
||||||
|
|
||||||
|
Durations can be turned into strings such as "3 days ago", numbers
|
||||||
|
representing sizes like 82854982 into useful strings like, "83MB" or
|
||||||
|
"79MiB" (whichever you prefer).
|
||||||
|
*/
|
||||||
|
package humanize
|
25
Godeps/_workspace/src/github.com/dustin/go-humanize/ordinals.go
generated
vendored
Normal file
25
Godeps/_workspace/src/github.com/dustin/go-humanize/ordinals.go
generated
vendored
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import "strconv"
|
||||||
|
|
||||||
|
// Ordinal gives you the input number in a rank/ordinal format.
|
||||||
|
//
|
||||||
|
// Ordinal(3) -> 3rd
|
||||||
|
func Ordinal(x int) string {
|
||||||
|
suffix := "th"
|
||||||
|
switch x % 10 {
|
||||||
|
case 1:
|
||||||
|
if x%100 != 11 {
|
||||||
|
suffix = "st"
|
||||||
|
}
|
||||||
|
case 2:
|
||||||
|
if x%100 != 12 {
|
||||||
|
suffix = "nd"
|
||||||
|
}
|
||||||
|
case 3:
|
||||||
|
if x%100 != 13 {
|
||||||
|
suffix = "rd"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return strconv.Itoa(x) + suffix
|
||||||
|
}
|
22
Godeps/_workspace/src/github.com/dustin/go-humanize/ordinals_test.go
generated
vendored
Normal file
22
Godeps/_workspace/src/github.com/dustin/go-humanize/ordinals_test.go
generated
vendored
Normal file
@ -0,0 +1,22 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestOrdinals(t *testing.T) {
|
||||||
|
testList{
|
||||||
|
{"0", Ordinal(0), "0th"},
|
||||||
|
{"1", Ordinal(1), "1st"},
|
||||||
|
{"2", Ordinal(2), "2nd"},
|
||||||
|
{"3", Ordinal(3), "3rd"},
|
||||||
|
{"4", Ordinal(4), "4th"},
|
||||||
|
{"10", Ordinal(10), "10th"},
|
||||||
|
{"11", Ordinal(11), "11th"},
|
||||||
|
{"12", Ordinal(12), "12th"},
|
||||||
|
{"13", Ordinal(13), "13th"},
|
||||||
|
{"101", Ordinal(101), "101st"},
|
||||||
|
{"102", Ordinal(102), "102nd"},
|
||||||
|
{"103", Ordinal(103), "103rd"},
|
||||||
|
}.validate(t)
|
||||||
|
}
|
110
Godeps/_workspace/src/github.com/dustin/go-humanize/si.go
generated
vendored
Normal file
110
Godeps/_workspace/src/github.com/dustin/go-humanize/si.go
generated
vendored
Normal file
@ -0,0 +1,110 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
"math"
|
||||||
|
"regexp"
|
||||||
|
"strconv"
|
||||||
|
)
|
||||||
|
|
||||||
|
var siPrefixTable = map[float64]string{
|
||||||
|
-24: "y", // yocto
|
||||||
|
-21: "z", // zepto
|
||||||
|
-18: "a", // atto
|
||||||
|
-15: "f", // femto
|
||||||
|
-12: "p", // pico
|
||||||
|
-9: "n", // nano
|
||||||
|
-6: "µ", // micro
|
||||||
|
-3: "m", // milli
|
||||||
|
0: "",
|
||||||
|
3: "k", // kilo
|
||||||
|
6: "M", // mega
|
||||||
|
9: "G", // giga
|
||||||
|
12: "T", // tera
|
||||||
|
15: "P", // peta
|
||||||
|
18: "E", // exa
|
||||||
|
21: "Z", // zetta
|
||||||
|
24: "Y", // yotta
|
||||||
|
}
|
||||||
|
|
||||||
|
var revSIPrefixTable = revfmap(siPrefixTable)
|
||||||
|
|
||||||
|
// revfmap reverses the map and precomputes the power multiplier
|
||||||
|
func revfmap(in map[float64]string) map[string]float64 {
|
||||||
|
rv := map[string]float64{}
|
||||||
|
for k, v := range in {
|
||||||
|
rv[v] = math.Pow(10, k)
|
||||||
|
}
|
||||||
|
return rv
|
||||||
|
}
|
||||||
|
|
||||||
|
var riParseRegex *regexp.Regexp
|
||||||
|
|
||||||
|
func init() {
|
||||||
|
ri := `^([0-9.]+)([`
|
||||||
|
for _, v := range siPrefixTable {
|
||||||
|
ri += v
|
||||||
|
}
|
||||||
|
ri += `]?)(.*)`
|
||||||
|
|
||||||
|
riParseRegex = regexp.MustCompile(ri)
|
||||||
|
}
|
||||||
|
|
||||||
|
// ComputeSI finds the most appropriate SI prefix for the given number
|
||||||
|
// and returns the prefix along with the value adjusted to be within
|
||||||
|
// that prefix.
|
||||||
|
//
|
||||||
|
// See also: SI, ParseSI.
|
||||||
|
//
|
||||||
|
// e.g. ComputeSI(2.2345e-12) -> (2.2345, "p")
|
||||||
|
func ComputeSI(input float64) (float64, string) {
|
||||||
|
if input == 0 {
|
||||||
|
return 0, ""
|
||||||
|
}
|
||||||
|
exponent := math.Floor(logn(input, 10))
|
||||||
|
exponent = math.Floor(exponent/3) * 3
|
||||||
|
|
||||||
|
value := input / math.Pow(10, exponent)
|
||||||
|
|
||||||
|
// Handle special case where value is exactly 1000.0
|
||||||
|
// Should return 1M instead of 1000k
|
||||||
|
if value == 1000.0 {
|
||||||
|
exponent += 3
|
||||||
|
value = input / math.Pow(10, exponent)
|
||||||
|
}
|
||||||
|
|
||||||
|
prefix := siPrefixTable[exponent]
|
||||||
|
return value, prefix
|
||||||
|
}
|
||||||
|
|
||||||
|
// SI returns a string with default formatting.
|
||||||
|
//
|
||||||
|
// SI uses Ftoa to format float value, removing trailing zeros.
|
||||||
|
//
|
||||||
|
// See also: ComputeSI, ParseSI.
|
||||||
|
//
|
||||||
|
// e.g. SI(1000000, B) -> 1MB
|
||||||
|
// e.g. SI(2.2345e-12, "F") -> 2.2345pF
|
||||||
|
func SI(input float64, unit string) string {
|
||||||
|
value, prefix := ComputeSI(input)
|
||||||
|
return Ftoa(value) + prefix + unit
|
||||||
|
}
|
||||||
|
|
||||||
|
var errInvalid = errors.New("invalid input")
|
||||||
|
|
||||||
|
// ParseSI parses an SI string back into the number and unit.
|
||||||
|
//
|
||||||
|
// See also: SI, ComputeSI.
|
||||||
|
//
|
||||||
|
// e.g. ParseSI(2.2345pF) -> (2.2345e-12, "F", nil)
|
||||||
|
func ParseSI(input string) (float64, string, error) {
|
||||||
|
found := riParseRegex.FindStringSubmatch(input)
|
||||||
|
if len(found) != 4 {
|
||||||
|
return 0, "", errInvalid
|
||||||
|
}
|
||||||
|
mag := revSIPrefixTable[found[2]]
|
||||||
|
unit := found[3]
|
||||||
|
|
||||||
|
base, err := strconv.ParseFloat(found[1], 64)
|
||||||
|
return base * mag, unit, err
|
||||||
|
}
|
98
Godeps/_workspace/src/github.com/dustin/go-humanize/si_test.go
generated
vendored
Normal file
98
Godeps/_workspace/src/github.com/dustin/go-humanize/si_test.go
generated
vendored
Normal file
@ -0,0 +1,98 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"math"
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestSI(t *testing.T) {
|
||||||
|
tests := []struct {
|
||||||
|
name string
|
||||||
|
num float64
|
||||||
|
formatted string
|
||||||
|
}{
|
||||||
|
{"e-24", 1e-24, "1yF"},
|
||||||
|
{"e-21", 1e-21, "1zF"},
|
||||||
|
{"e-18", 1e-18, "1aF"},
|
||||||
|
{"e-15", 1e-15, "1fF"},
|
||||||
|
{"e-12", 1e-12, "1pF"},
|
||||||
|
{"e-12", 2.2345e-12, "2.2345pF"},
|
||||||
|
{"e-12", 2.23e-12, "2.23pF"},
|
||||||
|
{"e-11", 2.23e-11, "22.3pF"},
|
||||||
|
{"e-10", 2.2e-10, "220pF"},
|
||||||
|
{"e-9", 2.2e-9, "2.2nF"},
|
||||||
|
{"e-8", 2.2e-8, "22nF"},
|
||||||
|
{"e-7", 2.2e-7, "220nF"},
|
||||||
|
{"e-6", 2.2e-6, "2.2µF"},
|
||||||
|
{"e-6", 1e-6, "1µF"},
|
||||||
|
{"e-5", 2.2e-5, "22µF"},
|
||||||
|
{"e-4", 2.2e-4, "220µF"},
|
||||||
|
{"e-3", 2.2e-3, "2.2mF"},
|
||||||
|
{"e-2", 2.2e-2, "22mF"},
|
||||||
|
{"e-1", 2.2e-1, "220mF"},
|
||||||
|
{"e+0", 2.2e-0, "2.2F"},
|
||||||
|
{"e+0", 2.2, "2.2F"},
|
||||||
|
{"e+1", 2.2e+1, "22F"},
|
||||||
|
{"0", 0, "0F"},
|
||||||
|
{"e+1", 22, "22F"},
|
||||||
|
{"e+2", 2.2e+2, "220F"},
|
||||||
|
{"e+2", 220, "220F"},
|
||||||
|
{"e+3", 2.2e+3, "2.2kF"},
|
||||||
|
{"e+3", 2200, "2.2kF"},
|
||||||
|
{"e+4", 2.2e+4, "22kF"},
|
||||||
|
{"e+4", 22000, "22kF"},
|
||||||
|
{"e+5", 2.2e+5, "220kF"},
|
||||||
|
{"e+6", 2.2e+6, "2.2MF"},
|
||||||
|
{"e+6", 1e+6, "1MF"},
|
||||||
|
{"e+7", 2.2e+7, "22MF"},
|
||||||
|
{"e+8", 2.2e+8, "220MF"},
|
||||||
|
{"e+9", 2.2e+9, "2.2GF"},
|
||||||
|
{"e+10", 2.2e+10, "22GF"},
|
||||||
|
{"e+11", 2.2e+11, "220GF"},
|
||||||
|
{"e+12", 2.2e+12, "2.2TF"},
|
||||||
|
{"e+15", 2.2e+15, "2.2PF"},
|
||||||
|
{"e+18", 2.2e+18, "2.2EF"},
|
||||||
|
{"e+21", 2.2e+21, "2.2ZF"},
|
||||||
|
{"e+24", 2.2e+24, "2.2YF"},
|
||||||
|
|
||||||
|
// special case
|
||||||
|
{"1F", 1000 * 1000, "1MF"},
|
||||||
|
{"1F", 1e6, "1MF"},
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, test := range tests {
|
||||||
|
got := SI(test.num, "F")
|
||||||
|
if got != test.formatted {
|
||||||
|
t.Errorf("On %v (%v), got %v, wanted %v",
|
||||||
|
test.name, test.num, got, test.formatted)
|
||||||
|
}
|
||||||
|
|
||||||
|
gotf, gotu, err := ParseSI(test.formatted)
|
||||||
|
if err != nil {
|
||||||
|
t.Errorf("Error parsing %v (%v): %v", test.name, test.formatted, err)
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
if math.Abs(1-(gotf/test.num)) > 0.01 {
|
||||||
|
t.Errorf("On %v (%v), got %v, wanted %v (±%v)",
|
||||||
|
test.name, test.formatted, gotf, test.num,
|
||||||
|
math.Abs(1-(gotf/test.num)))
|
||||||
|
}
|
||||||
|
if gotu != "F" {
|
||||||
|
t.Errorf("On %v (%v), expected unit F, got %v",
|
||||||
|
test.name, test.formatted, gotu)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Parse error
|
||||||
|
gotf, gotu, err := ParseSI("x1.21JW") // 1.21 jigga whats
|
||||||
|
if err == nil {
|
||||||
|
t.Errorf("Expected error on x1.21JW, got %v %v", gotf, gotu)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func BenchmarkParseSI(b *testing.B) {
|
||||||
|
for i := 0; i < b.N; i++ {
|
||||||
|
ParseSI("2.2346ZB")
|
||||||
|
}
|
||||||
|
}
|
91
Godeps/_workspace/src/github.com/dustin/go-humanize/times.go
generated
vendored
Normal file
91
Godeps/_workspace/src/github.com/dustin/go-humanize/times.go
generated
vendored
Normal file
@ -0,0 +1,91 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"math"
|
||||||
|
"sort"
|
||||||
|
"time"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Seconds-based time units
|
||||||
|
const (
|
||||||
|
Minute = 60
|
||||||
|
Hour = 60 * Minute
|
||||||
|
Day = 24 * Hour
|
||||||
|
Week = 7 * Day
|
||||||
|
Month = 30 * Day
|
||||||
|
Year = 12 * Month
|
||||||
|
LongTime = 37 * Year
|
||||||
|
)
|
||||||
|
|
||||||
|
// Time formats a time into a relative string.
|
||||||
|
//
|
||||||
|
// Time(someT) -> "3 weeks ago"
|
||||||
|
func Time(then time.Time) string {
|
||||||
|
return RelTime(then, time.Now(), "ago", "from now")
|
||||||
|
}
|
||||||
|
|
||||||
|
var magnitudes = []struct {
|
||||||
|
d int64
|
||||||
|
format string
|
||||||
|
divby int64
|
||||||
|
}{
|
||||||
|
{1, "now", 1},
|
||||||
|
{2, "1 second %s", 1},
|
||||||
|
{Minute, "%d seconds %s", 1},
|
||||||
|
{2 * Minute, "1 minute %s", 1},
|
||||||
|
{Hour, "%d minutes %s", Minute},
|
||||||
|
{2 * Hour, "1 hour %s", 1},
|
||||||
|
{Day, "%d hours %s", Hour},
|
||||||
|
{2 * Day, "1 day %s", 1},
|
||||||
|
{Week, "%d days %s", Day},
|
||||||
|
{2 * Week, "1 week %s", 1},
|
||||||
|
{Month, "%d weeks %s", Week},
|
||||||
|
{2 * Month, "1 month %s", 1},
|
||||||
|
{Year, "%d months %s", Month},
|
||||||
|
{18 * Month, "1 year %s", 1},
|
||||||
|
{2 * Year, "2 years %s", 1},
|
||||||
|
{LongTime, "%d years %s", Year},
|
||||||
|
{math.MaxInt64, "a long while %s", 1},
|
||||||
|
}
|
||||||
|
|
||||||
|
// RelTime formats a time into a relative string.
|
||||||
|
//
|
||||||
|
// It takes two times and two labels. In addition to the generic time
|
||||||
|
// delta string (e.g. 5 minutes), the labels are used applied so that
|
||||||
|
// the label corresponding to the smaller time is applied.
|
||||||
|
//
|
||||||
|
// RelTime(timeInPast, timeInFuture, "earlier", "later") -> "3 weeks earlier"
|
||||||
|
func RelTime(a, b time.Time, albl, blbl string) string {
|
||||||
|
lbl := albl
|
||||||
|
diff := b.Unix() - a.Unix()
|
||||||
|
|
||||||
|
after := a.After(b)
|
||||||
|
if after {
|
||||||
|
lbl = blbl
|
||||||
|
diff = a.Unix() - b.Unix()
|
||||||
|
}
|
||||||
|
|
||||||
|
n := sort.Search(len(magnitudes), func(i int) bool {
|
||||||
|
return magnitudes[i].d > diff
|
||||||
|
})
|
||||||
|
|
||||||
|
mag := magnitudes[n]
|
||||||
|
args := []interface{}{}
|
||||||
|
escaped := false
|
||||||
|
for _, ch := range mag.format {
|
||||||
|
if escaped {
|
||||||
|
switch ch {
|
||||||
|
case '%':
|
||||||
|
case 's':
|
||||||
|
args = append(args, lbl)
|
||||||
|
case 'd':
|
||||||
|
args = append(args, diff/mag.divby)
|
||||||
|
}
|
||||||
|
escaped = false
|
||||||
|
} else {
|
||||||
|
escaped = ch == '%'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return fmt.Sprintf(mag.format, args...)
|
||||||
|
}
|
71
Godeps/_workspace/src/github.com/dustin/go-humanize/times_test.go
generated
vendored
Normal file
71
Godeps/_workspace/src/github.com/dustin/go-humanize/times_test.go
generated
vendored
Normal file
@ -0,0 +1,71 @@
|
|||||||
|
package humanize
|
||||||
|
|
||||||
|
import (
|
||||||
|
"math"
|
||||||
|
"testing"
|
||||||
|
"time"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestPast(t *testing.T) {
|
||||||
|
now := time.Now().Unix()
|
||||||
|
testList{
|
||||||
|
{"now", Time(time.Unix(now, 0)), "now"},
|
||||||
|
{"1 second ago", Time(time.Unix(now-1, 0)), "1 second ago"},
|
||||||
|
{"12 seconds ago", Time(time.Unix(now-12, 0)), "12 seconds ago"},
|
||||||
|
{"30 seconds ago", Time(time.Unix(now-30, 0)), "30 seconds ago"},
|
||||||
|
{"45 seconds ago", Time(time.Unix(now-45, 0)), "45 seconds ago"},
|
||||||
|
{"1 minute ago", Time(time.Unix(now-63, 0)), "1 minute ago"},
|
||||||
|
{"15 minutes ago", Time(time.Unix(now-15*Minute, 0)), "15 minutes ago"},
|
||||||
|
{"1 hour ago", Time(time.Unix(now-63*Minute, 0)), "1 hour ago"},
|
||||||
|
{"2 hours ago", Time(time.Unix(now-2*Hour, 0)), "2 hours ago"},
|
||||||
|
{"21 hours ago", Time(time.Unix(now-21*Hour, 0)), "21 hours ago"},
|
||||||
|
{"1 day ago", Time(time.Unix(now-26*Hour, 0)), "1 day ago"},
|
||||||
|
{"2 days ago", Time(time.Unix(now-49*Hour, 0)), "2 days ago"},
|
||||||
|
{"3 days ago", Time(time.Unix(now-3*Day, 0)), "3 days ago"},
|
||||||
|
{"1 week ago (1)", Time(time.Unix(now-7*Day, 0)), "1 week ago"},
|
||||||
|
{"1 week ago (2)", Time(time.Unix(now-12*Day, 0)), "1 week ago"},
|
||||||
|
{"2 weeks ago", Time(time.Unix(now-15*Day, 0)), "2 weeks ago"},
|
||||||
|
{"1 month ago", Time(time.Unix(now-39*Day, 0)), "1 month ago"},
|
||||||
|
{"3 months ago", Time(time.Unix(now-99*Day, 0)), "3 months ago"},
|
||||||
|
{"1 year ago (1)", Time(time.Unix(now-365*Day, 0)), "1 year ago"},
|
||||||
|
{"1 year ago (1)", Time(time.Unix(now-400*Day, 0)), "1 year ago"},
|
||||||
|
{"2 years ago (1)", Time(time.Unix(now-548*Day, 0)), "2 years ago"},
|
||||||
|
{"2 years ago (2)", Time(time.Unix(now-725*Day, 0)), "2 years ago"},
|
||||||
|
{"2 years ago (3)", Time(time.Unix(now-800*Day, 0)), "2 years ago"},
|
||||||
|
{"3 years ago", Time(time.Unix(now-3*Year, 0)), "3 years ago"},
|
||||||
|
{"long ago", Time(time.Unix(now-LongTime, 0)), "a long while ago"},
|
||||||
|
}.validate(t)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestFuture(t *testing.T) {
|
||||||
|
now := time.Now().Unix()
|
||||||
|
testList{
|
||||||
|
{"now", Time(time.Unix(now, 0)), "now"},
|
||||||
|
{"1 second from now", Time(time.Unix(now+1, 0)), "1 second from now"},
|
||||||
|
{"12 seconds from now", Time(time.Unix(now+12, 0)), "12 seconds from now"},
|
||||||
|
{"30 seconds from now", Time(time.Unix(now+30, 0)), "30 seconds from now"},
|
||||||
|
{"45 seconds from now", Time(time.Unix(now+45, 0)), "45 seconds from now"},
|
||||||
|
{"15 minutes from now", Time(time.Unix(now+15*Minute, 0)), "15 minutes from now"},
|
||||||
|
{"2 hours from now", Time(time.Unix(now+2*Hour, 0)), "2 hours from now"},
|
||||||
|
{"21 hours from now", Time(time.Unix(now+21*Hour, 0)), "21 hours from now"},
|
||||||
|
{"1 day from now", Time(time.Unix(now+26*Hour, 0)), "1 day from now"},
|
||||||
|
{"2 days from now", Time(time.Unix(now+49*Hour, 0)), "2 days from now"},
|
||||||
|
{"3 days from now", Time(time.Unix(now+3*Day, 0)), "3 days from now"},
|
||||||
|
{"1 week from now (1)", Time(time.Unix(now+7*Day, 0)), "1 week from now"},
|
||||||
|
{"1 week from now (2)", Time(time.Unix(now+12*Day, 0)), "1 week from now"},
|
||||||
|
{"2 weeks from now", Time(time.Unix(now+15*Day, 0)), "2 weeks from now"},
|
||||||
|
{"1 month from now", Time(time.Unix(now+30*Day, 0)), "1 month from now"},
|
||||||
|
{"1 year from now", Time(time.Unix(now+365*Day, 0)), "1 year from now"},
|
||||||
|
{"2 years from now", Time(time.Unix(now+2*Year, 0)), "2 years from now"},
|
||||||
|
{"a while from now", Time(time.Unix(now+LongTime, 0)), "a long while from now"},
|
||||||
|
}.validate(t)
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestRange(t *testing.T) {
|
||||||
|
start := time.Time{}
|
||||||
|
end := time.Unix(math.MaxInt64, math.MaxInt64)
|
||||||
|
x := RelTime(start, end, "ago", "from now")
|
||||||
|
if x != "a long while from now" {
|
||||||
|
t.Errorf("Expected a long while from now, got %q", x)
|
||||||
|
}
|
||||||
|
}
|
2
main.go
2
main.go
@ -26,7 +26,7 @@ import (
|
|||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/minio-io/cli"
|
"github.com/minio-io/cli"
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
"github.com/minio-io/minio/pkg/server"
|
"github.com/minio-io/minio/pkg/server"
|
||||||
"github.com/minio-io/minio/pkg/utils/log"
|
"github.com/minio-io/minio/pkg/utils/log"
|
||||||
)
|
)
|
||||||
|
@ -20,7 +20,7 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
|
|
||||||
"github.com/gorilla/mux"
|
"github.com/gorilla/mux"
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
"github.com/minio-io/minio/pkg/storage/drivers"
|
"github.com/minio-io/minio/pkg/storage/drivers"
|
||||||
"github.com/minio-io/minio/pkg/utils/log"
|
"github.com/minio-io/minio/pkg/utils/log"
|
||||||
)
|
)
|
||||||
|
@ -20,7 +20,7 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
|
|
||||||
"github.com/gorilla/mux"
|
"github.com/gorilla/mux"
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
"github.com/minio-io/minio/pkg/storage/drivers"
|
"github.com/minio-io/minio/pkg/storage/drivers"
|
||||||
"github.com/minio-io/minio/pkg/utils/log"
|
"github.com/minio-io/minio/pkg/utils/log"
|
||||||
)
|
)
|
||||||
|
@ -21,7 +21,7 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
|
|
||||||
"github.com/gorilla/mux"
|
"github.com/gorilla/mux"
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
"github.com/minio-io/minio/pkg/storage/drivers"
|
"github.com/minio-io/minio/pkg/storage/drivers"
|
||||||
"github.com/minio-io/minio/pkg/utils/log"
|
"github.com/minio-io/minio/pkg/utils/log"
|
||||||
)
|
)
|
||||||
|
@ -21,8 +21,8 @@ import (
|
|||||||
"net/http"
|
"net/http"
|
||||||
|
|
||||||
router "github.com/gorilla/mux"
|
router "github.com/gorilla/mux"
|
||||||
"github.com/minio-io/iodine"
|
|
||||||
"github.com/minio-io/minio/pkg/api/config"
|
"github.com/minio-io/minio/pkg/api/config"
|
||||||
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
"github.com/minio-io/minio/pkg/storage/drivers"
|
"github.com/minio-io/minio/pkg/storage/drivers"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -24,7 +24,7 @@ import (
|
|||||||
"path"
|
"path"
|
||||||
"sync"
|
"sync"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
)
|
)
|
||||||
|
|
||||||
// Config context
|
// Config context
|
||||||
|
@ -23,8 +23,8 @@ import (
|
|||||||
"path"
|
"path"
|
||||||
|
|
||||||
"github.com/gorilla/mux"
|
"github.com/gorilla/mux"
|
||||||
"github.com/minio-io/iodine"
|
|
||||||
"github.com/minio-io/minio/pkg/api/config"
|
"github.com/minio-io/minio/pkg/api/config"
|
||||||
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
"github.com/minio-io/minio/pkg/utils/crypto/keys"
|
"github.com/minio-io/minio/pkg/utils/crypto/keys"
|
||||||
"github.com/minio-io/minio/pkg/utils/log"
|
"github.com/minio-io/minio/pkg/utils/log"
|
||||||
)
|
)
|
||||||
|
@ -31,7 +31,7 @@ import (
|
|||||||
"github.com/dustin/go-humanize"
|
"github.com/dustin/go-humanize"
|
||||||
)
|
)
|
||||||
|
|
||||||
// WrappedError is the iodine error which contains a pointer to the original error
|
// Error is the iodine error which contains a pointer to the original error
|
||||||
// and stack traces.
|
// and stack traces.
|
||||||
type Error struct {
|
type Error struct {
|
||||||
EmbeddedError error `json:"-"`
|
EmbeddedError error `json:"-"`
|
||||||
@ -93,7 +93,7 @@ func GetGlobalStateKey(k string) string {
|
|||||||
return result
|
return result
|
||||||
}
|
}
|
||||||
|
|
||||||
// Error - instantiate an error, turning it into an iodine error.
|
// New - instantiate an error, turning it into an iodine error.
|
||||||
// Adds an initial stack trace.
|
// Adds an initial stack trace.
|
||||||
func New(err error, data map[string]string) error {
|
func New(err error, data map[string]string) error {
|
||||||
if err != nil {
|
if err != nil {
|
@ -24,9 +24,9 @@ import (
|
|||||||
|
|
||||||
"errors"
|
"errors"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
|
||||||
"github.com/minio-io/minio/pkg/api"
|
"github.com/minio-io/minio/pkg/api"
|
||||||
"github.com/minio-io/minio/pkg/api/web"
|
"github.com/minio-io/minio/pkg/api/web"
|
||||||
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
"github.com/minio-io/minio/pkg/server/httpserver"
|
"github.com/minio-io/minio/pkg/server/httpserver"
|
||||||
"github.com/minio-io/minio/pkg/storage/drivers"
|
"github.com/minio-io/minio/pkg/storage/drivers"
|
||||||
"github.com/minio-io/minio/pkg/storage/drivers/donut"
|
"github.com/minio-io/minio/pkg/storage/drivers/donut"
|
||||||
|
@ -19,7 +19,7 @@ package donut
|
|||||||
import (
|
import (
|
||||||
"errors"
|
"errors"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
)
|
)
|
||||||
|
|
||||||
// donut struct internal data
|
// donut struct internal data
|
||||||
|
@ -29,7 +29,7 @@ import (
|
|||||||
"crypto/md5"
|
"crypto/md5"
|
||||||
"encoding/hex"
|
"encoding/hex"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
)
|
)
|
||||||
|
|
||||||
// internal struct carrying bucket specific information
|
// internal struct carrying bucket specific information
|
||||||
|
@ -29,7 +29,7 @@ import (
|
|||||||
"strconv"
|
"strconv"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
"github.com/minio-io/minio/pkg/utils/split"
|
"github.com/minio-io/minio/pkg/utils/split"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -24,7 +24,7 @@ import (
|
|||||||
|
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
)
|
)
|
||||||
|
|
||||||
// internal disk struct
|
// internal disk struct
|
||||||
|
@ -20,8 +20,8 @@ import (
|
|||||||
"errors"
|
"errors"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
|
||||||
encoding "github.com/minio-io/minio/pkg/erasure"
|
encoding "github.com/minio-io/minio/pkg/erasure"
|
||||||
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
)
|
)
|
||||||
|
|
||||||
// encoder internal struct
|
// encoder internal struct
|
||||||
|
@ -19,7 +19,7 @@ package donut
|
|||||||
import (
|
import (
|
||||||
"errors"
|
"errors"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
)
|
)
|
||||||
|
|
||||||
// node struct internal
|
// node struct internal
|
||||||
|
@ -21,7 +21,7 @@ import (
|
|||||||
"os"
|
"os"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
)
|
)
|
||||||
|
|
||||||
// Rebalance -
|
// Rebalance -
|
||||||
|
@ -5,7 +5,7 @@ import (
|
|||||||
"errors"
|
"errors"
|
||||||
"path"
|
"path"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
)
|
)
|
||||||
|
|
||||||
// Heal - heal a donut and fix bad data blocks
|
// Heal - heal a donut and fix bad data blocks
|
||||||
|
@ -24,7 +24,7 @@ import (
|
|||||||
"strings"
|
"strings"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
)
|
)
|
||||||
|
|
||||||
// MakeBucket - make a new bucket
|
// MakeBucket - make a new bucket
|
||||||
|
@ -22,7 +22,7 @@ import (
|
|||||||
"path"
|
"path"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
)
|
)
|
||||||
|
|
||||||
func (d donut) makeDonutBucket(bucketName string) error {
|
func (d donut) makeDonutBucket(bucketName string) error {
|
||||||
|
@ -30,7 +30,7 @@ import (
|
|||||||
|
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
"github.com/minio-io/minio/pkg/storage/donut"
|
"github.com/minio-io/minio/pkg/storage/donut"
|
||||||
"github.com/minio-io/minio/pkg/storage/drivers"
|
"github.com/minio-io/minio/pkg/storage/drivers"
|
||||||
"github.com/minio-io/minio/pkg/utils/log"
|
"github.com/minio-io/minio/pkg/utils/log"
|
||||||
|
@ -4,7 +4,7 @@ import (
|
|||||||
"bytes"
|
"bytes"
|
||||||
"io"
|
"io"
|
||||||
|
|
||||||
"github.com/minio-io/iodine"
|
"github.com/minio-io/minio/pkg/iodine"
|
||||||
"github.com/minio-io/minio/pkg/storage/drivers"
|
"github.com/minio-io/minio/pkg/storage/drivers"
|
||||||
"github.com/stretchr/testify/mock"
|
"github.com/stretchr/testify/mock"
|
||||||
)
|
)
|
||||||
|
Loading…
Reference in New Issue
Block a user