Merge pull request #369 from fkautz/pr_out_updating_iodine_now_has_global_state

This commit is contained in:
Frederick F. Kautz IV 2015-03-25 10:40:08 -07:00
commit da89132def
6 changed files with 163 additions and 81 deletions

2
Godeps/Godeps.json generated
View File

@ -20,7 +20,7 @@
},
{
"ImportPath": "github.com/minio-io/iodine",
"Rev": "d7c4850883ade19431e3808e9c712d3d3e69cdcc"
"Rev": "b279ca8ea714fabc969883a4d1612a4e93d01611"
},
{
"ImportPath": "gopkg.in/check.v1",

View File

@ -23,6 +23,7 @@ import (
"os"
"runtime"
"strconv"
"sync"
)
// Error is the iodine error which contains a pointer to the original error
@ -42,6 +43,35 @@ type StackEntry struct {
Data map[string]string
}
var globalState = struct {
sync.RWMutex
m map[string]string
}{m: make(map[string]string)}
func SetGlobalState(key, value string) {
globalState.Lock()
globalState.m[key] = value
globalState.Unlock()
}
func ClearGlobalState() {
globalState.Lock()
for k, _ := range globalState.m {
delete(globalState.m, k)
}
globalState.Unlock()
}
func GetGlobalState() map[string]string {
result := make(map[string]string)
globalState.RLock()
for k, v := range globalState.m {
result[k] = v
}
globalState.RUnlock()
return result
}
// Wrap an error, turning it into an iodine error.
// Adds an initial stack trace.
func New(err error, data map[string]string) *Error {
@ -63,18 +93,17 @@ func createStackEntry() StackEntry {
Host: host,
File: file,
Line: line,
Data: make(map[string]string),
Data: GetGlobalState(),
}
return entry
}
// Annotate an error with a stack entry and returns itself
func (err *Error) Annotate(info map[string]string) *Error {
data := make(map[string]string)
for k, v := range info {
data[k] = v
}
entry := createStackEntry()
for k, v := range info {
entry.Data[k] = v
}
err.Stack = append(err.Stack, entry)
return err
}

View File

@ -38,6 +38,54 @@ func TestIodine(t *testing.T) {
}
var prettyBuffer bytes.Buffer
json.Indent(&prettyBuffer, jsonResult, "", " ")
log.Println(string(prettyBuffer.Bytes()))
log.Println(iodineError.EmitHumanReadable())
}
func TestState(t *testing.T) {
SetGlobalState("hello", "world")
state := GetGlobalState()
if res, ok := state["hello"]; ok {
if res != "world" {
t.Error("global state not set: hello->world")
}
} else {
t.Fail()
}
ClearGlobalState()
if len(GetGlobalState()) != 0 {
t.Fail()
}
SetGlobalState("foo", "bar")
err := New(errors.New("a simple error"), nil)
if res, ok := err.Stack[0].Data["foo"]; ok {
if res != "bar" {
t.Error("global state not set: foo->bar")
}
} else {
t.Fail()
}
err.Annotate(map[string]string{"foo2": "bar2"})
if res, ok := err.Stack[0].Data["foo"]; ok {
if res != "bar" {
t.Error("annotate should not modify previous data entries")
}
} else {
t.Error("annotate should not remove previous data entries")
}
if res, ok := err.Stack[1].Data["foo"]; ok {
if res != "bar" {
t.Error("global state should set value properly in annotate")
}
} else {
t.Error("global state should set key properly in annotate")
}
if res, ok := err.Stack[1].Data["foo2"]; ok {
if res != "bar2" {
err.Annotate(nil)
t.Error("foo2 -> bar should be set")
}
} else {
err.Annotate(nil)
log.Println(err.EmitHumanReadable())
t.Error("foo2 should be set")
}
}

View File

@ -3,8 +3,8 @@
package check_test
import (
"time"
. "gopkg.in/check.v1"
"time"
)
var benchmarkS = Suite(&BenchmarkS{})

View File

@ -1,7 +1,7 @@
package check_test
import (
. "gopkg.in/check.v1"
. "gopkg.in/check.v1"
)
var _ = Suite(&PrinterS{})
@ -9,96 +9,101 @@ var _ = Suite(&PrinterS{})
type PrinterS struct{}
func (s *PrinterS) TestCountSuite(c *C) {
suitesRun += 1
suitesRun += 1
}
var printTestFuncLine int
func init() {
printTestFuncLine = getMyLine() + 3
printTestFuncLine = getMyLine() + 3
}
func printTestFunc() {
println(1) // Comment1
if 2 == 2 { // Comment2
println(3) // Comment3
}
switch 5 {
case 6: println(6) // Comment6
println(7)
}
switch interface{}(9).(type) {// Comment9
case int: println(10)
println(11)
}
select {
case <-(chan bool)(nil): println(14)
println(15)
default: println(16)
println(17)
}
println(19,
20)
_ = func() { println(21)
println(22)
}
println(24, func() {
println(25)
})
// Leading comment
// with multiple lines.
println(29) // Comment29
println(1) // Comment1
if 2 == 2 { // Comment2
println(3) // Comment3
}
switch 5 {
case 6:
println(6) // Comment6
println(7)
}
switch interface{}(9).(type) { // Comment9
case int:
println(10)
println(11)
}
select {
case <-(chan bool)(nil):
println(14)
println(15)
default:
println(16)
println(17)
}
println(19,
20)
_ = func() {
println(21)
println(22)
}
println(24, func() {
println(25)
})
// Leading comment
// with multiple lines.
println(29) // Comment29
}
var printLineTests = []struct {
line int
output string
line int
output string
}{
{1, "println(1) // Comment1"},
{2, "if 2 == 2 { // Comment2\n ...\n}"},
{3, "println(3) // Comment3"},
{5, "switch 5 {\n...\n}"},
{6, "case 6:\n println(6) // Comment6\n ..."},
{7, "println(7)"},
{9, "switch interface{}(9).(type) { // Comment9\n...\n}"},
{10, "case int:\n println(10)\n ..."},
{14, "case <-(chan bool)(nil):\n println(14)\n ..."},
{15, "println(15)"},
{16, "default:\n println(16)\n ..."},
{17, "println(17)"},
{19, "println(19,\n 20)"},
{20, "println(19,\n 20)"},
{21, "_ = func() {\n println(21)\n println(22)\n}"},
{22, "println(22)"},
{24, "println(24, func() {\n println(25)\n})"},
{25, "println(25)"},
{26, "println(24, func() {\n println(25)\n})"},
{29, "// Leading comment\n// with multiple lines.\nprintln(29) // Comment29"},
{1, "println(1) // Comment1"},
{2, "if 2 == 2 { // Comment2\n ...\n}"},
{3, "println(3) // Comment3"},
{5, "switch 5 {\n...\n}"},
{6, "case 6:\n println(6) // Comment6\n ..."},
{7, "println(7)"},
{9, "switch interface{}(9).(type) { // Comment9\n...\n}"},
{10, "case int:\n println(10)\n ..."},
{14, "case <-(chan bool)(nil):\n println(14)\n ..."},
{15, "println(15)"},
{16, "default:\n println(16)\n ..."},
{17, "println(17)"},
{19, "println(19,\n 20)"},
{20, "println(19,\n 20)"},
{21, "_ = func() {\n println(21)\n println(22)\n}"},
{22, "println(22)"},
{24, "println(24, func() {\n println(25)\n})"},
{25, "println(25)"},
{26, "println(24, func() {\n println(25)\n})"},
{29, "// Leading comment\n// with multiple lines.\nprintln(29) // Comment29"},
}
func (s *PrinterS) TestPrintLine(c *C) {
for _, test := range printLineTests {
output, err := PrintLine("printer_test.go", printTestFuncLine+test.line)
c.Assert(err, IsNil)
c.Assert(output, Equals, test.output)
}
for _, test := range printLineTests {
output, err := PrintLine("printer_test.go", printTestFuncLine+test.line)
c.Assert(err, IsNil)
c.Assert(output, Equals, test.output)
}
}
var indentTests = []struct {
in, out string
in, out string
}{
{"", ""},
{"\n", "\n"},
{"a", ">>>a"},
{"a\n", ">>>a\n"},
{"a\nb", ">>>a\n>>>b"},
{" ", ">>> "},
{"", ""},
{"\n", "\n"},
{"a", ">>>a"},
{"a\n", ">>>a\n"},
{"a\nb", ">>>a\n>>>b"},
{" ", ">>> "},
}
func (s *PrinterS) TestIndent(c *C) {
for _, test := range indentTests {
out := Indent(test.in, ">>>")
c.Assert(out, Equals, test.out)
}
for _, test := range indentTests {
out := Indent(test.in, ">>>")
c.Assert(out, Equals, test.out)
}
}

View File

@ -400,7 +400,7 @@ func (s *RunS) TestStreamModeWithMiss(c *C) {
// -----------------------------------------------------------------------
// Verify that that the keep work dir request indeed does so.
type WorkDirSuite struct {}
type WorkDirSuite struct{}
func (s *WorkDirSuite) Test(c *C) {
c.MkDir()
@ -411,7 +411,7 @@ func (s *RunS) TestKeepWorkDir(c *C) {
runConf := RunConf{Output: &output, Verbose: true, KeepWorkDir: true}
result := Run(&WorkDirSuite{}, &runConf)
c.Assert(result.String(), Matches, ".*\nWORK=" + result.WorkDir)
c.Assert(result.String(), Matches, ".*\nWORK="+result.WorkDir)
stat, err := os.Stat(result.WorkDir)
c.Assert(err, IsNil)