Merge branch 'alerting'
This commit is contained in:
@@ -24,7 +24,6 @@
|
||||
* **Graphite**: Fixed issue with mixed data sources and Graphite, fixes [#5617](https://github.com/grafana/grafana/issues/5617)
|
||||
* **Templating**: Fixed issue with template variable query was issued multiple times during dashboard load, fixes [#5637](https://github.com/grafana/grafana/issues/5637)
|
||||
* **Zoom**: Fixed issues with zoom in and out on embedded (iframed) panel, fixes [#4489](https://github.com/grafana/grafana/issues/4489), [#5666](https://github.com/grafana/grafana/issues/5666)
|
||||
* **Templating**: Row/Panel repeat issue when saving dashboard caused dupes to appear, fixes [#5591](https://github.com/grafana/grafana/issues/5591)
|
||||
|
||||
# 3.1.0 stable (2016-07-12)
|
||||
|
||||
|
||||
Generated
+12
@@ -130,6 +130,10 @@
|
||||
"Comment": "v1.4.1",
|
||||
"Rev": "f80e7d0182a463dff0c0da6bbed57f21369d4346"
|
||||
},
|
||||
{
|
||||
"ImportPath": "github.com/benbjohnson/clock",
|
||||
"Rev": "a620c1cc9866f84a2550ad53f4f353ec030fa26b"
|
||||
},
|
||||
{
|
||||
"ImportPath": "github.com/bmizerany/assert",
|
||||
"Comment": "release.r60-6-ge17e998",
|
||||
@@ -272,6 +276,14 @@
|
||||
"Comment": "go.weekly.2011-12-22-27-ge6ac2fc",
|
||||
"Rev": "e6ac2fc51e89a3249e82157fa0bb7a18ef9dd5bb"
|
||||
},
|
||||
{
|
||||
"ImportPath": "github.com/kr/s3",
|
||||
"Rev": "c070c8f9a8f0032d48f0d2a77d4e382788bd8a1d"
|
||||
},
|
||||
{
|
||||
"ImportPath": "github.com/kr/s3/s3util",
|
||||
"Rev": "c070c8f9a8f0032d48f0d2a77d4e382788bd8a1d"
|
||||
},
|
||||
{
|
||||
"ImportPath": "github.com/kr/text",
|
||||
"Rev": "bb797dc4fb8320488f47bf11de07a733d7233e1f"
|
||||
|
||||
+21
@@ -0,0 +1,21 @@
|
||||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2014 Ben Johnson
|
||||
|
||||
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.
|
||||
+104
@@ -0,0 +1,104 @@
|
||||
clock [](https://drone.io/github.com/benbjohnson/clock/latest) [](https://coveralls.io/r/benbjohnson/clock?branch=master) [](https://godoc.org/github.com/benbjohnson/clock) 
|
||||
=====
|
||||
|
||||
Clock is a small library for mocking time in Go. It provides an interface
|
||||
around the standard library's [`time`][time] package so that the application
|
||||
can use the realtime clock while tests can use the mock clock.
|
||||
|
||||
[time]: http://golang.org/pkg/time/
|
||||
|
||||
|
||||
## Usage
|
||||
|
||||
### Realtime Clock
|
||||
|
||||
Your application can maintain a `Clock` variable that will allow realtime and
|
||||
mock clocks to be interchangable. For example, if you had an `Application` type:
|
||||
|
||||
```go
|
||||
import "github.com/benbjohnson/clock"
|
||||
|
||||
type Application struct {
|
||||
Clock clock.Clock
|
||||
}
|
||||
```
|
||||
|
||||
You could initialize it to use the realtime clock like this:
|
||||
|
||||
```go
|
||||
var app Application
|
||||
app.Clock = clock.New()
|
||||
...
|
||||
```
|
||||
|
||||
Then all timers and time-related functionality should be performed from the
|
||||
`Clock` variable.
|
||||
|
||||
|
||||
### Mocking time
|
||||
|
||||
In your tests, you will want to use a `Mock` clock:
|
||||
|
||||
```go
|
||||
import (
|
||||
"testing"
|
||||
|
||||
"github.com/benbjohnson/clock"
|
||||
)
|
||||
|
||||
func TestApplication_DoSomething(t *testing.T) {
|
||||
mock := clock.NewMock()
|
||||
app := Application{Clock: mock}
|
||||
...
|
||||
}
|
||||
```
|
||||
|
||||
Now that you've initialized your application to use the mock clock, you can
|
||||
adjust the time programmatically. The mock clock always starts from the Unix
|
||||
epoch (midnight, Jan 1, 1970 UTC).
|
||||
|
||||
|
||||
### Controlling time
|
||||
|
||||
The mock clock provides the same functions that the standard library's `time`
|
||||
package provides. For example, to find the current time, you use the `Now()`
|
||||
function:
|
||||
|
||||
```go
|
||||
mock := clock.NewMock()
|
||||
|
||||
// Find the current time.
|
||||
mock.Now().UTC() // 1970-01-01 00:00:00 +0000 UTC
|
||||
|
||||
// Move the clock forward.
|
||||
mock.Add(2 * time.Hour)
|
||||
|
||||
// Check the time again. It's 2 hours later!
|
||||
mock.Now().UTC() // 1970-01-01 02:00:00 +0000 UTC
|
||||
```
|
||||
|
||||
Timers and Tickers are also controlled by this same mock clock. They will only
|
||||
execute when the clock is moved forward:
|
||||
|
||||
```
|
||||
mock := clock.NewMock()
|
||||
count := 0
|
||||
|
||||
// Kick off a timer to increment every 1 mock second.
|
||||
go func() {
|
||||
ticker := clock.Ticker(1 * time.Second)
|
||||
for {
|
||||
<-ticker.C
|
||||
count++
|
||||
}
|
||||
}()
|
||||
runtime.Gosched()
|
||||
|
||||
// Move the clock forward 10 second.
|
||||
mock.Add(10 * time.Second)
|
||||
|
||||
// This prints 10.
|
||||
fmt.Println(count)
|
||||
```
|
||||
|
||||
|
||||
+319
@@ -0,0 +1,319 @@
|
||||
package clock
|
||||
|
||||
import (
|
||||
"sort"
|
||||
"sync"
|
||||
"time"
|
||||
)
|
||||
|
||||
// Clock represents an interface to the functions in the standard library time
|
||||
// package. Two implementations are available in the clock package. The first
|
||||
// is a real-time clock which simply wraps the time package's functions. The
|
||||
// second is a mock clock which will only make forward progress when
|
||||
// programmatically adjusted.
|
||||
type Clock interface {
|
||||
After(d time.Duration) <-chan time.Time
|
||||
AfterFunc(d time.Duration, f func()) *Timer
|
||||
Now() time.Time
|
||||
Sleep(d time.Duration)
|
||||
Tick(d time.Duration) <-chan time.Time
|
||||
Ticker(d time.Duration) *Ticker
|
||||
Timer(d time.Duration) *Timer
|
||||
}
|
||||
|
||||
// New returns an instance of a real-time clock.
|
||||
func New() Clock {
|
||||
return &clock{}
|
||||
}
|
||||
|
||||
// clock implements a real-time clock by simply wrapping the time package functions.
|
||||
type clock struct{}
|
||||
|
||||
func (c *clock) After(d time.Duration) <-chan time.Time { return time.After(d) }
|
||||
|
||||
func (c *clock) AfterFunc(d time.Duration, f func()) *Timer {
|
||||
return &Timer{timer: time.AfterFunc(d, f)}
|
||||
}
|
||||
|
||||
func (c *clock) Now() time.Time { return time.Now() }
|
||||
|
||||
func (c *clock) Sleep(d time.Duration) { time.Sleep(d) }
|
||||
|
||||
func (c *clock) Tick(d time.Duration) <-chan time.Time { return time.Tick(d) }
|
||||
|
||||
func (c *clock) Ticker(d time.Duration) *Ticker {
|
||||
t := time.NewTicker(d)
|
||||
return &Ticker{C: t.C, ticker: t}
|
||||
}
|
||||
|
||||
func (c *clock) Timer(d time.Duration) *Timer {
|
||||
t := time.NewTimer(d)
|
||||
return &Timer{C: t.C, timer: t}
|
||||
}
|
||||
|
||||
// Mock represents a mock clock that only moves forward programmically.
|
||||
// It can be preferable to a real-time clock when testing time-based functionality.
|
||||
type Mock struct {
|
||||
mu sync.Mutex
|
||||
now time.Time // current time
|
||||
timers clockTimers // tickers & timers
|
||||
}
|
||||
|
||||
// NewMock returns an instance of a mock clock.
|
||||
// The current time of the mock clock on initialization is the Unix epoch.
|
||||
func NewMock() *Mock {
|
||||
return &Mock{now: time.Unix(0, 0)}
|
||||
}
|
||||
|
||||
// Add moves the current time of the mock clock forward by the duration.
|
||||
// This should only be called from a single goroutine at a time.
|
||||
func (m *Mock) Add(d time.Duration) {
|
||||
// Calculate the final current time.
|
||||
t := m.now.Add(d)
|
||||
|
||||
// Continue to execute timers until there are no more before the new time.
|
||||
for {
|
||||
if !m.runNextTimer(t) {
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
// Ensure that we end with the new time.
|
||||
m.mu.Lock()
|
||||
m.now = t
|
||||
m.mu.Unlock()
|
||||
|
||||
// Give a small buffer to make sure the other goroutines get handled.
|
||||
gosched()
|
||||
}
|
||||
|
||||
// Sets the current time of the mock clock to a specific one.
|
||||
// This should only be called from a single goroutine at a time.
|
||||
func (m *Mock) Set(t time.Time) {
|
||||
// Continue to execute timers until there are no more before the new time.
|
||||
for {
|
||||
if !m.runNextTimer(t) {
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
// Ensure that we end with the new time.
|
||||
m.mu.Lock()
|
||||
m.now = t
|
||||
m.mu.Unlock()
|
||||
|
||||
// Give a small buffer to make sure the other goroutines get handled.
|
||||
gosched()
|
||||
}
|
||||
|
||||
// runNextTimer executes the next timer in chronological order and moves the
|
||||
// current time to the timer's next tick time. The next time is not executed if
|
||||
// it's next time if after the max time. Returns true if a timer is executed.
|
||||
func (m *Mock) runNextTimer(max time.Time) bool {
|
||||
m.mu.Lock()
|
||||
|
||||
// Sort timers by time.
|
||||
sort.Sort(m.timers)
|
||||
|
||||
// If we have no more timers then exit.
|
||||
if len(m.timers) == 0 {
|
||||
m.mu.Unlock()
|
||||
return false
|
||||
}
|
||||
|
||||
// Retrieve next timer. Exit if next tick is after new time.
|
||||
t := m.timers[0]
|
||||
if t.Next().After(max) {
|
||||
m.mu.Unlock()
|
||||
return false
|
||||
}
|
||||
|
||||
// Move "now" forward and unlock clock.
|
||||
m.now = t.Next()
|
||||
m.mu.Unlock()
|
||||
|
||||
// Execute timer.
|
||||
t.Tick(m.now)
|
||||
return true
|
||||
}
|
||||
|
||||
// After waits for the duration to elapse and then sends the current time on the returned channel.
|
||||
func (m *Mock) After(d time.Duration) <-chan time.Time {
|
||||
return m.Timer(d).C
|
||||
}
|
||||
|
||||
// AfterFunc waits for the duration to elapse and then executes a function.
|
||||
// A Timer is returned that can be stopped.
|
||||
func (m *Mock) AfterFunc(d time.Duration, f func()) *Timer {
|
||||
t := m.Timer(d)
|
||||
t.C = nil
|
||||
t.fn = f
|
||||
return t
|
||||
}
|
||||
|
||||
// Now returns the current wall time on the mock clock.
|
||||
func (m *Mock) Now() time.Time {
|
||||
m.mu.Lock()
|
||||
defer m.mu.Unlock()
|
||||
return m.now
|
||||
}
|
||||
|
||||
// Sleep pauses the goroutine for the given duration on the mock clock.
|
||||
// The clock must be moved forward in a separate goroutine.
|
||||
func (m *Mock) Sleep(d time.Duration) {
|
||||
<-m.After(d)
|
||||
}
|
||||
|
||||
// Tick is a convenience function for Ticker().
|
||||
// It will return a ticker channel that cannot be stopped.
|
||||
func (m *Mock) Tick(d time.Duration) <-chan time.Time {
|
||||
return m.Ticker(d).C
|
||||
}
|
||||
|
||||
// Ticker creates a new instance of Ticker.
|
||||
func (m *Mock) Ticker(d time.Duration) *Ticker {
|
||||
m.mu.Lock()
|
||||
defer m.mu.Unlock()
|
||||
ch := make(chan time.Time, 1)
|
||||
t := &Ticker{
|
||||
C: ch,
|
||||
c: ch,
|
||||
mock: m,
|
||||
d: d,
|
||||
next: m.now.Add(d),
|
||||
}
|
||||
m.timers = append(m.timers, (*internalTicker)(t))
|
||||
return t
|
||||
}
|
||||
|
||||
// Timer creates a new instance of Timer.
|
||||
func (m *Mock) Timer(d time.Duration) *Timer {
|
||||
m.mu.Lock()
|
||||
defer m.mu.Unlock()
|
||||
ch := make(chan time.Time, 1)
|
||||
t := &Timer{
|
||||
C: ch,
|
||||
c: ch,
|
||||
mock: m,
|
||||
next: m.now.Add(d),
|
||||
stopped: false,
|
||||
}
|
||||
m.timers = append(m.timers, (*internalTimer)(t))
|
||||
return t
|
||||
}
|
||||
|
||||
func (m *Mock) removeClockTimer(t clockTimer) {
|
||||
m.mu.Lock()
|
||||
defer m.mu.Unlock()
|
||||
for i, timer := range m.timers {
|
||||
if timer == t {
|
||||
copy(m.timers[i:], m.timers[i+1:])
|
||||
m.timers[len(m.timers)-1] = nil
|
||||
m.timers = m.timers[:len(m.timers)-1]
|
||||
break
|
||||
}
|
||||
}
|
||||
sort.Sort(m.timers)
|
||||
}
|
||||
|
||||
// clockTimer represents an object with an associated start time.
|
||||
type clockTimer interface {
|
||||
Next() time.Time
|
||||
Tick(time.Time)
|
||||
}
|
||||
|
||||
// clockTimers represents a list of sortable timers.
|
||||
type clockTimers []clockTimer
|
||||
|
||||
func (a clockTimers) Len() int { return len(a) }
|
||||
func (a clockTimers) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
|
||||
func (a clockTimers) Less(i, j int) bool { return a[i].Next().Before(a[j].Next()) }
|
||||
|
||||
// Timer represents a single event.
|
||||
// The current time will be sent on C, unless the timer was created by AfterFunc.
|
||||
type Timer struct {
|
||||
C <-chan time.Time
|
||||
c chan time.Time
|
||||
timer *time.Timer // realtime impl, if set
|
||||
next time.Time // next tick time
|
||||
mock *Mock // mock clock, if set
|
||||
fn func() // AfterFunc function, if set
|
||||
stopped bool // True if stopped, false if running
|
||||
}
|
||||
|
||||
// Stop turns off the ticker.
|
||||
func (t *Timer) Stop() bool {
|
||||
if t.timer != nil {
|
||||
return t.timer.Stop()
|
||||
}
|
||||
|
||||
registered := !t.stopped
|
||||
t.mock.removeClockTimer((*internalTimer)(t))
|
||||
t.stopped = true
|
||||
return registered
|
||||
}
|
||||
|
||||
// Reset changes the expiry time of the timer
|
||||
func (t *Timer) Reset(d time.Duration) bool {
|
||||
if t.timer != nil {
|
||||
return t.timer.Reset(d)
|
||||
}
|
||||
|
||||
t.next = t.mock.now.Add(d)
|
||||
registered := !t.stopped
|
||||
if t.stopped {
|
||||
t.mock.mu.Lock()
|
||||
t.mock.timers = append(t.mock.timers, (*internalTimer)(t))
|
||||
t.mock.mu.Unlock()
|
||||
}
|
||||
t.stopped = false
|
||||
return registered
|
||||
}
|
||||
|
||||
type internalTimer Timer
|
||||
|
||||
func (t *internalTimer) Next() time.Time { return t.next }
|
||||
func (t *internalTimer) Tick(now time.Time) {
|
||||
if t.fn != nil {
|
||||
t.fn()
|
||||
} else {
|
||||
t.c <- now
|
||||
}
|
||||
t.mock.removeClockTimer((*internalTimer)(t))
|
||||
t.stopped = true
|
||||
gosched()
|
||||
}
|
||||
|
||||
// Ticker holds a channel that receives "ticks" at regular intervals.
|
||||
type Ticker struct {
|
||||
C <-chan time.Time
|
||||
c chan time.Time
|
||||
ticker *time.Ticker // realtime impl, if set
|
||||
next time.Time // next tick time
|
||||
mock *Mock // mock clock, if set
|
||||
d time.Duration // time between ticks
|
||||
}
|
||||
|
||||
// Stop turns off the ticker.
|
||||
func (t *Ticker) Stop() {
|
||||
if t.ticker != nil {
|
||||
t.ticker.Stop()
|
||||
} else {
|
||||
t.mock.removeClockTimer((*internalTicker)(t))
|
||||
}
|
||||
}
|
||||
|
||||
type internalTicker Ticker
|
||||
|
||||
func (t *internalTicker) Next() time.Time { return t.next }
|
||||
func (t *internalTicker) Tick(now time.Time) {
|
||||
select {
|
||||
case t.c <- now:
|
||||
default:
|
||||
}
|
||||
t.next = now.Add(t.d)
|
||||
gosched()
|
||||
}
|
||||
|
||||
// Sleep momentarily so that other goroutines can process.
|
||||
func gosched() { time.Sleep(1 * time.Millisecond) }
|
||||
+19
@@ -0,0 +1,19 @@
|
||||
Copyright (c) 2012 Keith Rarick.
|
||||
|
||||
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.
|
||||
+4
@@ -0,0 +1,4 @@
|
||||
Package s3 signs HTTP requests for use with Amazon’s S3 API.
|
||||
|
||||
Documentation:
|
||||
http://godoc.org/github.com/kr/s3
|
||||
+4
@@ -0,0 +1,4 @@
|
||||
Package s3util provides streaming transfers to and from Amazon S3.
|
||||
|
||||
Full documentation:
|
||||
http://godoc.org/github.com/kr/s3/s3util
|
||||
+27
@@ -0,0 +1,27 @@
|
||||
// Package s3util provides streaming transfers to and from Amazon S3.
|
||||
//
|
||||
// To use it, open or create an S3 object, read or write data,
|
||||
// and close the object.
|
||||
//
|
||||
// You must assign valid credentials to DefaultConfig.Keys before using
|
||||
// DefaultConfig. Be sure to close an io.WriteCloser returned by this package,
|
||||
// to flush buffers and complete the multipart upload process.
|
||||
package s3util
|
||||
|
||||
// TODO(kr): parse error responses; return structured data
|
||||
|
||||
import (
|
||||
"github.com/kr/s3"
|
||||
"net/http"
|
||||
)
|
||||
|
||||
var DefaultConfig = &Config{
|
||||
Service: s3.DefaultService,
|
||||
Keys: new(s3.Keys),
|
||||
}
|
||||
|
||||
type Config struct {
|
||||
*s3.Service
|
||||
*s3.Keys
|
||||
*http.Client // if nil, uses http.DefaultClient
|
||||
}
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
package s3util
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
"io"
|
||||
"net/http"
|
||||
)
|
||||
|
||||
type respError struct {
|
||||
r *http.Response
|
||||
b bytes.Buffer
|
||||
}
|
||||
|
||||
func newRespError(r *http.Response) *respError {
|
||||
e := new(respError)
|
||||
e.r = r
|
||||
io.Copy(&e.b, r.Body)
|
||||
r.Body.Close()
|
||||
return e
|
||||
}
|
||||
|
||||
func (e *respError) Error() string {
|
||||
return fmt.Sprintf(
|
||||
"unwanted http status %d: %q",
|
||||
e.r.StatusCode,
|
||||
e.b.String(),
|
||||
)
|
||||
}
|
||||
+33
@@ -0,0 +1,33 @@
|
||||
package s3util
|
||||
|
||||
import (
|
||||
"io"
|
||||
"net/http"
|
||||
"time"
|
||||
)
|
||||
|
||||
// Open requests the S3 object at url. An HTTP status other than 200 is
|
||||
// considered an error.
|
||||
//
|
||||
// If c is nil, Open uses DefaultConfig.
|
||||
func Open(url string, c *Config) (io.ReadCloser, error) {
|
||||
if c == nil {
|
||||
c = DefaultConfig
|
||||
}
|
||||
// TODO(kr): maybe parallel range fetching
|
||||
r, _ := http.NewRequest("GET", url, nil)
|
||||
r.Header.Set("Date", time.Now().UTC().Format(http.TimeFormat))
|
||||
c.Sign(r, *c.Keys)
|
||||
client := c.Client
|
||||
if client == nil {
|
||||
client = http.DefaultClient
|
||||
}
|
||||
resp, err := client.Do(r)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if resp.StatusCode != 200 {
|
||||
return nil, newRespError(resp)
|
||||
}
|
||||
return resp.Body, nil
|
||||
}
|
||||
+208
@@ -0,0 +1,208 @@
|
||||
package s3util
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"encoding/xml"
|
||||
"errors"
|
||||
"io"
|
||||
"net/http"
|
||||
"net/url"
|
||||
"os"
|
||||
"strconv"
|
||||
"strings"
|
||||
"time"
|
||||
)
|
||||
|
||||
// File represents an S3 object or directory.
|
||||
type File struct {
|
||||
url string
|
||||
prefix string
|
||||
config *Config
|
||||
result *listObjectsResult
|
||||
}
|
||||
|
||||
type fileInfo struct {
|
||||
name string
|
||||
size int64
|
||||
dir bool
|
||||
modTime time.Time
|
||||
sys *Stat
|
||||
}
|
||||
|
||||
// Stat contains information about an S3 object or directory.
|
||||
// It is the "underlying data source" returned by method Sys
|
||||
// for each FileInfo produced by this package.
|
||||
// fi.Sys().(*s3util.Stat)
|
||||
// For the meaning of these fields, see
|
||||
// http://docs.aws.amazon.com/AmazonS3/latest/API/RESTBucketGET.html.
|
||||
type Stat struct {
|
||||
Key string
|
||||
LastModified string
|
||||
ETag string // ETag value, without double quotes.
|
||||
Size string
|
||||
StorageClass string
|
||||
OwnerID string `xml:"Owner>ID"`
|
||||
OwnerName string `xml:"Owner>DisplayName"`
|
||||
}
|
||||
|
||||
type listObjectsResult struct {
|
||||
IsTruncated bool
|
||||
Contents []Stat
|
||||
Directories []string `xml:"CommonPrefixes>Prefix"` // Suffix "/" trimmed
|
||||
}
|
||||
|
||||
func (f *fileInfo) Name() string { return f.name }
|
||||
func (f *fileInfo) Size() int64 { return f.size }
|
||||
func (f *fileInfo) Mode() os.FileMode {
|
||||
if f.dir {
|
||||
return 0755 | os.ModeDir
|
||||
}
|
||||
return 0644
|
||||
}
|
||||
func (f *fileInfo) ModTime() time.Time {
|
||||
if f.modTime.IsZero() && f.sys != nil {
|
||||
// we return the zero value if a parse error ever happens.
|
||||
f.modTime, _ = time.Parse(time.RFC3339Nano, f.sys.LastModified)
|
||||
}
|
||||
return f.modTime
|
||||
}
|
||||
func (f *fileInfo) IsDir() bool { return f.dir }
|
||||
func (f *fileInfo) Sys() interface{} { return f.sys }
|
||||
|
||||
// NewFile returns a new File with the given URL and config.
|
||||
//
|
||||
// Set rawurl to a directory on S3, such as
|
||||
// https://mybucket.s3.amazonaws.com/myfolder.
|
||||
// The URL cannot have query parameters or a fragment.
|
||||
// If c is nil, DefaultConfig will be used.
|
||||
func NewFile(rawurl string, c *Config) (*File, error) {
|
||||
u, err := url.Parse(rawurl)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if u.RawQuery != "" {
|
||||
return nil, errors.New("url cannot have raw query parameters.")
|
||||
}
|
||||
if u.Fragment != "" {
|
||||
return nil, errors.New("url cannot have a fragment.")
|
||||
}
|
||||
|
||||
prefix := strings.TrimLeft(u.Path, "/")
|
||||
if prefix != "" && !strings.HasSuffix(prefix, "/") {
|
||||
prefix += "/"
|
||||
}
|
||||
u.Path = ""
|
||||
return &File{u.String(), prefix, c, nil}, nil
|
||||
}
|
||||
|
||||
// Readdir requests a list of entries in the S3 directory
|
||||
// represented by f and returns a slice of up to n FileInfo
|
||||
// values, in alphabetical order. Subsequent calls
|
||||
// on the same File will yield further FileInfos.
|
||||
// Only direct children are returned, not deeper descendants.
|
||||
func (f *File) Readdir(n int) ([]os.FileInfo, error) {
|
||||
if f.result != nil && !f.result.IsTruncated {
|
||||
return make([]os.FileInfo, 0), io.EOF
|
||||
}
|
||||
|
||||
reader, err := f.sendRequest(n)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
defer reader.Close()
|
||||
|
||||
return f.parseResponse(reader)
|
||||
}
|
||||
|
||||
func (f *File) sendRequest(count int) (io.ReadCloser, error) {
|
||||
c := f.config
|
||||
if c == nil {
|
||||
c = DefaultConfig
|
||||
}
|
||||
var buf bytes.Buffer
|
||||
buf.WriteString(f.url)
|
||||
buf.WriteString("?delimiter=%2F")
|
||||
if f.prefix != "" {
|
||||
buf.WriteString("&prefix=")
|
||||
buf.WriteString(url.QueryEscape(f.prefix))
|
||||
}
|
||||
if count > 0 {
|
||||
buf.WriteString("&max-keys=")
|
||||
buf.WriteString(strconv.Itoa(count))
|
||||
}
|
||||
if f.result != nil && f.result.IsTruncated {
|
||||
var lastDir, lastKey, marker string
|
||||
if len(f.result.Directories) > 0 {
|
||||
lastDir = f.result.Directories[len(f.result.Directories)-1]
|
||||
}
|
||||
if len(f.result.Contents) > 0 {
|
||||
lastKey = f.result.Contents[len(f.result.Contents)-1].Key
|
||||
}
|
||||
|
||||
if lastKey > lastDir {
|
||||
marker = lastKey
|
||||
} else {
|
||||
marker = lastDir
|
||||
}
|
||||
|
||||
if marker != "" {
|
||||
buf.WriteString("&marker=")
|
||||
buf.WriteString(url.QueryEscape(marker))
|
||||
}
|
||||
}
|
||||
u := buf.String()
|
||||
r, _ := http.NewRequest("GET", u, nil)
|
||||
r.Header.Set("Date", time.Now().UTC().Format(http.TimeFormat))
|
||||
c.Sign(r, *c.Keys)
|
||||
resp, err := http.DefaultClient.Do(r)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if resp.StatusCode != 200 {
|
||||
return nil, newRespError(resp)
|
||||
}
|
||||
return resp.Body, nil
|
||||
}
|
||||
|
||||
func (f *File) parseResponse(reader io.Reader) ([]os.FileInfo, error) {
|
||||
decoder := xml.NewDecoder(reader)
|
||||
result := listObjectsResult{}
|
||||
var err error
|
||||
err = decoder.Decode(&result)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
infos := make([]os.FileInfo, len(result.Contents)+len(result.Directories))
|
||||
var size int64
|
||||
var name string
|
||||
var is_dir bool
|
||||
for i, content := range result.Contents {
|
||||
c := content
|
||||
c.ETag = strings.Trim(c.ETag, `"`)
|
||||
size, _ = strconv.ParseInt(c.Size, 10, 0)
|
||||
if size == 0 && strings.HasSuffix(c.Key, "/") {
|
||||
name = strings.TrimRight(c.Key, "/")
|
||||
is_dir = true
|
||||
} else {
|
||||
name = c.Key
|
||||
is_dir = false
|
||||
}
|
||||
infos[i] = &fileInfo{
|
||||
name: name,
|
||||
size: size,
|
||||
dir: is_dir,
|
||||
sys: &c,
|
||||
}
|
||||
}
|
||||
for i, dir := range result.Directories {
|
||||
infos[len(result.Contents)+i] = &fileInfo{
|
||||
name: strings.TrimRight(dir, "/"),
|
||||
size: 0,
|
||||
dir: true,
|
||||
}
|
||||
}
|
||||
f.result = &result
|
||||
|
||||
return infos, nil
|
||||
}
|
||||
+267
@@ -0,0 +1,267 @@
|
||||
package s3util
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"encoding/xml"
|
||||
"github.com/kr/s3"
|
||||
"fmt"
|
||||
"io"
|
||||
"net/http"
|
||||
"net/url"
|
||||
"strconv"
|
||||
"sync"
|
||||
"syscall"
|
||||
"time"
|
||||
)
|
||||
|
||||
// defined by amazon
|
||||
const (
|
||||
minPartSize = 5 * 1024 * 1024
|
||||
maxPartSize = 1<<31 - 1 // for 32-bit use; amz max is 5GiB
|
||||
maxObjSize = 5 * 1024 * 1024 * 1024 * 1024
|
||||
maxNPart = 10000
|
||||
)
|
||||
|
||||
const (
|
||||
concurrency = 5
|
||||
nTry = 2
|
||||
)
|
||||
|
||||
type part struct {
|
||||
r io.ReadSeeker
|
||||
len int64
|
||||
|
||||
// read by xml encoder
|
||||
PartNumber int
|
||||
ETag string
|
||||
}
|
||||
|
||||
type uploader struct {
|
||||
s3 s3.Service
|
||||
keys s3.Keys
|
||||
url string
|
||||
client *http.Client
|
||||
UploadId string // written by xml decoder
|
||||
|
||||
bufsz int64
|
||||
buf []byte
|
||||
off int
|
||||
ch chan *part
|
||||
part int
|
||||
closed bool
|
||||
err error
|
||||
wg sync.WaitGroup
|
||||
|
||||
xml struct {
|
||||
XMLName string `xml:"CompleteMultipartUpload"`
|
||||
Part []*part
|
||||
}
|
||||
}
|
||||
|
||||
// Create creates an S3 object at url and sends multipart upload requests as
|
||||
// data is written.
|
||||
//
|
||||
// If h is not nil, each of its entries is added to the HTTP request header.
|
||||
// If c is nil, Create uses DefaultConfig.
|
||||
func Create(url string, h http.Header, c *Config) (io.WriteCloser, error) {
|
||||
if c == nil {
|
||||
c = DefaultConfig
|
||||
}
|
||||
return newUploader(url, h, c)
|
||||
}
|
||||
|
||||
// Sends an S3 multipart upload initiation request.
|
||||
// See http://docs.amazonwebservices.com/AmazonS3/latest/dev/mpuoverview.html.
|
||||
// This initial request returns an UploadId that we use to identify
|
||||
// subsequent PUT requests.
|
||||
func newUploader(url string, h http.Header, c *Config) (u *uploader, err error) {
|
||||
u = new(uploader)
|
||||
u.s3 = *c.Service
|
||||
u.url = url
|
||||
u.keys = *c.Keys
|
||||
u.client = c.Client
|
||||
if u.client == nil {
|
||||
u.client = http.DefaultClient
|
||||
}
|
||||
u.bufsz = minPartSize
|
||||
r, err := http.NewRequest("POST", url+"?uploads", nil)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
r.Header.Set("Date", time.Now().UTC().Format(http.TimeFormat))
|
||||
for k := range h {
|
||||
for _, v := range h[k] {
|
||||
r.Header.Add(k, v)
|
||||
}
|
||||
}
|
||||
u.s3.Sign(r, u.keys)
|
||||
resp, err := u.client.Do(r)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
defer resp.Body.Close()
|
||||
if resp.StatusCode != 200 {
|
||||
return nil, newRespError(resp)
|
||||
}
|
||||
err = xml.NewDecoder(resp.Body).Decode(u)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
u.ch = make(chan *part)
|
||||
for i := 0; i < concurrency; i++ {
|
||||
go u.worker()
|
||||
}
|
||||
return u, nil
|
||||
}
|
||||
|
||||
func (u *uploader) Write(p []byte) (n int, err error) {
|
||||
if u.closed {
|
||||
return 0, syscall.EINVAL
|
||||
}
|
||||
if u.err != nil {
|
||||
return 0, u.err
|
||||
}
|
||||
for n < len(p) {
|
||||
if cap(u.buf) == 0 {
|
||||
u.buf = make([]byte, int(u.bufsz))
|
||||
// Increase part size (1.001x).
|
||||
// This lets us reach the max object size (5TiB) while
|
||||
// still doing minimal buffering for small objects.
|
||||
u.bufsz = min(u.bufsz+u.bufsz/1000, maxPartSize)
|
||||
}
|
||||
r := copy(u.buf[u.off:], p[n:])
|
||||
u.off += r
|
||||
n += r
|
||||
if u.off == len(u.buf) {
|
||||
u.flush()
|
||||
}
|
||||
}
|
||||
return n, nil
|
||||
}
|
||||
|
||||
func (u *uploader) flush() {
|
||||
u.wg.Add(1)
|
||||
u.part++
|
||||
p := &part{bytes.NewReader(u.buf[:u.off]), int64(u.off), u.part, ""}
|
||||
u.xml.Part = append(u.xml.Part, p)
|
||||
u.ch <- p
|
||||
u.buf, u.off = nil, 0
|
||||
}
|
||||
|
||||
func (u *uploader) worker() {
|
||||
for p := range u.ch {
|
||||
u.retryUploadPart(p)
|
||||
}
|
||||
}
|
||||
|
||||
// Calls putPart up to nTry times to recover from transient errors.
|
||||
func (u *uploader) retryUploadPart(p *part) {
|
||||
defer u.wg.Done()
|
||||
defer func() { p.r = nil }() // free the large buffer
|
||||
var err error
|
||||
for i := 0; i < nTry; i++ {
|
||||
p.r.Seek(0, 0)
|
||||
err = u.putPart(p)
|
||||
if err == nil {
|
||||
return
|
||||
}
|
||||
}
|
||||
u.err = err
|
||||
}
|
||||
|
||||
// Uploads part p, reading its contents from p.r.
|
||||
// Stores the ETag in p.ETag.
|
||||
func (u *uploader) putPart(p *part) error {
|
||||
v := url.Values{}
|
||||
v.Set("partNumber", strconv.Itoa(p.PartNumber))
|
||||
v.Set("uploadId", u.UploadId)
|
||||
req, err := http.NewRequest("PUT", u.url+"?"+v.Encode(), p.r)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
req.ContentLength = p.len
|
||||
req.Header.Set("Date", time.Now().UTC().Format(http.TimeFormat))
|
||||
u.s3.Sign(req, u.keys)
|
||||
resp, err := u.client.Do(req)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
defer resp.Body.Close()
|
||||
if resp.StatusCode != 200 {
|
||||
return newRespError(resp)
|
||||
}
|
||||
s := resp.Header.Get("etag") // includes quote chars for some reason
|
||||
if len(s) < 2 {
|
||||
return fmt.Errorf("received invalid etag %q", s)
|
||||
}
|
||||
p.ETag = s[1 : len(s)-1]
|
||||
return nil
|
||||
}
|
||||
|
||||
func (u *uploader) Close() error {
|
||||
if u.closed {
|
||||
return syscall.EINVAL
|
||||
}
|
||||
if cap(u.buf) > 0 {
|
||||
u.flush()
|
||||
}
|
||||
u.wg.Wait()
|
||||
close(u.ch)
|
||||
u.closed = true
|
||||
if u.err != nil {
|
||||
u.abort()
|
||||
return u.err
|
||||
}
|
||||
|
||||
body, err := xml.Marshal(u.xml)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
b := bytes.NewBuffer(body)
|
||||
v := url.Values{}
|
||||
v.Set("uploadId", u.UploadId)
|
||||
req, err := http.NewRequest("POST", u.url+"?"+v.Encode(), b)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
req.Header.Set("Date", time.Now().UTC().Format(http.TimeFormat))
|
||||
u.s3.Sign(req, u.keys)
|
||||
resp, err := u.client.Do(req)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if resp.StatusCode != 200 {
|
||||
return newRespError(resp)
|
||||
}
|
||||
resp.Body.Close()
|
||||
return nil
|
||||
}
|
||||
|
||||
func (u *uploader) abort() {
|
||||
// TODO(kr): devise a reasonable way to report an error here in addition
|
||||
// to the error that caused the abort.
|
||||
v := url.Values{}
|
||||
v.Set("uploadId", u.UploadId)
|
||||
s := u.url + "?" + v.Encode()
|
||||
req, err := http.NewRequest("DELETE", s, nil)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
req.Header.Set("Date", time.Now().UTC().Format(http.TimeFormat))
|
||||
u.s3.Sign(req, u.keys)
|
||||
resp, err := u.client.Do(req)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
defer resp.Body.Close()
|
||||
if resp.StatusCode != 200 {
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
func min(a, b int64) int64 {
|
||||
if a < b {
|
||||
return a
|
||||
}
|
||||
return b
|
||||
}
|
||||
+200
@@ -0,0 +1,200 @@
|
||||
// Package s3 signs HTTP requests for Amazon S3 and compatible services.
|
||||
package s3
|
||||
|
||||
// See
|
||||
// http://docs.amazonwebservices.com/AmazonS3/2006-03-01/dev/RESTAuthentication.html.
|
||||
|
||||
import (
|
||||
"crypto/hmac"
|
||||
"crypto/sha1"
|
||||
"encoding/base64"
|
||||
"io"
|
||||
"net/http"
|
||||
"sort"
|
||||
"strings"
|
||||
)
|
||||
|
||||
var signParams = map[string]bool{
|
||||
"acl": true,
|
||||
"delete": true,
|
||||
"lifecycle": true,
|
||||
"location": true,
|
||||
"logging": true,
|
||||
"notification": true,
|
||||
"partNumber": true,
|
||||
"policy": true,
|
||||
"requestPayment": true,
|
||||
"response-cache-control": true,
|
||||
"response-content-disposition": true,
|
||||
"response-content-encoding": true,
|
||||
"response-content-language": true,
|
||||
"response-content-type": true,
|
||||
"response-expires": true,
|
||||
"restore": true,
|
||||
"torrent": true,
|
||||
"uploadId": true,
|
||||
"uploads": true,
|
||||
"versionId": true,
|
||||
"versioning": true,
|
||||
"versions": true,
|
||||
"website": true,
|
||||
}
|
||||
|
||||
// Keys holds a set of Amazon Security Credentials.
|
||||
type Keys struct {
|
||||
AccessKey string
|
||||
SecretKey string
|
||||
|
||||
// SecurityToken is used for temporary security credentials.
|
||||
// If set, it will be added to header field X-Amz-Security-Token
|
||||
// before signing a request.
|
||||
SecurityToken string
|
||||
// See http://docs.aws.amazon.com/AmazonS3/latest/dev/MakingRequests.html#TypesofSecurityCredentials
|
||||
}
|
||||
|
||||
// IdentityBucket returns subdomain.
|
||||
// It is designed to be used with S3-compatible services that
|
||||
// treat the entire subdomain as the bucket name, for example
|
||||
// storage.io.
|
||||
func IdentityBucket(subdomain string) string {
|
||||
return subdomain
|
||||
}
|
||||
|
||||
// AmazonBucket returns everything up to the last '.' in subdomain.
|
||||
// It is designed to be used with the Amazon service.
|
||||
// "johnsmith.s3" becomes "johnsmith"
|
||||
// "johnsmith.s3-eu-west-1" becomes "johnsmith"
|
||||
// "www.example.com.s3" becomes "www.example.com"
|
||||
func AmazonBucket(subdomain string) string {
|
||||
if i := strings.LastIndex(subdomain, "."); i != -1 {
|
||||
return subdomain[:i]
|
||||
}
|
||||
return ""
|
||||
}
|
||||
|
||||
// DefaultService is the default Service used by Sign.
|
||||
var DefaultService = &Service{Domain: "amazonaws.com"}
|
||||
|
||||
// Sign signs an HTTP request with the given S3 keys.
|
||||
//
|
||||
// This function is a wrapper around DefaultService.Sign.
|
||||
func Sign(r *http.Request, k Keys) {
|
||||
DefaultService.Sign(r, k)
|
||||
}
|
||||
|
||||
// Service represents an S3-compatible service.
|
||||
type Service struct {
|
||||
// Domain is the service's root domain. It is used to extract
|
||||
// the subdomain from an http.Request before passing the
|
||||
// subdomain to Bucket.
|
||||
Domain string
|
||||
|
||||
// Bucket derives the bucket name from a subdomain.
|
||||
// If nil, AmazonBucket is used.
|
||||
Bucket func(subdomain string) string
|
||||
}
|
||||
|
||||
// Sign signs an HTTP request with the given S3 keys for use on service s.
|
||||
func (s *Service) Sign(r *http.Request, k Keys) {
|
||||
if k.SecurityToken != "" {
|
||||
r.Header.Set("X-Amz-Security-Token", k.SecurityToken)
|
||||
}
|
||||
h := hmac.New(sha1.New, []byte(k.SecretKey))
|
||||
s.writeSigData(h, r)
|
||||
sig := make([]byte, base64.StdEncoding.EncodedLen(h.Size()))
|
||||
base64.StdEncoding.Encode(sig, h.Sum(nil))
|
||||
r.Header.Set("Authorization", "AWS "+k.AccessKey+":"+string(sig))
|
||||
}
|
||||
|
||||
func (s *Service) writeSigData(w io.Writer, r *http.Request) {
|
||||
w.Write([]byte(r.Method))
|
||||
w.Write([]byte{'\n'})
|
||||
w.Write([]byte(r.Header.Get("content-md5")))
|
||||
w.Write([]byte{'\n'})
|
||||
w.Write([]byte(r.Header.Get("content-type")))
|
||||
w.Write([]byte{'\n'})
|
||||
if _, ok := r.Header["X-Amz-Date"]; !ok {
|
||||
w.Write([]byte(r.Header.Get("date")))
|
||||
}
|
||||
w.Write([]byte{'\n'})
|
||||
writeAmzHeaders(w, r)
|
||||
s.writeResource(w, r)
|
||||
}
|
||||
|
||||
func (s *Service) writeResource(w io.Writer, r *http.Request) {
|
||||
s.writeVhostBucket(w, strings.ToLower(r.Host))
|
||||
path := r.URL.RequestURI()
|
||||
if r.URL.RawQuery != "" {
|
||||
path = path[:len(path)-len(r.URL.RawQuery)-1]
|
||||
}
|
||||
w.Write([]byte(path))
|
||||
s.writeSubResource(w, r)
|
||||
}
|
||||
|
||||
func (s *Service) writeVhostBucket(w io.Writer, host string) {
|
||||
if i := strings.Index(host, ":"); i != -1 {
|
||||
host = host[:i]
|
||||
}
|
||||
|
||||
if host == s.Domain {
|
||||
// no vhost - do nothing
|
||||
} else if strings.HasSuffix(host, "."+s.Domain) {
|
||||
// vhost - bucket may be in prefix
|
||||
b := s.Bucket
|
||||
if b == nil {
|
||||
b = AmazonBucket
|
||||
}
|
||||
bucket := b(host[:len(host)-len(s.Domain)-1])
|
||||
|
||||
if bucket != "" {
|
||||
w.Write([]byte{'/'})
|
||||
w.Write([]byte(bucket))
|
||||
}
|
||||
} else {
|
||||
// cname - bucket is host
|
||||
w.Write([]byte{'/'})
|
||||
w.Write([]byte(host))
|
||||
}
|
||||
}
|
||||
|
||||
func (s *Service) writeSubResource(w io.Writer, r *http.Request) {
|
||||
var a []string
|
||||
for k, vs := range r.URL.Query() {
|
||||
if signParams[k] {
|
||||
for _, v := range vs {
|
||||
if v == "" {
|
||||
a = append(a, k)
|
||||
} else {
|
||||
a = append(a, k+"="+v)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
sort.Strings(a)
|
||||
var p byte = '?'
|
||||
for _, s := range a {
|
||||
w.Write([]byte{p})
|
||||
w.Write([]byte(s))
|
||||
p = '&'
|
||||
}
|
||||
}
|
||||
|
||||
func writeAmzHeaders(w io.Writer, r *http.Request) {
|
||||
var keys []string
|
||||
for k, _ := range r.Header {
|
||||
if strings.HasPrefix(strings.ToLower(k), "x-amz-") {
|
||||
keys = append(keys, k)
|
||||
}
|
||||
}
|
||||
|
||||
sort.Strings(keys)
|
||||
var a []string
|
||||
for _, k := range keys {
|
||||
v := r.Header[k]
|
||||
a = append(a, strings.ToLower(k)+":"+strings.Join(v, ","))
|
||||
}
|
||||
for _, h := range a {
|
||||
w.Write([]byte(h))
|
||||
w.Write([]byte{'\n'})
|
||||
}
|
||||
}
|
||||
Generated
Vendored
-103
@@ -1,103 +0,0 @@
|
||||
package assertions
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
"time"
|
||||
)
|
||||
|
||||
func TestShouldContain(t *testing.T) {
|
||||
fail(t, so([]int{}, ShouldContain), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so([]int{}, ShouldContain, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(Thing1{}, ShouldContain, 1), "You must provide a valid container (was assertions.Thing1)!")
|
||||
fail(t, so(nil, ShouldContain, 1), "You must provide a valid container (was <nil>)!")
|
||||
fail(t, so([]int{1}, ShouldContain, 2), "Expected the container ([]int) to contain: '2' (but it didn't)!")
|
||||
|
||||
pass(t, so([]int{1}, ShouldContain, 1))
|
||||
pass(t, so([]int{1, 2, 3}, ShouldContain, 2))
|
||||
}
|
||||
|
||||
func TestShouldNotContain(t *testing.T) {
|
||||
fail(t, so([]int{}, ShouldNotContain), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so([]int{}, ShouldNotContain, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(Thing1{}, ShouldNotContain, 1), "You must provide a valid container (was assertions.Thing1)!")
|
||||
fail(t, so(nil, ShouldNotContain, 1), "You must provide a valid container (was <nil>)!")
|
||||
|
||||
fail(t, so([]int{1}, ShouldNotContain, 1), "Expected the container ([]int) NOT to contain: '1' (but it did)!")
|
||||
fail(t, so([]int{1, 2, 3}, ShouldNotContain, 2), "Expected the container ([]int) NOT to contain: '2' (but it did)!")
|
||||
|
||||
pass(t, so([]int{1}, ShouldNotContain, 2))
|
||||
}
|
||||
|
||||
func TestShouldBeIn(t *testing.T) {
|
||||
fail(t, so(4, ShouldBeIn), shouldHaveProvidedCollectionMembers)
|
||||
|
||||
container := []int{1, 2, 3, 4}
|
||||
pass(t, so(4, ShouldBeIn, container))
|
||||
pass(t, so(4, ShouldBeIn, 1, 2, 3, 4))
|
||||
|
||||
fail(t, so(4, ShouldBeIn, 1, 2, 3), "Expected '4' to be in the container ([]interface {}, but it wasn't)!")
|
||||
fail(t, so(4, ShouldBeIn, []int{1, 2, 3}), "Expected '4' to be in the container ([]int, but it wasn't)!")
|
||||
}
|
||||
|
||||
func TestShouldNotBeIn(t *testing.T) {
|
||||
fail(t, so(4, ShouldNotBeIn), shouldHaveProvidedCollectionMembers)
|
||||
|
||||
container := []int{1, 2, 3, 4}
|
||||
pass(t, so(42, ShouldNotBeIn, container))
|
||||
pass(t, so(42, ShouldNotBeIn, 1, 2, 3, 4))
|
||||
|
||||
fail(t, so(2, ShouldNotBeIn, 1, 2, 3), "Expected '2' NOT to be in the container ([]interface {}, but it was)!")
|
||||
fail(t, so(2, ShouldNotBeIn, []int{1, 2, 3}), "Expected '2' NOT to be in the container ([]int, but it was)!")
|
||||
}
|
||||
|
||||
func TestShouldBeEmpty(t *testing.T) {
|
||||
fail(t, so(1, ShouldBeEmpty, 2, 3), "This assertion requires exactly 0 comparison values (you provided 2).")
|
||||
|
||||
pass(t, so([]int{}, ShouldBeEmpty)) // empty slice
|
||||
pass(t, so([]interface{}{}, ShouldBeEmpty)) // empty slice
|
||||
pass(t, so(map[string]int{}, ShouldBeEmpty)) // empty map
|
||||
pass(t, so("", ShouldBeEmpty)) // empty string
|
||||
pass(t, so(&[]int{}, ShouldBeEmpty)) // pointer to empty slice
|
||||
pass(t, so(&[0]int{}, ShouldBeEmpty)) // pointer to empty array
|
||||
pass(t, so(nil, ShouldBeEmpty)) // nil
|
||||
pass(t, so(make(chan string), ShouldBeEmpty)) // empty channel
|
||||
|
||||
fail(t, so([]int{1}, ShouldBeEmpty), "Expected [1] to be empty (but it wasn't)!") // non-empty slice
|
||||
fail(t, so([]interface{}{1}, ShouldBeEmpty), "Expected [1] to be empty (but it wasn't)!") // non-empty slice
|
||||
fail(t, so(map[string]int{"hi": 0}, ShouldBeEmpty), "Expected map[hi:0] to be empty (but it wasn't)!") // non-empty map
|
||||
fail(t, so("hi", ShouldBeEmpty), "Expected hi to be empty (but it wasn't)!") // non-empty string
|
||||
fail(t, so(&[]int{1}, ShouldBeEmpty), "Expected &[1] to be empty (but it wasn't)!") // pointer to non-empty slice
|
||||
fail(t, so(&[1]int{1}, ShouldBeEmpty), "Expected &[1] to be empty (but it wasn't)!") // pointer to non-empty array
|
||||
c := make(chan int, 1) // non-empty channel
|
||||
go func() { c <- 1 }()
|
||||
time.Sleep(time.Millisecond)
|
||||
fail(t, so(c, ShouldBeEmpty), fmt.Sprintf("Expected %+v to be empty (but it wasn't)!", c))
|
||||
}
|
||||
|
||||
func TestShouldNotBeEmpty(t *testing.T) {
|
||||
fail(t, so(1, ShouldNotBeEmpty, 2, 3), "This assertion requires exactly 0 comparison values (you provided 2).")
|
||||
|
||||
fail(t, so([]int{}, ShouldNotBeEmpty), "Expected [] to NOT be empty (but it was)!") // empty slice
|
||||
fail(t, so([]interface{}{}, ShouldNotBeEmpty), "Expected [] to NOT be empty (but it was)!") // empty slice
|
||||
fail(t, so(map[string]int{}, ShouldNotBeEmpty), "Expected map[] to NOT be empty (but it was)!") // empty map
|
||||
fail(t, so("", ShouldNotBeEmpty), "Expected to NOT be empty (but it was)!") // empty string
|
||||
fail(t, so(&[]int{}, ShouldNotBeEmpty), "Expected &[] to NOT be empty (but it was)!") // pointer to empty slice
|
||||
fail(t, so(&[0]int{}, ShouldNotBeEmpty), "Expected &[] to NOT be empty (but it was)!") // pointer to empty array
|
||||
fail(t, so(nil, ShouldNotBeEmpty), "Expected <nil> to NOT be empty (but it was)!") // nil
|
||||
c := make(chan int, 0) // non-empty channel
|
||||
fail(t, so(c, ShouldNotBeEmpty), fmt.Sprintf("Expected %+v to NOT be empty (but it was)!", c)) // empty channel
|
||||
|
||||
pass(t, so([]int{1}, ShouldNotBeEmpty)) // non-empty slice
|
||||
pass(t, so([]interface{}{1}, ShouldNotBeEmpty)) // non-empty slice
|
||||
pass(t, so(map[string]int{"hi": 0}, ShouldNotBeEmpty)) // non-empty map
|
||||
pass(t, so("hi", ShouldNotBeEmpty)) // non-empty string
|
||||
pass(t, so(&[]int{1}, ShouldNotBeEmpty)) // pointer to non-empty slice
|
||||
pass(t, so(&[1]int{1}, ShouldNotBeEmpty)) // pointer to non-empty array
|
||||
c = make(chan int, 1)
|
||||
go func() { c <- 1 }()
|
||||
time.Sleep(time.Millisecond)
|
||||
pass(t, so(c, ShouldNotBeEmpty))
|
||||
}
|
||||
Generated
Vendored
-267
@@ -1,267 +0,0 @@
|
||||
package assertions
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"reflect"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestShouldEqual(t *testing.T) {
|
||||
serializer = newFakeSerializer()
|
||||
|
||||
fail(t, so(1, ShouldEqual), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(1, ShouldEqual, 1, 2), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
fail(t, so(1, ShouldEqual, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
pass(t, so(1, ShouldEqual, 1))
|
||||
fail(t, so(1, ShouldEqual, 2), "2|1|Expected: '2' Actual: '1' (Should be equal)")
|
||||
|
||||
pass(t, so(true, ShouldEqual, true))
|
||||
fail(t, so(true, ShouldEqual, false), "false|true|Expected: 'false' Actual: 'true' (Should be equal)")
|
||||
|
||||
pass(t, so("hi", ShouldEqual, "hi"))
|
||||
fail(t, so("hi", ShouldEqual, "bye"), "bye|hi|Expected: 'bye' Actual: 'hi' (Should be equal)")
|
||||
|
||||
pass(t, so(42, ShouldEqual, uint(42)))
|
||||
|
||||
fail(t, so(Thing1{"hi"}, ShouldEqual, Thing1{}), "{}|{hi}|Expected: '{}' Actual: '{hi}' (Should be equal)")
|
||||
fail(t, so(Thing1{"hi"}, ShouldEqual, Thing1{"hi"}), "{hi}|{hi}|Expected: '{hi}' Actual: '{hi}' (Should be equal)")
|
||||
fail(t, so(&Thing1{"hi"}, ShouldEqual, &Thing1{"hi"}), "&{hi}|&{hi}|Expected: '&{hi}' Actual: '&{hi}' (Should be equal)")
|
||||
|
||||
fail(t, so(Thing1{}, ShouldEqual, Thing2{}), "{}|{}|Expected: '{}' Actual: '{}' (Should be equal)")
|
||||
}
|
||||
|
||||
func TestShouldNotEqual(t *testing.T) {
|
||||
fail(t, so(1, ShouldNotEqual), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(1, ShouldNotEqual, 1, 2), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
fail(t, so(1, ShouldNotEqual, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
pass(t, so(1, ShouldNotEqual, 2))
|
||||
fail(t, so(1, ShouldNotEqual, 1), "Expected '1' to NOT equal '1' (but it did)!")
|
||||
|
||||
pass(t, so(true, ShouldNotEqual, false))
|
||||
fail(t, so(true, ShouldNotEqual, true), "Expected 'true' to NOT equal 'true' (but it did)!")
|
||||
|
||||
pass(t, so("hi", ShouldNotEqual, "bye"))
|
||||
fail(t, so("hi", ShouldNotEqual, "hi"), "Expected 'hi' to NOT equal 'hi' (but it did)!")
|
||||
|
||||
pass(t, so(&Thing1{"hi"}, ShouldNotEqual, &Thing1{"hi"}))
|
||||
pass(t, so(Thing1{"hi"}, ShouldNotEqual, Thing1{"hi"}))
|
||||
pass(t, so(Thing1{}, ShouldNotEqual, Thing1{}))
|
||||
pass(t, so(Thing1{}, ShouldNotEqual, Thing2{}))
|
||||
}
|
||||
|
||||
func TestShouldAlmostEqual(t *testing.T) {
|
||||
fail(t, so(1, ShouldAlmostEqual), "This assertion requires exactly one comparison value and an optional delta (you provided neither)")
|
||||
fail(t, so(1, ShouldAlmostEqual, 1, 2, 3), "This assertion requires exactly one comparison value and an optional delta (you provided more values)")
|
||||
|
||||
// with the default delta
|
||||
pass(t, so(1, ShouldAlmostEqual, .99999999999999))
|
||||
pass(t, so(1.3612499999999996, ShouldAlmostEqual, 1.36125))
|
||||
pass(t, so(0.7285312499999999, ShouldAlmostEqual, 0.72853125))
|
||||
fail(t, so(1, ShouldAlmostEqual, .99), "Expected '1' to almost equal '0.99' (but it didn't)!")
|
||||
|
||||
// with a different delta
|
||||
pass(t, so(100.0, ShouldAlmostEqual, 110.0, 10.0))
|
||||
fail(t, so(100.0, ShouldAlmostEqual, 111.0, 10.5), "Expected '100' to almost equal '111' (but it didn't)!")
|
||||
|
||||
// ints should work
|
||||
pass(t, so(100, ShouldAlmostEqual, 100.0))
|
||||
fail(t, so(100, ShouldAlmostEqual, 99.0), "Expected '100' to almost equal '99' (but it didn't)!")
|
||||
|
||||
// float32 should work
|
||||
pass(t, so(float64(100.0), ShouldAlmostEqual, float32(100.0)))
|
||||
fail(t, so(float32(100.0), ShouldAlmostEqual, 99.0, float32(0.1)), "Expected '100' to almost equal '99' (but it didn't)!")
|
||||
}
|
||||
|
||||
func TestShouldNotAlmostEqual(t *testing.T) {
|
||||
fail(t, so(1, ShouldNotAlmostEqual), "This assertion requires exactly one comparison value and an optional delta (you provided neither)")
|
||||
fail(t, so(1, ShouldNotAlmostEqual, 1, 2, 3), "This assertion requires exactly one comparison value and an optional delta (you provided more values)")
|
||||
|
||||
// with the default delta
|
||||
fail(t, so(1, ShouldNotAlmostEqual, .99999999999999), "Expected '1' to NOT almost equal '0.99999999999999' (but it did)!")
|
||||
fail(t, so(1.3612499999999996, ShouldNotAlmostEqual, 1.36125), "Expected '1.3612499999999996' to NOT almost equal '1.36125' (but it did)!")
|
||||
pass(t, so(1, ShouldNotAlmostEqual, .99))
|
||||
|
||||
// with a different delta
|
||||
fail(t, so(100.0, ShouldNotAlmostEqual, 110.0, 10.0), "Expected '100' to NOT almost equal '110' (but it did)!")
|
||||
pass(t, so(100.0, ShouldNotAlmostEqual, 111.0, 10.5))
|
||||
|
||||
// ints should work
|
||||
fail(t, so(100, ShouldNotAlmostEqual, 100.0), "Expected '100' to NOT almost equal '100' (but it did)!")
|
||||
pass(t, so(100, ShouldNotAlmostEqual, 99.0))
|
||||
|
||||
// float32 should work
|
||||
fail(t, so(float64(100.0), ShouldNotAlmostEqual, float32(100.0)), "Expected '100' to NOT almost equal '100' (but it did)!")
|
||||
pass(t, so(float32(100.0), ShouldNotAlmostEqual, 99.0, float32(0.1)))
|
||||
}
|
||||
|
||||
func TestShouldResemble(t *testing.T) {
|
||||
serializer = newFakeSerializer()
|
||||
|
||||
fail(t, so(Thing1{"hi"}, ShouldResemble), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(Thing1{"hi"}, ShouldResemble, Thing1{"hi"}, Thing1{"hi"}), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
|
||||
pass(t, so(Thing1{"hi"}, ShouldResemble, Thing1{"hi"}))
|
||||
fail(t, so(Thing1{"hi"}, ShouldResemble, Thing1{"bye"}), "{bye}|{hi}|Expected: 'assertions.Thing1{a:\"bye\"}' Actual: 'assertions.Thing1{a:\"hi\"}' (Should resemble)!")
|
||||
|
||||
var (
|
||||
a []int
|
||||
b []int = []int{}
|
||||
)
|
||||
|
||||
fail(t, so(a, ShouldResemble, b), "[]|[]|Expected: '[]int{}' Actual: '[]int(nil)' (Should resemble)!")
|
||||
fail(t, so(2, ShouldResemble, 1), "1|2|Expected: '1' Actual: '2' (Should resemble)!")
|
||||
|
||||
fail(t, so(StringStringMapAlias{"hi": "bye"}, ShouldResemble, map[string]string{"hi": "bye"}),
|
||||
"map[hi:bye]|map[hi:bye]|Expected: 'map[string]string{\"hi\":\"bye\"}' Actual: 'assertions.StringStringMapAlias{\"hi\":\"bye\"}' (Should resemble)!")
|
||||
fail(t, so(StringSliceAlias{"hi", "bye"}, ShouldResemble, []string{"hi", "bye"}),
|
||||
"[hi bye]|[hi bye]|Expected: '[]string{\"hi\", \"bye\"}' Actual: 'assertions.StringSliceAlias{\"hi\", \"bye\"}' (Should resemble)!")
|
||||
|
||||
// some types come out looking the same when represented with "%#v" so we show type mismatch info:
|
||||
fail(t, so(StringAlias("hi"), ShouldResemble, "hi"), "hi|hi|Expected: '\"hi\"' Actual: '\"hi\"' (Type mismatch: 'string' vs 'assertions.StringAlias')!")
|
||||
fail(t, so(IntAlias(42), ShouldResemble, 42), "42|42|Expected: '42' Actual: '42' (Type mismatch: 'int' vs 'assertions.IntAlias')!")
|
||||
}
|
||||
|
||||
func TestShouldNotResemble(t *testing.T) {
|
||||
fail(t, so(Thing1{"hi"}, ShouldNotResemble), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(Thing1{"hi"}, ShouldNotResemble, Thing1{"hi"}, Thing1{"hi"}), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
|
||||
pass(t, so(Thing1{"hi"}, ShouldNotResemble, Thing1{"bye"}))
|
||||
fail(t, so(Thing1{"hi"}, ShouldNotResemble, Thing1{"hi"}),
|
||||
"Expected 'assertions.Thing1{a:\"hi\"}' to NOT resemble 'assertions.Thing1{a:\"hi\"}' (but it did)!")
|
||||
|
||||
pass(t, so(map[string]string{"hi": "bye"}, ShouldResemble, map[string]string{"hi": "bye"}))
|
||||
pass(t, so(IntAlias(42), ShouldNotResemble, 42))
|
||||
|
||||
pass(t, so(StringSliceAlias{"hi", "bye"}, ShouldNotResemble, []string{"hi", "bye"}))
|
||||
}
|
||||
|
||||
func TestShouldPointTo(t *testing.T) {
|
||||
serializer = newFakeSerializer()
|
||||
|
||||
t1 := &Thing1{}
|
||||
t2 := t1
|
||||
t3 := &Thing1{}
|
||||
|
||||
pointer1 := reflect.ValueOf(t1).Pointer()
|
||||
pointer3 := reflect.ValueOf(t3).Pointer()
|
||||
|
||||
fail(t, so(t1, ShouldPointTo), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(t1, ShouldPointTo, t2, t3), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
|
||||
pass(t, so(t1, ShouldPointTo, t2))
|
||||
fail(t, so(t1, ShouldPointTo, t3), fmt.Sprintf(
|
||||
"%v|%v|Expected '&{a:}' (address: '%v') and '&{a:}' (address: '%v') to be the same address (but their weren't)!",
|
||||
pointer3, pointer1, pointer1, pointer3))
|
||||
|
||||
t4 := Thing1{}
|
||||
t5 := t4
|
||||
|
||||
fail(t, so(t4, ShouldPointTo, t5), "Both arguments should be pointers (the first was not)!")
|
||||
fail(t, so(&t4, ShouldPointTo, t5), "Both arguments should be pointers (the second was not)!")
|
||||
fail(t, so(nil, ShouldPointTo, nil), "Both arguments should be pointers (the first was nil)!")
|
||||
fail(t, so(&t4, ShouldPointTo, nil), "Both arguments should be pointers (the second was nil)!")
|
||||
}
|
||||
|
||||
func TestShouldNotPointTo(t *testing.T) {
|
||||
t1 := &Thing1{}
|
||||
t2 := t1
|
||||
t3 := &Thing1{}
|
||||
|
||||
pointer1 := reflect.ValueOf(t1).Pointer()
|
||||
|
||||
fail(t, so(t1, ShouldNotPointTo), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(t1, ShouldNotPointTo, t2, t3), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
|
||||
pass(t, so(t1, ShouldNotPointTo, t3))
|
||||
fail(t, so(t1, ShouldNotPointTo, t2), fmt.Sprintf("Expected '&{a:}' and '&{a:}' to be different references (but they matched: '%v')!", pointer1))
|
||||
|
||||
t4 := Thing1{}
|
||||
t5 := t4
|
||||
|
||||
fail(t, so(t4, ShouldNotPointTo, t5), "Both arguments should be pointers (the first was not)!")
|
||||
fail(t, so(&t4, ShouldNotPointTo, t5), "Both arguments should be pointers (the second was not)!")
|
||||
fail(t, so(nil, ShouldNotPointTo, nil), "Both arguments should be pointers (the first was nil)!")
|
||||
fail(t, so(&t4, ShouldNotPointTo, nil), "Both arguments should be pointers (the second was nil)!")
|
||||
}
|
||||
|
||||
func TestShouldBeNil(t *testing.T) {
|
||||
fail(t, so(nil, ShouldBeNil, nil, nil, nil), "This assertion requires exactly 0 comparison values (you provided 3).")
|
||||
fail(t, so(nil, ShouldBeNil, nil), "This assertion requires exactly 0 comparison values (you provided 1).")
|
||||
|
||||
pass(t, so(nil, ShouldBeNil))
|
||||
fail(t, so(1, ShouldBeNil), "Expected: nil Actual: '1'")
|
||||
|
||||
var thing Thinger
|
||||
pass(t, so(thing, ShouldBeNil))
|
||||
thing = &Thing{}
|
||||
fail(t, so(thing, ShouldBeNil), "Expected: nil Actual: '&{}'")
|
||||
|
||||
var thingOne *Thing1
|
||||
pass(t, so(thingOne, ShouldBeNil))
|
||||
|
||||
var nilSlice []int = nil
|
||||
pass(t, so(nilSlice, ShouldBeNil))
|
||||
|
||||
var nilMap map[string]string = nil
|
||||
pass(t, so(nilMap, ShouldBeNil))
|
||||
|
||||
var nilChannel chan int = nil
|
||||
pass(t, so(nilChannel, ShouldBeNil))
|
||||
|
||||
var nilFunc func() = nil
|
||||
pass(t, so(nilFunc, ShouldBeNil))
|
||||
|
||||
var nilInterface interface{} = nil
|
||||
pass(t, so(nilInterface, ShouldBeNil))
|
||||
}
|
||||
|
||||
func TestShouldNotBeNil(t *testing.T) {
|
||||
fail(t, so(nil, ShouldNotBeNil, nil, nil, nil), "This assertion requires exactly 0 comparison values (you provided 3).")
|
||||
fail(t, so(nil, ShouldNotBeNil, nil), "This assertion requires exactly 0 comparison values (you provided 1).")
|
||||
|
||||
fail(t, so(nil, ShouldNotBeNil), "Expected '<nil>' to NOT be nil (but it was)!")
|
||||
pass(t, so(1, ShouldNotBeNil))
|
||||
|
||||
var thing Thinger
|
||||
fail(t, so(thing, ShouldNotBeNil), "Expected '<nil>' to NOT be nil (but it was)!")
|
||||
thing = &Thing{}
|
||||
pass(t, so(thing, ShouldNotBeNil))
|
||||
}
|
||||
|
||||
func TestShouldBeTrue(t *testing.T) {
|
||||
fail(t, so(true, ShouldBeTrue, 1, 2, 3), "This assertion requires exactly 0 comparison values (you provided 3).")
|
||||
fail(t, so(true, ShouldBeTrue, 1), "This assertion requires exactly 0 comparison values (you provided 1).")
|
||||
|
||||
fail(t, so(false, ShouldBeTrue), "Expected: true Actual: false")
|
||||
fail(t, so(1, ShouldBeTrue), "Expected: true Actual: 1")
|
||||
pass(t, so(true, ShouldBeTrue))
|
||||
}
|
||||
|
||||
func TestShouldBeFalse(t *testing.T) {
|
||||
fail(t, so(false, ShouldBeFalse, 1, 2, 3), "This assertion requires exactly 0 comparison values (you provided 3).")
|
||||
fail(t, so(false, ShouldBeFalse, 1), "This assertion requires exactly 0 comparison values (you provided 1).")
|
||||
|
||||
fail(t, so(true, ShouldBeFalse), "Expected: false Actual: true")
|
||||
fail(t, so(1, ShouldBeFalse), "Expected: false Actual: 1")
|
||||
pass(t, so(false, ShouldBeFalse))
|
||||
}
|
||||
|
||||
func TestShouldBeZeroValue(t *testing.T) {
|
||||
serializer = newFakeSerializer()
|
||||
|
||||
fail(t, so(0, ShouldBeZeroValue, 1, 2, 3), "This assertion requires exactly 0 comparison values (you provided 3).")
|
||||
fail(t, so(false, ShouldBeZeroValue, true), "This assertion requires exactly 0 comparison values (you provided 1).")
|
||||
|
||||
fail(t, so(1, ShouldBeZeroValue), "0|1|'1' should have been the zero value") //"Expected: (zero value) Actual: 1")
|
||||
fail(t, so(true, ShouldBeZeroValue), "false|true|'true' should have been the zero value") //"Expected: (zero value) Actual: true")
|
||||
fail(t, so("123", ShouldBeZeroValue), "|123|'123' should have been the zero value") //"Expected: (zero value) Actual: 123")
|
||||
fail(t, so(" ", ShouldBeZeroValue), "| |' ' should have been the zero value") //"Expected: (zero value) Actual: ")
|
||||
fail(t, so([]string{"Nonempty"}, ShouldBeZeroValue), "[]|[Nonempty]|'[Nonempty]' should have been the zero value") //"Expected: (zero value) Actual: [Nonempty]")
|
||||
fail(t, so(struct{ a string }{a: "asdf"}, ShouldBeZeroValue), "{}|{asdf}|'{a:asdf}' should have been the zero value")
|
||||
pass(t, so(0, ShouldBeZeroValue))
|
||||
pass(t, so(false, ShouldBeZeroValue))
|
||||
pass(t, so("", ShouldBeZeroValue))
|
||||
pass(t, so(struct{}{}, ShouldBeZeroValue))
|
||||
}
|
||||
Generated
Vendored
-110
@@ -1,110 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"errors"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type allOfFakeMatcher struct {
|
||||
desc string
|
||||
err error
|
||||
}
|
||||
|
||||
func (m *allOfFakeMatcher) Matches(c interface{}) error {
|
||||
return m.err
|
||||
}
|
||||
|
||||
func (m *allOfFakeMatcher) Description() string {
|
||||
return m.desc
|
||||
}
|
||||
|
||||
type AllOfTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&AllOfTest{}) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *AllOfTest) DescriptionWithEmptySet() {
|
||||
m := AllOf()
|
||||
ExpectEq("is anything", m.Description())
|
||||
}
|
||||
|
||||
func (t *AllOfTest) DescriptionWithOneMatcher() {
|
||||
m := AllOf(&allOfFakeMatcher{"taco", errors.New("")})
|
||||
ExpectEq("taco", m.Description())
|
||||
}
|
||||
|
||||
func (t *AllOfTest) DescriptionWithMultipleMatchers() {
|
||||
m := AllOf(
|
||||
&allOfFakeMatcher{"taco", errors.New("")},
|
||||
&allOfFakeMatcher{"burrito", errors.New("")},
|
||||
&allOfFakeMatcher{"enchilada", errors.New("")})
|
||||
|
||||
ExpectEq("taco, and burrito, and enchilada", m.Description())
|
||||
}
|
||||
|
||||
func (t *AllOfTest) EmptySet() {
|
||||
m := AllOf()
|
||||
err := m.Matches(17)
|
||||
|
||||
ExpectEq(nil, err)
|
||||
}
|
||||
|
||||
func (t *AllOfTest) OneMatcherReturnsFatalErrorAndSomeOthersFail() {
|
||||
m := AllOf(
|
||||
&allOfFakeMatcher{"", errors.New("")},
|
||||
&allOfFakeMatcher{"", NewFatalError("taco")},
|
||||
&allOfFakeMatcher{"", errors.New("")},
|
||||
&allOfFakeMatcher{"", nil})
|
||||
|
||||
err := m.Matches(17)
|
||||
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("taco")))
|
||||
}
|
||||
|
||||
func (t *AllOfTest) OneMatcherReturnsNonFatalAndOthersSayTrue() {
|
||||
m := AllOf(
|
||||
&allOfFakeMatcher{"", nil},
|
||||
&allOfFakeMatcher{"", errors.New("taco")},
|
||||
&allOfFakeMatcher{"", nil})
|
||||
|
||||
err := m.Matches(17)
|
||||
|
||||
ExpectFalse(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("taco")))
|
||||
}
|
||||
|
||||
func (t *AllOfTest) AllMatchersSayTrue() {
|
||||
m := AllOf(
|
||||
&allOfFakeMatcher{"", nil},
|
||||
&allOfFakeMatcher{"", nil},
|
||||
&allOfFakeMatcher{"", nil})
|
||||
|
||||
err := m.Matches(17)
|
||||
|
||||
ExpectEq(nil, err)
|
||||
}
|
||||
Generated
Vendored
-121
@@ -1,121 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"errors"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type fakeAnyOfMatcher struct {
|
||||
desc string
|
||||
err error
|
||||
}
|
||||
|
||||
func (m *fakeAnyOfMatcher) Matches(c interface{}) error {
|
||||
return m.err
|
||||
}
|
||||
|
||||
func (m *fakeAnyOfMatcher) Description() string {
|
||||
return m.desc
|
||||
}
|
||||
|
||||
type AnyOfTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&AnyOfTest{}) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *AnyOfTest) EmptySet() {
|
||||
matcher := AnyOf()
|
||||
|
||||
err := matcher.Matches(0)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
}
|
||||
|
||||
func (t *AnyOfTest) OneTrue() {
|
||||
matcher := AnyOf(
|
||||
&fakeAnyOfMatcher{"", NewFatalError("foo")},
|
||||
17,
|
||||
&fakeAnyOfMatcher{"", errors.New("foo")},
|
||||
&fakeAnyOfMatcher{"", nil},
|
||||
&fakeAnyOfMatcher{"", errors.New("foo")},
|
||||
)
|
||||
|
||||
err := matcher.Matches(0)
|
||||
ExpectEq(nil, err)
|
||||
}
|
||||
|
||||
func (t *AnyOfTest) OneEqual() {
|
||||
matcher := AnyOf(
|
||||
&fakeAnyOfMatcher{"", NewFatalError("foo")},
|
||||
&fakeAnyOfMatcher{"", errors.New("foo")},
|
||||
13,
|
||||
"taco",
|
||||
19,
|
||||
&fakeAnyOfMatcher{"", errors.New("foo")},
|
||||
)
|
||||
|
||||
err := matcher.Matches("taco")
|
||||
ExpectEq(nil, err)
|
||||
}
|
||||
|
||||
func (t *AnyOfTest) OneFatal() {
|
||||
matcher := AnyOf(
|
||||
&fakeAnyOfMatcher{"", errors.New("foo")},
|
||||
17,
|
||||
&fakeAnyOfMatcher{"", NewFatalError("taco")},
|
||||
&fakeAnyOfMatcher{"", errors.New("foo")},
|
||||
)
|
||||
|
||||
err := matcher.Matches(0)
|
||||
ExpectThat(err, Error(Equals("taco")))
|
||||
}
|
||||
|
||||
func (t *AnyOfTest) AllFalseAndNotEqual() {
|
||||
matcher := AnyOf(
|
||||
&fakeAnyOfMatcher{"", errors.New("foo")},
|
||||
17,
|
||||
&fakeAnyOfMatcher{"", errors.New("foo")},
|
||||
19,
|
||||
)
|
||||
|
||||
err := matcher.Matches(0)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
}
|
||||
|
||||
func (t *AnyOfTest) DescriptionForEmptySet() {
|
||||
matcher := AnyOf()
|
||||
ExpectEq("or()", matcher.Description())
|
||||
}
|
||||
|
||||
func (t *AnyOfTest) DescriptionForNonEmptySet() {
|
||||
matcher := AnyOf(
|
||||
&fakeAnyOfMatcher{"taco", nil},
|
||||
"burrito",
|
||||
&fakeAnyOfMatcher{"enchilada", nil},
|
||||
)
|
||||
|
||||
ExpectEq("or(taco, burrito, enchilada)", matcher.Description())
|
||||
}
|
||||
Generated
Vendored
-53
@@ -1,53 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type AnyTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&AnyTest{}) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *AnyTest) Description() {
|
||||
m := Any()
|
||||
ExpectEq("is anything", m.Description())
|
||||
}
|
||||
|
||||
func (t *AnyTest) Matches() {
|
||||
var err error
|
||||
m := Any()
|
||||
|
||||
err = m.Matches(nil)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches(17)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches("taco")
|
||||
ExpectEq(nil, err)
|
||||
}
|
||||
Generated
Vendored
-234
@@ -1,234 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type ContainsTest struct{}
|
||||
|
||||
func init() { RegisterTestSuite(&ContainsTest{}) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *ContainsTest) WrongTypeCandidates() {
|
||||
m := Contains("")
|
||||
ExpectEq("contains: ", m.Description())
|
||||
|
||||
var err error
|
||||
|
||||
// Nil candidate
|
||||
err = m.Matches(nil)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("array")))
|
||||
ExpectThat(err, Error(HasSubstr("slice")))
|
||||
|
||||
// String candidate
|
||||
err = m.Matches("")
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("array")))
|
||||
ExpectThat(err, Error(HasSubstr("slice")))
|
||||
|
||||
// Map candidate
|
||||
err = m.Matches(make(map[string]string))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("array")))
|
||||
ExpectThat(err, Error(HasSubstr("slice")))
|
||||
}
|
||||
|
||||
func (t *ContainsTest) NilArgument() {
|
||||
m := Contains(nil)
|
||||
ExpectEq("contains: is nil", m.Description())
|
||||
|
||||
var c interface{}
|
||||
var err error
|
||||
|
||||
// Empty array of pointers
|
||||
c = [...]*int{}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Empty slice of pointers
|
||||
c = []*int{}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Non-empty array of integers
|
||||
c = [...]int{17, 0, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Non-empty slice of integers
|
||||
c = []int{17, 0, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Non-matching array of pointers
|
||||
c = [...]*int{new(int), new(int)}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Non-matching slice of pointers
|
||||
c = []*int{new(int), new(int)}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Matching array of pointers
|
||||
c = [...]*int{new(int), nil, new(int)}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Matching slice of pointers
|
||||
c = []*int{new(int), nil, new(int)}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Non-matching slice of pointers from matching array
|
||||
someArray := [...]*int{new(int), nil, new(int)}
|
||||
c = someArray[0:1]
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
}
|
||||
|
||||
func (t *ContainsTest) StringArgument() {
|
||||
m := Contains("taco")
|
||||
ExpectEq("contains: taco", m.Description())
|
||||
|
||||
var c interface{}
|
||||
var err error
|
||||
|
||||
// Non-matching array of strings
|
||||
c = [...]string{"burrito", "enchilada"}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Non-matching slice of strings
|
||||
c = []string{"burrito", "enchilada"}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Matching array of strings
|
||||
c = [...]string{"burrito", "taco", "enchilada"}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Matching slice of strings
|
||||
c = []string{"burrito", "taco", "enchilada"}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Non-matching slice of strings from matching array
|
||||
someArray := [...]string{"burrito", "taco", "enchilada"}
|
||||
c = someArray[0:1]
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
}
|
||||
|
||||
func (t *ContainsTest) IntegerArgument() {
|
||||
m := Contains(int(17))
|
||||
ExpectEq("contains: 17", m.Description())
|
||||
|
||||
var c interface{}
|
||||
var err error
|
||||
|
||||
// Non-matching array of integers
|
||||
c = [...]int{13, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Non-matching slice of integers
|
||||
c = []int{13, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Matching array of integers
|
||||
c = [...]int{13, 17, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Matching slice of integers
|
||||
c = []int{13, 17, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Non-matching slice of integers from matching array
|
||||
someArray := [...]int{13, 17, 19}
|
||||
c = someArray[0:1]
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Non-matching array of floats
|
||||
c = [...]float32{13, 17.5, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Non-matching slice of floats
|
||||
c = []float32{13, 17.5, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Matching array of floats
|
||||
c = [...]float32{13, 17, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Matching slice of floats
|
||||
c = []float32{13, 17, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
}
|
||||
|
||||
func (t *ContainsTest) MatcherArgument() {
|
||||
m := Contains(HasSubstr("ac"))
|
||||
ExpectEq("contains: has substring \"ac\"", m.Description())
|
||||
|
||||
var c interface{}
|
||||
var err error
|
||||
|
||||
// Non-matching array of strings
|
||||
c = [...]string{"burrito", "enchilada"}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Non-matching slice of strings
|
||||
c = []string{"burrito", "enchilada"}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Matching array of strings
|
||||
c = [...]string{"burrito", "taco", "enchilada"}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Matching slice of strings
|
||||
c = []string{"burrito", "taco", "enchilada"}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Non-matching slice of strings from matching array
|
||||
someArray := [...]string{"burrito", "taco", "enchilada"}
|
||||
c = someArray[0:1]
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
}
|
||||
Generated
Vendored
-344
@@ -1,344 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"testing"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type DeepEqualsTest struct{}
|
||||
|
||||
func init() { RegisterTestSuite(&DeepEqualsTest{}) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *DeepEqualsTest) WrongTypeCandidateWithScalarValue() {
|
||||
var x int = 17
|
||||
m := DeepEquals(x)
|
||||
|
||||
var err error
|
||||
|
||||
// Nil candidate.
|
||||
err = m.Matches(nil)
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("<nil>")))
|
||||
|
||||
// Int alias candidate.
|
||||
type intAlias int
|
||||
err = m.Matches(intAlias(x))
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("intAlias")))
|
||||
|
||||
// String candidate.
|
||||
err = m.Matches("taco")
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("string")))
|
||||
|
||||
// Byte slice candidate.
|
||||
err = m.Matches([]byte{})
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("[]uint8")))
|
||||
|
||||
// Other slice candidate.
|
||||
err = m.Matches([]uint16{})
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("[]uint16")))
|
||||
|
||||
// Unsigned int candidate.
|
||||
err = m.Matches(uint(17))
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("uint")))
|
||||
}
|
||||
|
||||
func (t *DeepEqualsTest) WrongTypeCandidateWithByteSliceValue() {
|
||||
x := []byte{}
|
||||
m := DeepEquals(x)
|
||||
|
||||
var err error
|
||||
|
||||
// Nil candidate.
|
||||
err = m.Matches(nil)
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("<nil>")))
|
||||
|
||||
// String candidate.
|
||||
err = m.Matches("taco")
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("string")))
|
||||
|
||||
// Slice candidate with wrong value type.
|
||||
err = m.Matches([]uint16{})
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("[]uint16")))
|
||||
}
|
||||
|
||||
func (t *DeepEqualsTest) WrongTypeCandidateWithOtherSliceValue() {
|
||||
x := []uint16{}
|
||||
m := DeepEquals(x)
|
||||
|
||||
var err error
|
||||
|
||||
// Nil candidate.
|
||||
err = m.Matches(nil)
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("<nil>")))
|
||||
|
||||
// String candidate.
|
||||
err = m.Matches("taco")
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("string")))
|
||||
|
||||
// Byte slice candidate with wrong value type.
|
||||
err = m.Matches([]byte{})
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("[]uint8")))
|
||||
|
||||
// Other slice candidate with wrong value type.
|
||||
err = m.Matches([]uint32{})
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("[]uint32")))
|
||||
}
|
||||
|
||||
func (t *DeepEqualsTest) WrongTypeCandidateWithNilLiteralValue() {
|
||||
m := DeepEquals(nil)
|
||||
|
||||
var err error
|
||||
|
||||
// String candidate.
|
||||
err = m.Matches("taco")
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("string")))
|
||||
|
||||
// Nil byte slice candidate.
|
||||
err = m.Matches([]byte(nil))
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("[]uint8")))
|
||||
|
||||
// Nil other slice candidate.
|
||||
err = m.Matches([]uint16(nil))
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("type")))
|
||||
ExpectThat(err, Error(HasSubstr("[]uint16")))
|
||||
}
|
||||
|
||||
func (t *DeepEqualsTest) NilLiteralValue() {
|
||||
m := DeepEquals(nil)
|
||||
ExpectEq("deep equals: <nil>", m.Description())
|
||||
|
||||
var c interface{}
|
||||
var err error
|
||||
|
||||
// Nil literal candidate.
|
||||
c = nil
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
}
|
||||
|
||||
func (t *DeepEqualsTest) IntValue() {
|
||||
m := DeepEquals(int(17))
|
||||
ExpectEq("deep equals: 17", m.Description())
|
||||
|
||||
var c interface{}
|
||||
var err error
|
||||
|
||||
// Matching int.
|
||||
c = int(17)
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Non-matching int.
|
||||
c = int(18)
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
}
|
||||
|
||||
func (t *DeepEqualsTest) ByteSliceValue() {
|
||||
x := []byte{17, 19}
|
||||
m := DeepEquals(x)
|
||||
ExpectEq("deep equals: [17 19]", m.Description())
|
||||
|
||||
var c []byte
|
||||
var err error
|
||||
|
||||
// Matching.
|
||||
c = make([]byte, len(x))
|
||||
AssertEq(len(x), copy(c, x))
|
||||
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Nil slice.
|
||||
c = []byte(nil)
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("which is nil")))
|
||||
|
||||
// Prefix.
|
||||
AssertGt(len(x), 1)
|
||||
c = make([]byte, len(x)-1)
|
||||
AssertEq(len(x)-1, copy(c, x))
|
||||
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Suffix.
|
||||
c = make([]byte, len(x)+1)
|
||||
AssertEq(len(x), copy(c, x))
|
||||
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
}
|
||||
|
||||
func (t *DeepEqualsTest) OtherSliceValue() {
|
||||
x := []uint16{17, 19}
|
||||
m := DeepEquals(x)
|
||||
ExpectEq("deep equals: [17 19]", m.Description())
|
||||
|
||||
var c []uint16
|
||||
var err error
|
||||
|
||||
// Matching.
|
||||
c = make([]uint16, len(x))
|
||||
AssertEq(len(x), copy(c, x))
|
||||
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Nil slice.
|
||||
c = []uint16(nil)
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("which is nil")))
|
||||
|
||||
// Prefix.
|
||||
AssertGt(len(x), 1)
|
||||
c = make([]uint16, len(x)-1)
|
||||
AssertEq(len(x)-1, copy(c, x))
|
||||
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Suffix.
|
||||
c = make([]uint16, len(x)+1)
|
||||
AssertEq(len(x), copy(c, x))
|
||||
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
}
|
||||
|
||||
func (t *DeepEqualsTest) NilByteSliceValue() {
|
||||
x := []byte(nil)
|
||||
m := DeepEquals(x)
|
||||
ExpectEq("deep equals: <nil slice>", m.Description())
|
||||
|
||||
var c []byte
|
||||
var err error
|
||||
|
||||
// Nil slice.
|
||||
c = []byte(nil)
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Non-nil slice.
|
||||
c = []byte{}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
}
|
||||
|
||||
func (t *DeepEqualsTest) NilOtherSliceValue() {
|
||||
x := []uint16(nil)
|
||||
m := DeepEquals(x)
|
||||
ExpectEq("deep equals: <nil slice>", m.Description())
|
||||
|
||||
var c []uint16
|
||||
var err error
|
||||
|
||||
// Nil slice.
|
||||
c = []uint16(nil)
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Non-nil slice.
|
||||
c = []uint16{}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Benchmarks
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func benchmarkWithSize(b *testing.B, size int) {
|
||||
b.StopTimer()
|
||||
buf := bytes.Repeat([]byte{0x01}, size)
|
||||
bufCopy := make([]byte, size)
|
||||
copy(bufCopy, buf)
|
||||
|
||||
matcher := DeepEquals(buf)
|
||||
b.StartTimer()
|
||||
|
||||
for i := 0; i < b.N; i++ {
|
||||
matcher.Matches(bufCopy)
|
||||
}
|
||||
|
||||
b.SetBytes(int64(size))
|
||||
}
|
||||
|
||||
func BenchmarkShortByteSlice(b *testing.B) {
|
||||
benchmarkWithSize(b, 256)
|
||||
}
|
||||
|
||||
func BenchmarkLongByteSlice(b *testing.B) {
|
||||
benchmarkWithSize(b, 1<<24)
|
||||
}
|
||||
Generated
Vendored
-208
@@ -1,208 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type ElementsAreTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&ElementsAreTest{}) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *ElementsAreTest) EmptySet() {
|
||||
m := ElementsAre()
|
||||
ExpectEq("elements are: []", m.Description())
|
||||
|
||||
var c []interface{}
|
||||
var err error
|
||||
|
||||
// No candidates.
|
||||
c = []interface{}{}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// One candidate.
|
||||
c = []interface{}{17}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(HasSubstr("length 1")))
|
||||
}
|
||||
|
||||
func (t *ElementsAreTest) OneMatcher() {
|
||||
m := ElementsAre(LessThan(17))
|
||||
ExpectEq("elements are: [less than 17]", m.Description())
|
||||
|
||||
var c []interface{}
|
||||
var err error
|
||||
|
||||
// No candidates.
|
||||
c = []interface{}{}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(HasSubstr("length 0")))
|
||||
|
||||
// Matching candidate.
|
||||
c = []interface{}{16}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Non-matching candidate.
|
||||
c = []interface{}{19}
|
||||
err = m.Matches(c)
|
||||
ExpectNe(nil, err)
|
||||
|
||||
// Two candidates.
|
||||
c = []interface{}{17, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(HasSubstr("length 2")))
|
||||
}
|
||||
|
||||
func (t *ElementsAreTest) OneValue() {
|
||||
m := ElementsAre(17)
|
||||
ExpectEq("elements are: [17]", m.Description())
|
||||
|
||||
var c []interface{}
|
||||
var err error
|
||||
|
||||
// No candidates.
|
||||
c = []interface{}{}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(HasSubstr("length 0")))
|
||||
|
||||
// Matching int.
|
||||
c = []interface{}{int(17)}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Matching float.
|
||||
c = []interface{}{float32(17)}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Non-matching candidate.
|
||||
c = []interface{}{19}
|
||||
err = m.Matches(c)
|
||||
ExpectNe(nil, err)
|
||||
|
||||
// Two candidates.
|
||||
c = []interface{}{17, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(HasSubstr("length 2")))
|
||||
}
|
||||
|
||||
func (t *ElementsAreTest) MultipleElements() {
|
||||
m := ElementsAre("taco", LessThan(17))
|
||||
ExpectEq("elements are: [taco, less than 17]", m.Description())
|
||||
|
||||
var c []interface{}
|
||||
var err error
|
||||
|
||||
// One candidate.
|
||||
c = []interface{}{17}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(HasSubstr("length 1")))
|
||||
|
||||
// Both matching.
|
||||
c = []interface{}{"taco", 16}
|
||||
err = m.Matches(c)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// First non-matching.
|
||||
c = []interface{}{"burrito", 16}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("whose element 0 doesn't match")))
|
||||
|
||||
// Second non-matching.
|
||||
c = []interface{}{"taco", 17}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(Equals("whose element 1 doesn't match")))
|
||||
|
||||
// Three candidates.
|
||||
c = []interface{}{"taco", 17, 19}
|
||||
err = m.Matches(c)
|
||||
ExpectThat(err, Error(HasSubstr("length 3")))
|
||||
}
|
||||
|
||||
func (t *ElementsAreTest) ArrayCandidates() {
|
||||
m := ElementsAre("taco", LessThan(17))
|
||||
|
||||
var err error
|
||||
|
||||
// One candidate.
|
||||
err = m.Matches([1]interface{}{"taco"})
|
||||
ExpectThat(err, Error(HasSubstr("length 1")))
|
||||
|
||||
// Both matching.
|
||||
err = m.Matches([2]interface{}{"taco", 16})
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// First non-matching.
|
||||
err = m.Matches([2]interface{}{"burrito", 16})
|
||||
ExpectThat(err, Error(Equals("whose element 0 doesn't match")))
|
||||
}
|
||||
|
||||
func (t *ElementsAreTest) WrongTypeCandidate() {
|
||||
m := ElementsAre("taco")
|
||||
|
||||
var err error
|
||||
|
||||
// String candidate.
|
||||
err = m.Matches("taco")
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("array")))
|
||||
ExpectThat(err, Error(HasSubstr("slice")))
|
||||
|
||||
// Map candidate.
|
||||
err = m.Matches(map[string]string{})
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("array")))
|
||||
ExpectThat(err, Error(HasSubstr("slice")))
|
||||
|
||||
// Nil candidate.
|
||||
err = m.Matches(nil)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("array")))
|
||||
ExpectThat(err, Error(HasSubstr("slice")))
|
||||
}
|
||||
|
||||
func (t *ElementsAreTest) PropagatesFatality() {
|
||||
m := ElementsAre(LessThan(17))
|
||||
ExpectEq("elements are: [less than 17]", m.Description())
|
||||
|
||||
var c []interface{}
|
||||
var err error
|
||||
|
||||
// Non-fatal error.
|
||||
c = []interface{}{19}
|
||||
err = m.Matches(c)
|
||||
AssertNe(nil, err)
|
||||
ExpectFalse(isFatal(err))
|
||||
|
||||
// Fatal error.
|
||||
c = []interface{}{"taco"}
|
||||
err = m.Matches(c)
|
||||
AssertNe(nil, err)
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
Generated
Vendored
-3785
File diff suppressed because it is too large
Load Diff
Godeps/_workspace/src/github.com/smartystreets/goconvey/convey/assertions/oglematchers/error_test.go
Generated
Vendored
-92
@@ -1,92 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"errors"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type ErrorTest struct {
|
||||
matcherCalled bool
|
||||
suppliedCandidate interface{}
|
||||
wrappedError error
|
||||
|
||||
matcher Matcher
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&ErrorTest{}) }
|
||||
|
||||
func (t *ErrorTest) SetUp(i *TestInfo) {
|
||||
wrapped := &fakeMatcher{
|
||||
func(c interface{}) error {
|
||||
t.matcherCalled = true
|
||||
t.suppliedCandidate = c
|
||||
return t.wrappedError
|
||||
},
|
||||
"is foo",
|
||||
}
|
||||
|
||||
t.matcher = Error(wrapped)
|
||||
}
|
||||
|
||||
func isFatal(err error) bool {
|
||||
_, isFatal := err.(*FatalError)
|
||||
return isFatal
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *ErrorTest) Description() {
|
||||
ExpectThat(t.matcher.Description(), Equals("error is foo"))
|
||||
}
|
||||
|
||||
func (t *ErrorTest) CandidateIsNil() {
|
||||
err := t.matcher.Matches(nil)
|
||||
|
||||
ExpectThat(t.matcherCalled, Equals(false))
|
||||
ExpectThat(err.Error(), Equals("which is not an error"))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *ErrorTest) CandidateIsString() {
|
||||
err := t.matcher.Matches("taco")
|
||||
|
||||
ExpectThat(t.matcherCalled, Equals(false))
|
||||
ExpectThat(err.Error(), Equals("which is not an error"))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *ErrorTest) CallsWrappedMatcher() {
|
||||
candidate := errors.New("taco")
|
||||
t.matcher.Matches(candidate)
|
||||
|
||||
ExpectThat(t.matcherCalled, Equals(true))
|
||||
ExpectThat(t.suppliedCandidate, Equals("taco"))
|
||||
}
|
||||
|
||||
func (t *ErrorTest) ReturnsWrappedMatcherResult() {
|
||||
t.wrappedError = errors.New("burrito")
|
||||
err := t.matcher.Matches(errors.New(""))
|
||||
ExpectThat(err, Equals(t.wrappedError))
|
||||
}
|
||||
Generated
Vendored
-1059
File diff suppressed because it is too large
Load Diff
Generated
Vendored
-1079
File diff suppressed because it is too large
Load Diff
Generated
Vendored
-92
@@ -1,92 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type HasSubstrTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&HasSubstrTest{}) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *HasSubstrTest) Description() {
|
||||
matcher := HasSubstr("taco")
|
||||
ExpectThat(matcher.Description(), Equals("has substring \"taco\""))
|
||||
}
|
||||
|
||||
func (t *HasSubstrTest) CandidateIsNil() {
|
||||
matcher := HasSubstr("")
|
||||
err := matcher.Matches(nil)
|
||||
|
||||
ExpectThat(err, Error(Equals("which is not a string")))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *HasSubstrTest) CandidateIsInteger() {
|
||||
matcher := HasSubstr("")
|
||||
err := matcher.Matches(17)
|
||||
|
||||
ExpectThat(err, Error(Equals("which is not a string")))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *HasSubstrTest) CandidateIsByteSlice() {
|
||||
matcher := HasSubstr("")
|
||||
err := matcher.Matches([]byte{17})
|
||||
|
||||
ExpectThat(err, Error(Equals("which is not a string")))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *HasSubstrTest) CandidateDoesntHaveSubstring() {
|
||||
matcher := HasSubstr("taco")
|
||||
err := matcher.Matches("tac")
|
||||
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
ExpectFalse(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *HasSubstrTest) CandidateEqualsArg() {
|
||||
matcher := HasSubstr("taco")
|
||||
err := matcher.Matches("taco")
|
||||
|
||||
ExpectThat(err, Equals(nil))
|
||||
}
|
||||
|
||||
func (t *HasSubstrTest) CandidateHasProperSubstring() {
|
||||
matcher := HasSubstr("taco")
|
||||
err := matcher.Matches("burritos and tacos")
|
||||
|
||||
ExpectThat(err, Equals(nil))
|
||||
}
|
||||
|
||||
func (t *HasSubstrTest) EmptyStringIsAlwaysSubString() {
|
||||
matcher := HasSubstr("")
|
||||
err := matcher.Matches("asdf")
|
||||
|
||||
ExpectThat(err, Equals(nil))
|
||||
}
|
||||
Generated
Vendored
-849
@@ -1,849 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"io"
|
||||
"unsafe"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type IdenticalToTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&IdenticalToTest{}) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *IdenticalToTest) TypesNotIdentical() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
type intAlias int
|
||||
|
||||
// Type alias expected value
|
||||
m = IdenticalTo(intAlias(17))
|
||||
err = m.Matches(int(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int")))
|
||||
|
||||
// Type alias candidate
|
||||
m = IdenticalTo(int(17))
|
||||
err = m.Matches(intAlias(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.intAlias")))
|
||||
|
||||
// int and uint
|
||||
m = IdenticalTo(int(17))
|
||||
err = m.Matches(uint(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type uint")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) PredeclaredNilIdentifier() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
// Nil literal
|
||||
m = IdenticalTo(nil)
|
||||
err = m.Matches(nil)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Zero interface var (which is the same as above since IdenticalTo takes an
|
||||
// interface{} as an arg)
|
||||
var nilReader io.Reader
|
||||
var nilWriter io.Writer
|
||||
|
||||
m = IdenticalTo(nilReader)
|
||||
err = m.Matches(nilWriter)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Typed nil value.
|
||||
m = IdenticalTo(nil)
|
||||
err = m.Matches((chan int)(nil))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type chan int")))
|
||||
|
||||
// Non-nil value.
|
||||
m = IdenticalTo(nil)
|
||||
err = m.Matches("taco")
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type string")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Slices() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
// Nil expected value
|
||||
m = IdenticalTo(([]int)(nil))
|
||||
ExpectEq("identical to <[]int> []", m.Description())
|
||||
|
||||
err = m.Matches(([]int)(nil))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches([]int{})
|
||||
ExpectThat(err, Error(Equals("which is not an identical reference")))
|
||||
|
||||
// Non-nil expected value
|
||||
o1 := make([]int, 1)
|
||||
o2 := make([]int, 1)
|
||||
m = IdenticalTo(o1)
|
||||
ExpectEq(fmt.Sprintf("identical to <[]int> %v", o1), m.Description())
|
||||
|
||||
err = m.Matches(o1)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches(o2)
|
||||
ExpectThat(err, Error(Equals("which is not an identical reference")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Maps() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
// Nil expected value
|
||||
m = IdenticalTo((map[int]int)(nil))
|
||||
ExpectEq("identical to <map[int]int> map[]", m.Description())
|
||||
|
||||
err = m.Matches((map[int]int)(nil))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches(map[int]int{})
|
||||
ExpectThat(err, Error(Equals("which is not an identical reference")))
|
||||
|
||||
// Non-nil expected value
|
||||
o1 := map[int]int{}
|
||||
o2 := map[int]int{}
|
||||
m = IdenticalTo(o1)
|
||||
ExpectEq(fmt.Sprintf("identical to <map[int]int> %v", o1), m.Description())
|
||||
|
||||
err = m.Matches(o1)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches(o2)
|
||||
ExpectThat(err, Error(Equals("which is not an identical reference")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Functions() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
// Nil expected value
|
||||
m = IdenticalTo((func())(nil))
|
||||
ExpectEq("identical to <func()> <nil>", m.Description())
|
||||
|
||||
err = m.Matches((func())(nil))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches(func() {})
|
||||
ExpectThat(err, Error(Equals("which is not an identical reference")))
|
||||
|
||||
// Non-nil expected value
|
||||
o1 := func() {}
|
||||
o2 := func() {}
|
||||
m = IdenticalTo(o1)
|
||||
ExpectEq(fmt.Sprintf("identical to <func()> %v", o1), m.Description())
|
||||
|
||||
err = m.Matches(o1)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches(o2)
|
||||
ExpectThat(err, Error(Equals("which is not an identical reference")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Channels() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
// Nil expected value
|
||||
m = IdenticalTo((chan int)(nil))
|
||||
ExpectEq("identical to <chan int> <nil>", m.Description())
|
||||
|
||||
err = m.Matches((chan int)(nil))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches(make(chan int))
|
||||
ExpectThat(err, Error(Equals("which is not an identical reference")))
|
||||
|
||||
// Non-nil expected value
|
||||
o1 := make(chan int)
|
||||
o2 := make(chan int)
|
||||
m = IdenticalTo(o1)
|
||||
ExpectEq(fmt.Sprintf("identical to <chan int> %v", o1), m.Description())
|
||||
|
||||
err = m.Matches(o1)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches(o2)
|
||||
ExpectThat(err, Error(Equals("which is not an identical reference")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Bools() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
// false
|
||||
m = IdenticalTo(false)
|
||||
ExpectEq("identical to <bool> false", m.Description())
|
||||
|
||||
err = m.Matches(false)
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches(true)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// true
|
||||
m = IdenticalTo(true)
|
||||
ExpectEq("identical to <bool> true", m.Description())
|
||||
|
||||
err = m.Matches(false)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
err = m.Matches(true)
|
||||
ExpectEq(nil, err)
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Ints() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(int(17))
|
||||
ExpectEq("identical to <int> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(int(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType int
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Int8s() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(int8(17))
|
||||
ExpectEq("identical to <int8> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(int8(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType int8
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Int16s() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(int16(17))
|
||||
ExpectEq("identical to <int16> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(int16(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType int16
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Int32s() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(int32(17))
|
||||
ExpectEq("identical to <int32> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(int32(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType int32
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int16(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int16")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Int64s() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(int64(17))
|
||||
ExpectEq("identical to <int64> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(int64(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType int64
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Uints() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(uint(17))
|
||||
ExpectEq("identical to <uint> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(uint(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType uint
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Uint8s() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(uint8(17))
|
||||
ExpectEq("identical to <uint8> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(uint8(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType uint8
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Uint16s() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(uint16(17))
|
||||
ExpectEq("identical to <uint16> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(uint16(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType uint16
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Uint32s() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(uint32(17))
|
||||
ExpectEq("identical to <uint32> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(uint32(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType uint32
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Uint64s() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(uint64(17))
|
||||
ExpectEq("identical to <uint64> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(uint64(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType uint64
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Uintptrs() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(uintptr(17))
|
||||
ExpectEq("identical to <uintptr> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(uintptr(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType uintptr
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Float32s() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(float32(17))
|
||||
ExpectEq("identical to <float32> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(float32(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType float32
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Float64s() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(float64(17))
|
||||
ExpectEq("identical to <float64> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(float64(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType float64
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Complex64s() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(complex64(17))
|
||||
ExpectEq("identical to <complex64> (17+0i)", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(complex64(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType complex64
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Complex128s() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo(complex128(17))
|
||||
ExpectEq("identical to <complex128> (17+0i)", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(complex128(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType complex128
|
||||
err = m.Matches(myType(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) EmptyComparableArrays() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo([0]int{})
|
||||
ExpectEq("identical to <[0]int> []", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches([0]int{})
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Length too long
|
||||
err = m.Matches([1]int{17})
|
||||
ExpectThat(err, Error(Equals("which is of type [1]int")))
|
||||
|
||||
// Element type alias
|
||||
type myType int
|
||||
err = m.Matches([0]myType{})
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type [0]oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong element type
|
||||
err = m.Matches([0]int32{})
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type [0]int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) NonEmptyComparableArrays() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo([2]int{17, 19})
|
||||
ExpectEq("identical to <[2]int> [17 19]", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches([2]int{17, 19})
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Length too short
|
||||
err = m.Matches([1]int{17})
|
||||
ExpectThat(err, Error(Equals("which is of type [1]int")))
|
||||
|
||||
// Length too long
|
||||
err = m.Matches([3]int{17, 19, 23})
|
||||
ExpectThat(err, Error(Equals("which is of type [3]int")))
|
||||
|
||||
// First element different
|
||||
err = m.Matches([2]int{13, 19})
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Second element different
|
||||
err = m.Matches([2]int{17, 23})
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Element type alias
|
||||
type myType int
|
||||
err = m.Matches([2]myType{17, 19})
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type [2]oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong element type
|
||||
err = m.Matches([2]int32{17, 19})
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type [2]int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) NonEmptyArraysOfComparableArrays() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
x := [2][2]int{
|
||||
[2]int{17, 19},
|
||||
[2]int{23, 29},
|
||||
}
|
||||
m = IdenticalTo(x)
|
||||
ExpectEq("identical to <[2][2]int> [[17 19] [23 29]]", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches([2][2]int{[2]int{17, 19}, [2]int{23, 29}})
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Outer length too short
|
||||
err = m.Matches([1][2]int{[2]int{17, 19}})
|
||||
ExpectThat(err, Error(Equals("which is of type [1][2]int")))
|
||||
|
||||
// Inner length too short
|
||||
err = m.Matches([2][1]int{[1]int{17}, [1]int{23}})
|
||||
ExpectThat(err, Error(Equals("which is of type [2][1]int")))
|
||||
|
||||
// First element different
|
||||
err = m.Matches([2][2]int{[2]int{13, 19}, [2]int{23, 29}})
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Element type alias
|
||||
type myType int
|
||||
err = m.Matches([2][2]myType{[2]myType{17, 19}, [2]myType{23, 29}})
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type [2][2]oglematchers_test.myType")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) NonComparableArrays() {
|
||||
x := [0]func(){}
|
||||
f := func() { IdenticalTo(x) }
|
||||
ExpectThat(f, Panics(HasSubstr("is not comparable")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) ArraysOfNonComparableArrays() {
|
||||
x := [0][0]func(){}
|
||||
f := func() { IdenticalTo(x) }
|
||||
ExpectThat(f, Panics(HasSubstr("is not comparable")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) Strings() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
m = IdenticalTo("taco")
|
||||
ExpectEq("identical to <string> taco", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches("ta" + "co")
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Type alias
|
||||
type myType string
|
||||
err = m.Matches(myType("taco"))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) ComparableStructs() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
type subStruct struct {
|
||||
i int
|
||||
}
|
||||
|
||||
type myStruct struct {
|
||||
u uint
|
||||
s subStruct
|
||||
}
|
||||
|
||||
x := myStruct{17, subStruct{19}}
|
||||
m = IdenticalTo(x)
|
||||
ExpectEq("identical to <oglematchers_test.myStruct> {17 {19}}", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(myStruct{17, subStruct{19}})
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Wrong outer field
|
||||
err = m.Matches(myStruct{13, subStruct{19}})
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Wrong inner field
|
||||
err = m.Matches(myStruct{17, subStruct{23}})
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Type alias
|
||||
type myType myStruct
|
||||
err = m.Matches(myType{17, subStruct{19}})
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) NonComparableStructs() {
|
||||
type subStruct struct {
|
||||
s []int
|
||||
}
|
||||
|
||||
type myStruct struct {
|
||||
u uint
|
||||
s subStruct
|
||||
}
|
||||
|
||||
x := myStruct{17, subStruct{[]int{19}}}
|
||||
f := func() { IdenticalTo(x) }
|
||||
ExpectThat(f, Panics(AllOf(HasSubstr("IdenticalTo"), HasSubstr("comparable"))))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) NilUnsafePointer() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
x := unsafe.Pointer(nil)
|
||||
m = IdenticalTo(x)
|
||||
ExpectEq(fmt.Sprintf("identical to <unsafe.Pointer> %v", x), m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(unsafe.Pointer(nil))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Wrong value
|
||||
j := 17
|
||||
err = m.Matches(unsafe.Pointer(&j))
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Type alias
|
||||
type myType unsafe.Pointer
|
||||
err = m.Matches(myType(unsafe.Pointer(nil)))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) NonNilUnsafePointer() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
i := 17
|
||||
x := unsafe.Pointer(&i)
|
||||
m = IdenticalTo(x)
|
||||
ExpectEq(fmt.Sprintf("identical to <unsafe.Pointer> %v", x), m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(unsafe.Pointer(&i))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Nil value
|
||||
err = m.Matches(unsafe.Pointer(nil))
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Wrong value
|
||||
j := 17
|
||||
err = m.Matches(unsafe.Pointer(&j))
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
|
||||
// Type alias
|
||||
type myType unsafe.Pointer
|
||||
err = m.Matches(myType(unsafe.Pointer(&i)))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type oglematchers_test.myType")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
|
||||
func (t *IdenticalToTest) IntAlias() {
|
||||
var m Matcher
|
||||
var err error
|
||||
|
||||
type intAlias int
|
||||
|
||||
m = IdenticalTo(intAlias(17))
|
||||
ExpectEq("identical to <oglematchers_test.intAlias> 17", m.Description())
|
||||
|
||||
// Identical value
|
||||
err = m.Matches(intAlias(17))
|
||||
ExpectEq(nil, err)
|
||||
|
||||
// Int
|
||||
err = m.Matches(int(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int")))
|
||||
|
||||
// Completely wrong type
|
||||
err = m.Matches(int32(17))
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("which is of type int32")))
|
||||
}
|
||||
Generated
Vendored
-1079
File diff suppressed because it is too large
Load Diff
Generated
Vendored
-1059
File diff suppressed because it is too large
Load Diff
Generated
Vendored
-92
@@ -1,92 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type MatchesRegexpTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&MatchesRegexpTest{}) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *MatchesRegexpTest) Description() {
|
||||
m := MatchesRegexp("foo.*bar")
|
||||
ExpectEq("matches regexp \"foo.*bar\"", m.Description())
|
||||
}
|
||||
|
||||
func (t *MatchesRegexpTest) InvalidRegexp() {
|
||||
ExpectThat(
|
||||
func() { MatchesRegexp("(foo") },
|
||||
Panics(HasSubstr("missing closing )")))
|
||||
}
|
||||
|
||||
func (t *MatchesRegexpTest) CandidateIsNil() {
|
||||
m := MatchesRegexp("")
|
||||
err := m.Matches(nil)
|
||||
|
||||
ExpectThat(err, Error(Equals("which is not a string or []byte")))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *MatchesRegexpTest) CandidateIsInteger() {
|
||||
m := MatchesRegexp("")
|
||||
err := m.Matches(17)
|
||||
|
||||
ExpectThat(err, Error(Equals("which is not a string or []byte")))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *MatchesRegexpTest) NonMatchingCandidates() {
|
||||
m := MatchesRegexp("fo[op]\\s+x")
|
||||
var err error
|
||||
|
||||
err = m.Matches("fon x")
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
ExpectFalse(isFatal(err))
|
||||
|
||||
err = m.Matches("fopx")
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
ExpectFalse(isFatal(err))
|
||||
|
||||
err = m.Matches("fop ")
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
ExpectFalse(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *MatchesRegexpTest) MatchingCandidates() {
|
||||
m := MatchesRegexp("fo[op]\\s+x")
|
||||
var err error
|
||||
|
||||
err = m.Matches("foo x")
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches("fop x")
|
||||
ExpectEq(nil, err)
|
||||
|
||||
err = m.Matches("blah blah foo x blah blah")
|
||||
ExpectEq(nil, err)
|
||||
}
|
||||
Generated
Vendored
-107
@@ -1,107 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"testing"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type fakeMatcher struct {
|
||||
matchFunc func(interface{}) error
|
||||
description string
|
||||
}
|
||||
|
||||
func (m *fakeMatcher) Matches(c interface{}) error {
|
||||
return m.matchFunc(c)
|
||||
}
|
||||
|
||||
func (m *fakeMatcher) Description() string {
|
||||
return m.description
|
||||
}
|
||||
|
||||
type NotTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&NotTest{}) }
|
||||
func TestOgletest(t *testing.T) { RunTests(t) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *NotTest) CallsWrapped() {
|
||||
var suppliedCandidate interface{}
|
||||
matchFunc := func(c interface{}) error {
|
||||
suppliedCandidate = c
|
||||
return nil
|
||||
}
|
||||
|
||||
wrapped := &fakeMatcher{matchFunc, ""}
|
||||
matcher := Not(wrapped)
|
||||
|
||||
matcher.Matches(17)
|
||||
ExpectThat(suppliedCandidate, Equals(17))
|
||||
}
|
||||
|
||||
func (t *NotTest) WrappedReturnsTrue() {
|
||||
matchFunc := func(c interface{}) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
wrapped := &fakeMatcher{matchFunc, ""}
|
||||
matcher := Not(wrapped)
|
||||
|
||||
err := matcher.Matches(0)
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
}
|
||||
|
||||
func (t *NotTest) WrappedReturnsNonFatalError() {
|
||||
matchFunc := func(c interface{}) error {
|
||||
return errors.New("taco")
|
||||
}
|
||||
|
||||
wrapped := &fakeMatcher{matchFunc, ""}
|
||||
matcher := Not(wrapped)
|
||||
|
||||
err := matcher.Matches(0)
|
||||
ExpectEq(nil, err)
|
||||
}
|
||||
|
||||
func (t *NotTest) WrappedReturnsFatalError() {
|
||||
matchFunc := func(c interface{}) error {
|
||||
return NewFatalError("taco")
|
||||
}
|
||||
|
||||
wrapped := &fakeMatcher{matchFunc, ""}
|
||||
matcher := Not(wrapped)
|
||||
|
||||
err := matcher.Matches(0)
|
||||
ExpectThat(err, Error(Equals("taco")))
|
||||
}
|
||||
|
||||
func (t *NotTest) Description() {
|
||||
wrapped := &fakeMatcher{nil, "taco"}
|
||||
matcher := Not(wrapped)
|
||||
|
||||
ExpectEq("not(taco)", matcher.Description())
|
||||
}
|
||||
Generated
Vendored
-141
@@ -1,141 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"errors"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type PanicsTest struct {
|
||||
matcherCalled bool
|
||||
suppliedCandidate interface{}
|
||||
wrappedError error
|
||||
|
||||
matcher Matcher
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&PanicsTest{}) }
|
||||
|
||||
func (t *PanicsTest) SetUp(i *TestInfo) {
|
||||
wrapped := &fakeMatcher{
|
||||
func(c interface{}) error {
|
||||
t.matcherCalled = true
|
||||
t.suppliedCandidate = c
|
||||
return t.wrappedError
|
||||
},
|
||||
"foo",
|
||||
}
|
||||
|
||||
t.matcher = Panics(wrapped)
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *PanicsTest) Description() {
|
||||
ExpectThat(t.matcher.Description(), Equals("panics with: foo"))
|
||||
}
|
||||
|
||||
func (t *PanicsTest) CandidateIsNil() {
|
||||
err := t.matcher.Matches(nil)
|
||||
|
||||
ExpectThat(err, Error(Equals("which is not a zero-arg function")))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *PanicsTest) CandidateIsString() {
|
||||
err := t.matcher.Matches("taco")
|
||||
|
||||
ExpectThat(err, Error(Equals("which is not a zero-arg function")))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *PanicsTest) CandidateTakesArgs() {
|
||||
err := t.matcher.Matches(func(i int) string { return "" })
|
||||
|
||||
ExpectThat(err, Error(Equals("which is not a zero-arg function")))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *PanicsTest) CallsFunction() {
|
||||
callCount := 0
|
||||
t.matcher.Matches(func() string {
|
||||
callCount++
|
||||
return ""
|
||||
})
|
||||
|
||||
ExpectThat(callCount, Equals(1))
|
||||
}
|
||||
|
||||
func (t *PanicsTest) FunctionDoesntPanic() {
|
||||
err := t.matcher.Matches(func() {})
|
||||
|
||||
ExpectThat(err, Error(Equals("which didn't panic")))
|
||||
ExpectFalse(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *PanicsTest) CallsWrappedMatcher() {
|
||||
expectedErr := 17
|
||||
t.wrappedError = errors.New("")
|
||||
t.matcher.Matches(func() { panic(expectedErr) })
|
||||
|
||||
ExpectThat(t.suppliedCandidate, Equals(expectedErr))
|
||||
}
|
||||
|
||||
func (t *PanicsTest) WrappedReturnsTrue() {
|
||||
err := t.matcher.Matches(func() { panic("") })
|
||||
|
||||
ExpectEq(nil, err)
|
||||
}
|
||||
|
||||
func (t *PanicsTest) WrappedReturnsFatalErrorWithoutText() {
|
||||
t.wrappedError = NewFatalError("")
|
||||
err := t.matcher.Matches(func() { panic(17) })
|
||||
|
||||
ExpectThat(err, Error(Equals("which panicked with: 17")))
|
||||
ExpectFalse(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *PanicsTest) WrappedReturnsFatalErrorWithText() {
|
||||
t.wrappedError = NewFatalError("which blah")
|
||||
err := t.matcher.Matches(func() { panic(17) })
|
||||
|
||||
ExpectThat(err, Error(Equals("which panicked with: 17, which blah")))
|
||||
ExpectFalse(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *PanicsTest) WrappedReturnsNonFatalErrorWithoutText() {
|
||||
t.wrappedError = errors.New("")
|
||||
err := t.matcher.Matches(func() { panic(17) })
|
||||
|
||||
ExpectThat(err, Error(Equals("which panicked with: 17")))
|
||||
ExpectFalse(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *PanicsTest) WrappedReturnsNonFatalErrorWithText() {
|
||||
t.wrappedError = errors.New("which blah")
|
||||
err := t.matcher.Matches(func() { panic(17) })
|
||||
|
||||
ExpectThat(err, Error(Equals("which panicked with: 17, which blah")))
|
||||
ExpectFalse(isFatal(err))
|
||||
}
|
||||
Generated
Vendored
-153
@@ -1,153 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"testing"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type PointeeTest struct{}
|
||||
|
||||
func init() { RegisterTestSuite(&PointeeTest{}) }
|
||||
|
||||
func TestPointee(t *testing.T) { RunTests(t) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *PointeeTest) Description() {
|
||||
wrapped := &fakeMatcher{nil, "taco"}
|
||||
matcher := Pointee(wrapped)
|
||||
|
||||
ExpectEq("pointee(taco)", matcher.Description())
|
||||
}
|
||||
|
||||
func (t *PointeeTest) CandidateIsNotAPointer() {
|
||||
matcher := Pointee(HasSubstr(""))
|
||||
err := matcher.Matches([]byte{})
|
||||
|
||||
ExpectThat(err, Error(Equals("which is not a pointer")))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *PointeeTest) CandidateIsANilLiteral() {
|
||||
matcher := Pointee(HasSubstr(""))
|
||||
err := matcher.Matches(nil)
|
||||
|
||||
ExpectThat(err, Error(Equals("which is not a pointer")))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *PointeeTest) CandidateIsANilPointer() {
|
||||
matcher := Pointee(HasSubstr(""))
|
||||
err := matcher.Matches((*int)(nil))
|
||||
|
||||
ExpectThat(err, Error(Equals("")))
|
||||
ExpectTrue(isFatal(err))
|
||||
}
|
||||
|
||||
func (t *PointeeTest) CallsWrapped() {
|
||||
var suppliedCandidate interface{}
|
||||
matchFunc := func(c interface{}) error {
|
||||
suppliedCandidate = c
|
||||
return nil
|
||||
}
|
||||
|
||||
wrapped := &fakeMatcher{matchFunc, ""}
|
||||
matcher := Pointee(wrapped)
|
||||
|
||||
someSlice := []byte{}
|
||||
matcher.Matches(&someSlice)
|
||||
ExpectThat(suppliedCandidate, IdenticalTo(someSlice))
|
||||
}
|
||||
|
||||
func (t *PointeeTest) WrappedReturnsOkay() {
|
||||
matchFunc := func(c interface{}) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
wrapped := &fakeMatcher{matchFunc, ""}
|
||||
matcher := Pointee(wrapped)
|
||||
|
||||
err := matcher.Matches(new(int))
|
||||
ExpectEq(nil, err)
|
||||
}
|
||||
|
||||
func (t *PointeeTest) WrappedReturnsNonFatalNonEmptyError() {
|
||||
matchFunc := func(c interface{}) error {
|
||||
return errors.New("taco")
|
||||
}
|
||||
|
||||
wrapped := &fakeMatcher{matchFunc, ""}
|
||||
matcher := Pointee(wrapped)
|
||||
|
||||
i := 17
|
||||
err := matcher.Matches(&i)
|
||||
ExpectFalse(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("taco")))
|
||||
}
|
||||
|
||||
func (t *PointeeTest) WrappedReturnsNonFatalEmptyError() {
|
||||
matchFunc := func(c interface{}) error {
|
||||
return errors.New("")
|
||||
}
|
||||
|
||||
wrapped := &fakeMatcher{matchFunc, ""}
|
||||
matcher := Pointee(wrapped)
|
||||
|
||||
i := 17
|
||||
err := matcher.Matches(&i)
|
||||
ExpectFalse(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("whose pointee")))
|
||||
ExpectThat(err, Error(HasSubstr("17")))
|
||||
}
|
||||
|
||||
func (t *PointeeTest) WrappedReturnsFatalNonEmptyError() {
|
||||
matchFunc := func(c interface{}) error {
|
||||
return NewFatalError("taco")
|
||||
}
|
||||
|
||||
wrapped := &fakeMatcher{matchFunc, ""}
|
||||
matcher := Pointee(wrapped)
|
||||
|
||||
i := 17
|
||||
err := matcher.Matches(&i)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(Equals("taco")))
|
||||
}
|
||||
|
||||
func (t *PointeeTest) WrappedReturnsFatalEmptyError() {
|
||||
matchFunc := func(c interface{}) error {
|
||||
return NewFatalError("")
|
||||
}
|
||||
|
||||
wrapped := &fakeMatcher{matchFunc, ""}
|
||||
matcher := Pointee(wrapped)
|
||||
|
||||
i := 17
|
||||
err := matcher.Matches(&i)
|
||||
ExpectTrue(isFatal(err))
|
||||
ExpectThat(err, Error(HasSubstr("whose pointee")))
|
||||
ExpectThat(err, Error(HasSubstr("17")))
|
||||
}
|
||||
Generated
-5
@@ -1,5 +0,0 @@
|
||||
*.6
|
||||
6.out
|
||||
_obj/
|
||||
_test/
|
||||
_testmain.go
|
||||
Generated
Vendored
-202
@@ -1,202 +0,0 @@
|
||||
|
||||
Apache License
|
||||
Version 2.0, January 2004
|
||||
http://www.apache.org/licenses/
|
||||
|
||||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||
|
||||
1. Definitions.
|
||||
|
||||
"License" shall mean the terms and conditions for use, reproduction,
|
||||
and distribution as defined by Sections 1 through 9 of this document.
|
||||
|
||||
"Licensor" shall mean the copyright owner or entity authorized by
|
||||
the copyright owner that is granting the License.
|
||||
|
||||
"Legal Entity" shall mean the union of the acting entity and all
|
||||
other entities that control, are controlled by, or are under common
|
||||
control with that entity. For the purposes of this definition,
|
||||
"control" means (i) the power, direct or indirect, to cause the
|
||||
direction or management of such entity, whether by contract or
|
||||
otherwise, or (ii) ownership of fifty percent (50%) or more of the
|
||||
outstanding shares, or (iii) beneficial ownership of such entity.
|
||||
|
||||
"You" (or "Your") shall mean an individual or Legal Entity
|
||||
exercising permissions granted by this License.
|
||||
|
||||
"Source" form shall mean the preferred form for making modifications,
|
||||
including but not limited to software source code, documentation
|
||||
source, and configuration files.
|
||||
|
||||
"Object" form shall mean any form resulting from mechanical
|
||||
transformation or translation of a Source form, including but
|
||||
not limited to compiled object code, generated documentation,
|
||||
and conversions to other media types.
|
||||
|
||||
"Work" shall mean the work of authorship, whether in Source or
|
||||
Object form, made available under the License, as indicated by a
|
||||
copyright notice that is included in or attached to the work
|
||||
(an example is provided in the Appendix below).
|
||||
|
||||
"Derivative Works" shall mean any work, whether in Source or Object
|
||||
form, that is based on (or derived from) the Work and for which the
|
||||
editorial revisions, annotations, elaborations, or other modifications
|
||||
represent, as a whole, an original work of authorship. For the purposes
|
||||
of this License, Derivative Works shall not include works that remain
|
||||
separable from, or merely link (or bind by name) to the interfaces of,
|
||||
the Work and Derivative Works thereof.
|
||||
|
||||
"Contribution" shall mean any work of authorship, including
|
||||
the original version of the Work and any modifications or additions
|
||||
to that Work or Derivative Works thereof, that is intentionally
|
||||
submitted to Licensor for inclusion in the Work by the copyright owner
|
||||
or by an individual or Legal Entity authorized to submit on behalf of
|
||||
the copyright owner. For the purposes of this definition, "submitted"
|
||||
means any form of electronic, verbal, or written communication sent
|
||||
to the Licensor or its representatives, including but not limited to
|
||||
communication on electronic mailing lists, source code control systems,
|
||||
and issue tracking systems that are managed by, or on behalf of, the
|
||||
Licensor for the purpose of discussing and improving the Work, but
|
||||
excluding communication that is conspicuously marked or otherwise
|
||||
designated in writing by the copyright owner as "Not a Contribution."
|
||||
|
||||
"Contributor" shall mean Licensor and any individual or Legal Entity
|
||||
on behalf of whom a Contribution has been received by Licensor and
|
||||
subsequently incorporated within the Work.
|
||||
|
||||
2. Grant of Copyright License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
copyright license to reproduce, prepare Derivative Works of,
|
||||
publicly display, publicly perform, sublicense, and distribute the
|
||||
Work and such Derivative Works in Source or Object form.
|
||||
|
||||
3. Grant of Patent License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
(except as stated in this section) patent license to make, have made,
|
||||
use, offer to sell, sell, import, and otherwise transfer the Work,
|
||||
where such license applies only to those patent claims licensable
|
||||
by such Contributor that are necessarily infringed by their
|
||||
Contribution(s) alone or by combination of their Contribution(s)
|
||||
with the Work to which such Contribution(s) was submitted. If You
|
||||
institute patent litigation against any entity (including a
|
||||
cross-claim or counterclaim in a lawsuit) alleging that the Work
|
||||
or a Contribution incorporated within the Work constitutes direct
|
||||
or contributory patent infringement, then any patent licenses
|
||||
granted to You under this License for that Work shall terminate
|
||||
as of the date such litigation is filed.
|
||||
|
||||
4. Redistribution. You may reproduce and distribute copies of the
|
||||
Work or Derivative Works thereof in any medium, with or without
|
||||
modifications, and in Source or Object form, provided that You
|
||||
meet the following conditions:
|
||||
|
||||
(a) You must give any other recipients of the Work or
|
||||
Derivative Works a copy of this License; and
|
||||
|
||||
(b) You must cause any modified files to carry prominent notices
|
||||
stating that You changed the files; and
|
||||
|
||||
(c) You must retain, in the Source form of any Derivative Works
|
||||
that You distribute, all copyright, patent, trademark, and
|
||||
attribution notices from the Source form of the Work,
|
||||
excluding those notices that do not pertain to any part of
|
||||
the Derivative Works; and
|
||||
|
||||
(d) If the Work includes a "NOTICE" text file as part of its
|
||||
distribution, then any Derivative Works that You distribute must
|
||||
include a readable copy of the attribution notices contained
|
||||
within such NOTICE file, excluding those notices that do not
|
||||
pertain to any part of the Derivative Works, in at least one
|
||||
of the following places: within a NOTICE text file distributed
|
||||
as part of the Derivative Works; within the Source form or
|
||||
documentation, if provided along with the Derivative Works; or,
|
||||
within a display generated by the Derivative Works, if and
|
||||
wherever such third-party notices normally appear. The contents
|
||||
of the NOTICE file are for informational purposes only and
|
||||
do not modify the License. You may add Your own attribution
|
||||
notices within Derivative Works that You distribute, alongside
|
||||
or as an addendum to the NOTICE text from the Work, provided
|
||||
that such additional attribution notices cannot be construed
|
||||
as modifying the License.
|
||||
|
||||
You may add Your own copyright statement to Your modifications and
|
||||
may provide additional or different license terms and conditions
|
||||
for use, reproduction, or distribution of Your modifications, or
|
||||
for any such Derivative Works as a whole, provided Your use,
|
||||
reproduction, and distribution of the Work otherwise complies with
|
||||
the conditions stated in this License.
|
||||
|
||||
5. Submission of Contributions. Unless You explicitly state otherwise,
|
||||
any Contribution intentionally submitted for inclusion in the Work
|
||||
by You to the Licensor shall be under the terms and conditions of
|
||||
this License, without any additional terms or conditions.
|
||||
Notwithstanding the above, nothing herein shall supersede or modify
|
||||
the terms of any separate license agreement you may have executed
|
||||
with Licensor regarding such Contributions.
|
||||
|
||||
6. Trademarks. This License does not grant permission to use the trade
|
||||
names, trademarks, service marks, or product names of the Licensor,
|
||||
except as required for reasonable and customary use in describing the
|
||||
origin of the Work and reproducing the content of the NOTICE file.
|
||||
|
||||
7. Disclaimer of Warranty. Unless required by applicable law or
|
||||
agreed to in writing, Licensor provides the Work (and each
|
||||
Contributor provides its Contributions) on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
implied, including, without limitation, any warranties or conditions
|
||||
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
|
||||
PARTICULAR PURPOSE. You are solely responsible for determining the
|
||||
appropriateness of using or redistributing the Work and assume any
|
||||
risks associated with Your exercise of permissions under this License.
|
||||
|
||||
8. Limitation of Liability. In no event and under no legal theory,
|
||||
whether in tort (including negligence), contract, or otherwise,
|
||||
unless required by applicable law (such as deliberate and grossly
|
||||
negligent acts) or agreed to in writing, shall any Contributor be
|
||||
liable to You for damages, including any direct, indirect, special,
|
||||
incidental, or consequential damages of any character arising as a
|
||||
result of this License or out of the use or inability to use the
|
||||
Work (including but not limited to damages for loss of goodwill,
|
||||
work stoppage, computer failure or malfunction, or any and all
|
||||
other commercial damages or losses), even if such Contributor
|
||||
has been advised of the possibility of such damages.
|
||||
|
||||
9. Accepting Warranty or Additional Liability. While redistributing
|
||||
the Work or Derivative Works thereof, You may choose to offer,
|
||||
and charge a fee for, acceptance of support, warranty, indemnity,
|
||||
or other liability obligations and/or rights consistent with this
|
||||
License. However, in accepting such obligations, You may act only
|
||||
on Your own behalf and on Your sole responsibility, not on behalf
|
||||
of any other Contributor, and only if You agree to indemnify,
|
||||
defend, and hold each Contributor harmless for any liability
|
||||
incurred by, or claims asserted against, such Contributor by reason
|
||||
of your accepting any such warranty or additional liability.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
|
||||
APPENDIX: How to apply the Apache License to your work.
|
||||
|
||||
To apply the Apache License to your work, attach the following
|
||||
boilerplate notice, with the fields enclosed by brackets "[]"
|
||||
replaced with your own identifying information. (Don't include
|
||||
the brackets!) The text should be enclosed in the appropriate
|
||||
comment syntax for the file format. We also recommend that a
|
||||
file or class name and description of purpose be included on the
|
||||
same "printed page" as the copyright notice for easier
|
||||
identification within third-party archives.
|
||||
|
||||
Copyright [yyyy] [name of copyright owner]
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
Generated
Vendored
-101
@@ -1,101 +0,0 @@
|
||||
`oglemock` is a mocking framework for the Go programming language with the
|
||||
following features:
|
||||
|
||||
* An extensive and extensible set of matchers for expressing call
|
||||
expectations (provided by the [oglematchers][] package).
|
||||
|
||||
* Clean, readable output that tells you exactly what you need to know.
|
||||
|
||||
* Style and semantics similar to [Google Mock][googlemock] and
|
||||
[Google JS Test][google-js-test].
|
||||
|
||||
* Seamless integration with the [ogletest][] unit testing framework.
|
||||
|
||||
It can be integrated into any testing framework (including Go's `testing`
|
||||
package), but out of the box support is built in to [ogletest][] and that is the
|
||||
easiest place to use it.
|
||||
|
||||
|
||||
Installation
|
||||
------------
|
||||
|
||||
First, make sure you have installed Go 1.0.2 or newer. See
|
||||
[here][golang-install] for instructions.
|
||||
|
||||
Use the following command to install `oglemock` and its dependencies, and to
|
||||
keep them up to date:
|
||||
|
||||
go get -u github.com/smartystreets/goconvey/convey/assertions/oglemock
|
||||
go get -u github.com/smartystreets/goconvey/convey/assertions/oglemock/createmock
|
||||
|
||||
Those commands will install the `oglemock` package itself, along with the
|
||||
`createmock` tool that is used to auto-generate mock types.
|
||||
|
||||
|
||||
Generating and using mock types
|
||||
-------------------------------
|
||||
|
||||
Automatically generating a mock implementation of an interface is easy. If you
|
||||
want to mock interfaces `Bar` and `Baz` from package `foo`, simply run the
|
||||
following:
|
||||
|
||||
createmock foo Bar Baz
|
||||
|
||||
That will print source code that can be saved to a file and used in your tests.
|
||||
For example, to create a `mock_io` package containing mock implementations of
|
||||
`io.Reader` and `io.Writer`:
|
||||
|
||||
mkdir mock_io
|
||||
createmock io Reader Writer > mock_io/mock_io.go
|
||||
|
||||
The new package will be named `mock_io`, and contain types called `MockReader`
|
||||
and `MockWriter`, which implement `io.Reader` and `io.Writer` respectively.
|
||||
|
||||
For each generated mock type, there is a corresponding function for creating an
|
||||
instance of that type given a `Controller` object (see below). For example, to
|
||||
create a mock reader:
|
||||
|
||||
```go
|
||||
someController := [...] // See next section.
|
||||
someReader := mock_io.NewMockReader(someController, "Mock file reader")
|
||||
```
|
||||
|
||||
The snippet above creates a mock `io.Reader` that reports failures to
|
||||
`someController`. The reader can subsequently have expectations set up and be
|
||||
passed to your code under test that uses an `io.Reader`.
|
||||
|
||||
|
||||
Getting ahold of a controller
|
||||
-----------------------------
|
||||
|
||||
[oglemock.Controller][controller-ref] is used to create mock objects, and to set
|
||||
up and verify expectations for them. You can create one by calling
|
||||
`NewController` with an `ErrorReporter`, which is the basic type used to
|
||||
interface between `oglemock` and the testing framework within which it is being
|
||||
used.
|
||||
|
||||
If you are using [ogletest][] you don't need to worry about any of this, since
|
||||
the `TestInfo` struct provided to your test's `SetUp` function already contains
|
||||
a working `Controller` that you can use to create mock object, and you can use
|
||||
the built-in `ExpectCall` function for setting expectations. (See the
|
||||
[ogletest documentation][ogletest-docs] for more info.) Otherwise, you will need
|
||||
to implement the simple [ErrorReporter interface][reporter-ref] for your test
|
||||
environment.
|
||||
|
||||
|
||||
Documentation
|
||||
-------------
|
||||
|
||||
For thorough documentation, including information on how to set up expectations,
|
||||
see [here][oglemock-docs].
|
||||
|
||||
|
||||
[controller-ref]: http://gopkgdoc.appspot.com/pkg/github.com/smartystreets/goconvey/convey/assertions/oglemock#Controller
|
||||
[reporter-ref]: http://gopkgdoc.appspot.com/pkg/github.com/smartystreets/goconvey/convey/assertions/oglemock#ErrorReporter
|
||||
[golang-install]: http://golang.org/doc/install.html
|
||||
[google-js-test]: http://code.google.com/p/google-js-test/
|
||||
[googlemock]: http://code.google.com/p/googlemock/
|
||||
[oglematchers]: https://github.com/smartystreets/goconvey/convey/assertions/oglematchers
|
||||
[oglemock-docs]: http://gopkgdoc.appspot.com/pkg/github.com/smartystreets/goconvey/convey/assertions/oglemock
|
||||
[ogletest]: https://github.com/smartystreets/goconvey/convey/assertions/oglematchers
|
||||
[ogletest-docs]: http://gopkgdoc.appspot.com/pkg/github.com/smartystreets/goconvey/convey/assertions/ogletest
|
||||
Generated
Vendored
-36
@@ -1,36 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglemock
|
||||
|
||||
import (
|
||||
"reflect"
|
||||
)
|
||||
|
||||
// Action represents an action to be taken in response to a call to a mock
|
||||
// method.
|
||||
type Action interface {
|
||||
// Set the signature of the function with which this action is being used.
|
||||
// This must be called before Invoke is called.
|
||||
SetSignature(signature reflect.Type) error
|
||||
|
||||
// Invoke runs the specified action, given the arguments to the mock method.
|
||||
// It returns zero or more values that may be treated as the return values of
|
||||
// the method. If the action doesn't return any values, it may return the nil
|
||||
// slice.
|
||||
//
|
||||
// You must call SetSignature before calling Invoke.
|
||||
Invoke(methodArgs []interface{}) []interface{}
|
||||
}
|
||||
Generated
Vendored
-480
@@ -1,480 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglemock
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"log"
|
||||
"math"
|
||||
"reflect"
|
||||
"sync"
|
||||
)
|
||||
|
||||
// PartialExpecation is a function that should be called exactly once with
|
||||
// expected arguments or matchers in order to set up an expected method call.
|
||||
// See Controller.ExpectMethodCall below. It returns an expectation that can be
|
||||
// further modified (e.g. by calling WillOnce).
|
||||
//
|
||||
// If the arguments are of the wrong type, the function reports a fatal error
|
||||
// and returns nil.
|
||||
type PartialExpecation func(...interface{}) Expectation
|
||||
|
||||
// Controller represents an object that implements the central logic of
|
||||
// oglemock: recording and verifying expectations, responding to mock method
|
||||
// calls, and so on.
|
||||
type Controller interface {
|
||||
// ExpectCall expresses an expectation that the method of the given name
|
||||
// should be called on the supplied mock object. It returns a function that
|
||||
// should be called with the expected arguments, matchers for the arguments,
|
||||
// or a mix of both.
|
||||
//
|
||||
// fileName and lineNumber should indicate the line on which the expectation
|
||||
// was made, if known.
|
||||
//
|
||||
// For example:
|
||||
//
|
||||
// mockWriter := [...]
|
||||
// controller.ExpectCall(mockWriter, "Write", "foo.go", 17)(ElementsAre(0x1))
|
||||
// .WillOnce(Return(1, nil))
|
||||
//
|
||||
// If the mock object doesn't have a method of the supplied name, the
|
||||
// function reports a fatal error and returns nil.
|
||||
ExpectCall(
|
||||
o MockObject,
|
||||
methodName string,
|
||||
fileName string,
|
||||
lineNumber int) PartialExpecation
|
||||
|
||||
// Finish causes the controller to check for any unsatisfied expectations,
|
||||
// and report them as errors if they exist.
|
||||
//
|
||||
// The controller may panic if any of its methods (including this one) are
|
||||
// called after Finish is called.
|
||||
Finish()
|
||||
|
||||
// HandleMethodCall looks for a registered expectation matching the call of
|
||||
// the given method on mock object o, invokes the appropriate action (if
|
||||
// any), and returns the values returned by that action (if any).
|
||||
//
|
||||
// If the action returns nothing, the controller returns zero values. If
|
||||
// there is no matching expectation, the controller reports an error and
|
||||
// returns zero values.
|
||||
//
|
||||
// If the mock object doesn't have a method of the supplied name, the
|
||||
// arguments are of the wrong type, or the action returns the wrong types,
|
||||
// the function reports a fatal error.
|
||||
//
|
||||
// HandleMethodCall is exported for the sake of mock implementations, and
|
||||
// should not be used directly.
|
||||
HandleMethodCall(
|
||||
o MockObject,
|
||||
methodName string,
|
||||
fileName string,
|
||||
lineNumber int,
|
||||
args []interface{}) []interface{}
|
||||
}
|
||||
|
||||
// methodMap represents a map from method name to set of expectations for that
|
||||
// method.
|
||||
type methodMap map[string][]*InternalExpectation
|
||||
|
||||
// objectMap represents a map from mock object ID to a methodMap for that object.
|
||||
type objectMap map[uintptr]methodMap
|
||||
|
||||
// NewController sets up a fresh controller, without any expectations set, and
|
||||
// configures the controller to use the supplied error reporter.
|
||||
func NewController(reporter ErrorReporter) Controller {
|
||||
return &controllerImpl{reporter, sync.RWMutex{}, objectMap{}}
|
||||
}
|
||||
|
||||
type controllerImpl struct {
|
||||
reporter ErrorReporter
|
||||
|
||||
mutex sync.RWMutex
|
||||
expectationsByObject objectMap // Protected by mutex
|
||||
}
|
||||
|
||||
// Return the list of registered expectations for the named method of the
|
||||
// supplied object, or an empty slice if none have been registered. When this
|
||||
// method returns, it is guaranteed that c.expectationsByObject has an entry
|
||||
// for the object.
|
||||
//
|
||||
// c.mutex must be held for reading.
|
||||
func (c *controllerImpl) getExpectationsLocked(
|
||||
o MockObject,
|
||||
methodName string) []*InternalExpectation {
|
||||
id := o.Oglemock_Id()
|
||||
|
||||
// Look up the mock object.
|
||||
expectationsByMethod, ok := c.expectationsByObject[id]
|
||||
if !ok {
|
||||
expectationsByMethod = methodMap{}
|
||||
c.expectationsByObject[id] = expectationsByMethod
|
||||
}
|
||||
|
||||
result, ok := expectationsByMethod[methodName]
|
||||
if !ok {
|
||||
return []*InternalExpectation{}
|
||||
}
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
// Add an expectation to the list registered for the named method of the
|
||||
// supplied mock object.
|
||||
//
|
||||
// c.mutex must be held for writing.
|
||||
func (c *controllerImpl) addExpectationLocked(
|
||||
o MockObject,
|
||||
methodName string,
|
||||
exp *InternalExpectation) {
|
||||
// Get the existing list.
|
||||
existing := c.getExpectationsLocked(o, methodName)
|
||||
|
||||
// Store a modified list.
|
||||
id := o.Oglemock_Id()
|
||||
c.expectationsByObject[id][methodName] = append(existing, exp)
|
||||
}
|
||||
|
||||
func (c *controllerImpl) ExpectCall(
|
||||
o MockObject,
|
||||
methodName string,
|
||||
fileName string,
|
||||
lineNumber int) PartialExpecation {
|
||||
// Find the signature for the requested method.
|
||||
ov := reflect.ValueOf(o)
|
||||
method := ov.MethodByName(methodName)
|
||||
if method.Kind() == reflect.Invalid {
|
||||
c.reporter.ReportFatalError(
|
||||
fileName,
|
||||
lineNumber,
|
||||
errors.New("Unknown method: "+methodName))
|
||||
return nil
|
||||
}
|
||||
|
||||
partialAlreadyCalled := false // Protected by c.mutex
|
||||
return func(args ...interface{}) Expectation {
|
||||
c.mutex.Lock()
|
||||
defer c.mutex.Unlock()
|
||||
|
||||
// This function should only be called once.
|
||||
if partialAlreadyCalled {
|
||||
c.reporter.ReportFatalError(
|
||||
fileName,
|
||||
lineNumber,
|
||||
errors.New("Partial expectation called more than once."))
|
||||
return nil
|
||||
}
|
||||
|
||||
partialAlreadyCalled = true
|
||||
|
||||
// Make sure that the number of args is legal. Keep in mind that the
|
||||
// method's type has an extra receiver arg.
|
||||
if len(args) != method.Type().NumIn() {
|
||||
c.reporter.ReportFatalError(
|
||||
fileName,
|
||||
lineNumber,
|
||||
errors.New(
|
||||
fmt.Sprintf(
|
||||
"Expectation for %s given wrong number of arguments: "+
|
||||
"expected %d, got %d.",
|
||||
methodName,
|
||||
method.Type().NumIn(),
|
||||
len(args))))
|
||||
return nil
|
||||
}
|
||||
|
||||
// Create an expectation and insert it into the controller's map.
|
||||
exp := InternalNewExpectation(
|
||||
c.reporter,
|
||||
method.Type(),
|
||||
args,
|
||||
fileName,
|
||||
lineNumber)
|
||||
|
||||
c.addExpectationLocked(o, methodName, exp)
|
||||
|
||||
// Return the expectation to the user.
|
||||
return exp
|
||||
}
|
||||
}
|
||||
|
||||
func (c *controllerImpl) Finish() {
|
||||
c.mutex.Lock()
|
||||
defer c.mutex.Unlock()
|
||||
|
||||
// Check whether the minimum cardinality for each registered expectation has
|
||||
// been satisfied.
|
||||
for _, expectationsByMethod := range c.expectationsByObject {
|
||||
for methodName, expectations := range expectationsByMethod {
|
||||
for _, exp := range expectations {
|
||||
exp.mutex.Lock()
|
||||
defer exp.mutex.Unlock()
|
||||
|
||||
minCardinality, _ := computeCardinalityLocked(exp)
|
||||
if exp.NumMatches < minCardinality {
|
||||
c.reporter.ReportError(
|
||||
exp.FileName,
|
||||
exp.LineNumber,
|
||||
errors.New(
|
||||
fmt.Sprintf(
|
||||
"Unsatisfied expectation; expected %s to be called "+
|
||||
"at least %d times; called %d times.",
|
||||
methodName,
|
||||
minCardinality,
|
||||
exp.NumMatches)))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// expectationMatches checks the matchers for the expectation against the
|
||||
// supplied arguments.
|
||||
func expectationMatches(exp *InternalExpectation, args []interface{}) bool {
|
||||
matchers := exp.ArgMatchers
|
||||
if len(args) != len(matchers) {
|
||||
panic("expectationMatches: len(args)")
|
||||
}
|
||||
|
||||
// Check each matcher.
|
||||
for i, matcher := range matchers {
|
||||
if err := matcher.Matches(args[i]); err != nil {
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
||||
return true
|
||||
}
|
||||
|
||||
// Return the expectation that matches the supplied arguments. If there is more
|
||||
// than one such expectation, the one furthest along in the list for the method
|
||||
// is returned. If there is no such expectation, nil is returned.
|
||||
//
|
||||
// c.mutex must be held for reading.
|
||||
func (c *controllerImpl) chooseExpectationLocked(
|
||||
o MockObject,
|
||||
methodName string,
|
||||
args []interface{}) *InternalExpectation {
|
||||
// Do we have any expectations for this method?
|
||||
expectations := c.getExpectationsLocked(o, methodName)
|
||||
if len(expectations) == 0 {
|
||||
return nil
|
||||
}
|
||||
|
||||
for i := len(expectations) - 1; i >= 0; i-- {
|
||||
if expectationMatches(expectations[i], args) {
|
||||
return expectations[i]
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// makeZeroReturnValues creates a []interface{} containing appropriate zero
|
||||
// values for returning from the supplied method type.
|
||||
func makeZeroReturnValues(signature reflect.Type) []interface{} {
|
||||
result := make([]interface{}, signature.NumOut())
|
||||
|
||||
for i, _ := range result {
|
||||
outType := signature.Out(i)
|
||||
zeroVal := reflect.Zero(outType)
|
||||
result[i] = zeroVal.Interface()
|
||||
}
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
// computeCardinality decides on the [min, max] range of the number of expected
|
||||
// matches for the supplied expectations, according to the rules documented in
|
||||
// expectation.go.
|
||||
//
|
||||
// exp.mutex must be held for reading.
|
||||
func computeCardinalityLocked(exp *InternalExpectation) (min, max uint) {
|
||||
// Explicit cardinality.
|
||||
if exp.ExpectedNumMatches >= 0 {
|
||||
min = uint(exp.ExpectedNumMatches)
|
||||
max = min
|
||||
return
|
||||
}
|
||||
|
||||
// Implicit count based on one-time actions.
|
||||
if len(exp.OneTimeActions) != 0 {
|
||||
min = uint(len(exp.OneTimeActions))
|
||||
max = min
|
||||
|
||||
// If there is a fallback action, this is only a lower bound.
|
||||
if exp.FallbackAction != nil {
|
||||
max = math.MaxUint32
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
// Implicit lack of restriction based on a fallback action being configured.
|
||||
if exp.FallbackAction != nil {
|
||||
min = 0
|
||||
max = math.MaxUint32
|
||||
return
|
||||
}
|
||||
|
||||
// Implicit cardinality of one.
|
||||
min = 1
|
||||
max = 1
|
||||
return
|
||||
}
|
||||
|
||||
// chooseAction returns the action that should be invoked for the i'th match to
|
||||
// the supplied expectation (counting from zero). If the implicit "return zero
|
||||
// values" action should be used, it returns nil.
|
||||
//
|
||||
// exp.mutex must be held for reading.
|
||||
func chooseActionLocked(i uint, exp *InternalExpectation) Action {
|
||||
// Exhaust one-time actions first.
|
||||
if i < uint(len(exp.OneTimeActions)) {
|
||||
return exp.OneTimeActions[i]
|
||||
}
|
||||
|
||||
// Fallback action (or nil if none is configured).
|
||||
return exp.FallbackAction
|
||||
}
|
||||
|
||||
// Find an action for the method call, updating expectation match state in the
|
||||
// process. Return either an action that should be invoked or a set of zero
|
||||
// values to return immediately.
|
||||
//
|
||||
// This is split out from HandleMethodCall in order to more easily avoid
|
||||
// invoking the action with locks held.
|
||||
func (c *controllerImpl) chooseActionAndUpdateExpectations(
|
||||
o MockObject,
|
||||
methodName string,
|
||||
fileName string,
|
||||
lineNumber int,
|
||||
args []interface{},
|
||||
) (action Action, zeroVals []interface{}) {
|
||||
c.mutex.Lock()
|
||||
defer c.mutex.Unlock()
|
||||
|
||||
// Find the signature for the requested method.
|
||||
ov := reflect.ValueOf(o)
|
||||
method := ov.MethodByName(methodName)
|
||||
if method.Kind() == reflect.Invalid {
|
||||
c.reporter.ReportFatalError(
|
||||
fileName,
|
||||
lineNumber,
|
||||
errors.New("Unknown method: "+methodName),
|
||||
)
|
||||
|
||||
// Should never get here in real code.
|
||||
log.Println("ReportFatalError unexpectedly returned.")
|
||||
return
|
||||
}
|
||||
|
||||
// HACK(jacobsa): Make sure we got the correct number of arguments. This will
|
||||
// need to be refined when issue #5 (variadic methods) is handled.
|
||||
if len(args) != method.Type().NumIn() {
|
||||
c.reporter.ReportFatalError(
|
||||
fileName,
|
||||
lineNumber,
|
||||
errors.New(
|
||||
fmt.Sprintf(
|
||||
"Wrong number of arguments: expected %d; got %d",
|
||||
method.Type().NumIn(),
|
||||
len(args),
|
||||
),
|
||||
),
|
||||
)
|
||||
|
||||
// Should never get here in real code.
|
||||
log.Println("ReportFatalError unexpectedly returned.")
|
||||
return
|
||||
}
|
||||
|
||||
// Find an expectation matching this call.
|
||||
expectation := c.chooseExpectationLocked(o, methodName, args)
|
||||
if expectation == nil {
|
||||
c.reporter.ReportError(
|
||||
fileName,
|
||||
lineNumber,
|
||||
errors.New(
|
||||
fmt.Sprintf("Unexpected call to %s with args: %v", methodName, args),
|
||||
),
|
||||
)
|
||||
|
||||
zeroVals = makeZeroReturnValues(method.Type())
|
||||
return
|
||||
}
|
||||
|
||||
expectation.mutex.Lock()
|
||||
defer expectation.mutex.Unlock()
|
||||
|
||||
// Increase the number of matches recorded, and check whether we're over the
|
||||
// number expected.
|
||||
expectation.NumMatches++
|
||||
_, maxCardinality := computeCardinalityLocked(expectation)
|
||||
if expectation.NumMatches > maxCardinality {
|
||||
c.reporter.ReportError(
|
||||
expectation.FileName,
|
||||
expectation.LineNumber,
|
||||
errors.New(
|
||||
fmt.Sprintf(
|
||||
"Unexpected call to %s: "+
|
||||
"expected to be called at most %d times; called %d times.",
|
||||
methodName,
|
||||
maxCardinality,
|
||||
expectation.NumMatches,
|
||||
),
|
||||
),
|
||||
)
|
||||
|
||||
zeroVals = makeZeroReturnValues(method.Type())
|
||||
return
|
||||
}
|
||||
|
||||
// Choose an action to invoke. If there is none, just return zero values.
|
||||
action = chooseActionLocked(expectation.NumMatches-1, expectation)
|
||||
if action == nil {
|
||||
zeroVals = makeZeroReturnValues(method.Type())
|
||||
return
|
||||
}
|
||||
|
||||
// Let the action take over.
|
||||
return
|
||||
}
|
||||
|
||||
func (c *controllerImpl) HandleMethodCall(
|
||||
o MockObject,
|
||||
methodName string,
|
||||
fileName string,
|
||||
lineNumber int,
|
||||
args []interface{},
|
||||
) []interface{} {
|
||||
// Figure out whether to invoke an action or return zero values.
|
||||
action, zeroVals := c.chooseActionAndUpdateExpectations(
|
||||
o,
|
||||
methodName,
|
||||
fileName,
|
||||
lineNumber,
|
||||
args,
|
||||
)
|
||||
|
||||
if action != nil {
|
||||
return action.Invoke(args)
|
||||
}
|
||||
|
||||
return zeroVals
|
||||
}
|
||||
Generated
Vendored
-226
@@ -1,226 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
// createmock is used to generate source code for mock versions of interfaces
|
||||
// from installed packages.
|
||||
package main
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"flag"
|
||||
"fmt"
|
||||
"go/build"
|
||||
"io/ioutil"
|
||||
"log"
|
||||
"os"
|
||||
"os/exec"
|
||||
"path"
|
||||
"regexp"
|
||||
"text/template"
|
||||
|
||||
// Ensure that the generate package, which is used by the generated code, is
|
||||
// installed by goinstall.
|
||||
_ "github.com/smartystreets/goconvey/convey/assertions/oglemock/generate"
|
||||
)
|
||||
|
||||
// A template for generated code that is used to print the result.
|
||||
const tmplStr = `
|
||||
{{$inputPkg := .InputPkg}}
|
||||
{{$outputPkg := .OutputPkg}}
|
||||
|
||||
package main
|
||||
|
||||
import (
|
||||
{{range $identifier, $import := .Imports}}
|
||||
{{$identifier}} "{{$import}}"
|
||||
{{end}}
|
||||
)
|
||||
|
||||
func getTypeForPtr(ptr interface{}) reflect.Type {
|
||||
return reflect.TypeOf(ptr).Elem()
|
||||
}
|
||||
|
||||
func main() {
|
||||
// Reduce noise in logging output.
|
||||
log.SetFlags(0)
|
||||
|
||||
interfaces := []reflect.Type{
|
||||
{{range $typeName := .TypeNames}}
|
||||
getTypeForPtr((*{{base $inputPkg}}.{{$typeName}})(nil)),
|
||||
{{end}}
|
||||
}
|
||||
|
||||
err := generate.GenerateMockSource(os.Stdout, "{{$outputPkg}}", interfaces)
|
||||
if err != nil {
|
||||
log.Fatalf("Error generating mock source: %v", err)
|
||||
}
|
||||
}
|
||||
`
|
||||
|
||||
// A map from import identifier to package to use that identifier for,
|
||||
// containing elements for each import needed by the generated code.
|
||||
type importMap map[string]string
|
||||
|
||||
type tmplArg struct {
|
||||
InputPkg string
|
||||
OutputPkg string
|
||||
|
||||
// Imports needed by the generated code.
|
||||
Imports importMap
|
||||
|
||||
// Types to be mocked, relative to their package's name.
|
||||
TypeNames []string
|
||||
}
|
||||
|
||||
var unknownPackageRegexp = regexp.MustCompile(
|
||||
`tool\.go:\d+:\d+: cannot find package "([^"]+)"`)
|
||||
|
||||
var undefinedInterfaceRegexp = regexp.MustCompile(`tool\.go:\d+: undefined: [\pL_0-9]+\.([\pL_0-9]+)`)
|
||||
|
||||
// Does the 'go build' output indicate that a package wasn't found? If so,
|
||||
// return the name of the package.
|
||||
func findUnknownPackage(output []byte) *string {
|
||||
if match := unknownPackageRegexp.FindSubmatch(output); match != nil {
|
||||
res := string(match[1])
|
||||
return &res
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// Does the 'go build' output indicate that an interface wasn't found? If so,
|
||||
// return the name of the interface.
|
||||
func findUndefinedInterface(output []byte) *string {
|
||||
if match := undefinedInterfaceRegexp.FindSubmatch(output); match != nil {
|
||||
res := string(match[1])
|
||||
return &res
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// Split out from main so that deferred calls are executed even in the event of
|
||||
// an error.
|
||||
func run() error {
|
||||
// Reduce noise in logging output.
|
||||
log.SetFlags(0)
|
||||
|
||||
// Check the command-line arguments.
|
||||
flag.Parse()
|
||||
|
||||
cmdLineArgs := flag.Args()
|
||||
if len(cmdLineArgs) < 2 {
|
||||
return errors.New("Usage: createmock [package] [interface ...]")
|
||||
}
|
||||
|
||||
// Create a temporary directory inside of $GOPATH to hold generated code.
|
||||
buildPkg, err := build.Import("github.com/smartystreets/goconvey/convey/assertions/oglemock", "", build.FindOnly)
|
||||
if err != nil {
|
||||
return errors.New(fmt.Sprintf("Couldn't find oglemock in $GOPATH: %v", err))
|
||||
}
|
||||
|
||||
tmpDir, err := ioutil.TempDir(buildPkg.SrcRoot, "tmp-createmock-")
|
||||
if err != nil {
|
||||
return errors.New(fmt.Sprintf("Creating temp dir: %v", err))
|
||||
}
|
||||
|
||||
defer os.RemoveAll(tmpDir)
|
||||
|
||||
// Create a file to hold generated code.
|
||||
codeFile, err := os.Create(path.Join(tmpDir, "tool.go"))
|
||||
if err != nil {
|
||||
return errors.New(fmt.Sprintf("Couldn't create a file to hold code: %v", err))
|
||||
}
|
||||
|
||||
// Create an appropriate path for the built binary.
|
||||
binaryPath := path.Join(tmpDir, "tool")
|
||||
|
||||
// Create an appropriate template argument.
|
||||
var arg tmplArg
|
||||
arg.InputPkg = cmdLineArgs[0]
|
||||
arg.OutputPkg = "mock_" + path.Base(arg.InputPkg)
|
||||
arg.TypeNames = cmdLineArgs[1:]
|
||||
|
||||
arg.Imports = make(importMap)
|
||||
arg.Imports[path.Base(arg.InputPkg)] = arg.InputPkg
|
||||
arg.Imports["generate"] = "github.com/smartystreets/goconvey/convey/assertions/oglemock/generate"
|
||||
arg.Imports["log"] = "log"
|
||||
arg.Imports["os"] = "os"
|
||||
arg.Imports["reflect"] = "reflect"
|
||||
|
||||
// Execute the template to generate code that will itself generate the mock
|
||||
// code. Write the code to the temp file.
|
||||
tmpl := template.Must(
|
||||
template.New("code").Funcs(
|
||||
template.FuncMap{
|
||||
"base": path.Base,
|
||||
}).Parse(tmplStr))
|
||||
if err := tmpl.Execute(codeFile, arg); err != nil {
|
||||
return errors.New(fmt.Sprintf("Error executing template: %v", err))
|
||||
}
|
||||
|
||||
codeFile.Close()
|
||||
|
||||
// Attempt to build the code.
|
||||
cmd := exec.Command("go", "build", "-o", binaryPath)
|
||||
cmd.Dir = tmpDir
|
||||
buildOutput, err := cmd.CombinedOutput()
|
||||
|
||||
if err != nil {
|
||||
// Did the compilation fail due to the user-specified package not being found?
|
||||
if pkg := findUnknownPackage(buildOutput); pkg != nil && *pkg == arg.InputPkg {
|
||||
return errors.New(fmt.Sprintf("Unknown package: %s", *pkg))
|
||||
}
|
||||
|
||||
// Did the compilation fail due to an unknown interface?
|
||||
if in := findUndefinedInterface(buildOutput); in != nil {
|
||||
return errors.New(fmt.Sprintf("Unknown interface: %s", *in))
|
||||
}
|
||||
|
||||
// Otherwise return a generic error.
|
||||
return errors.New(fmt.Sprintf(
|
||||
"%s\n\nError building generated code:\n\n"+
|
||||
" %v\n\nPlease report this oglemock bug.",
|
||||
buildOutput,
|
||||
err))
|
||||
}
|
||||
|
||||
// Run the binary.
|
||||
cmd = exec.Command(binaryPath)
|
||||
binaryOutput, err := cmd.CombinedOutput()
|
||||
|
||||
if err != nil {
|
||||
return errors.New(fmt.Sprintf(
|
||||
"%s\n\nError running generated code:\n\n"+
|
||||
" %v\n\n Please report this oglemock bug.",
|
||||
binaryOutput,
|
||||
err))
|
||||
}
|
||||
|
||||
// Copy its output.
|
||||
_, err = os.Stdout.Write(binaryOutput)
|
||||
if err != nil {
|
||||
return errors.New(fmt.Sprintf("Error copying binary output: %v", err))
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func main() {
|
||||
if err := run(); err != nil {
|
||||
fmt.Println(err.Error())
|
||||
os.Exit(1)
|
||||
}
|
||||
}
|
||||
Generated
Vendored
-1
@@ -1 +0,0 @@
|
||||
Usage: createmock [package] [interface ...]
|
||||
Generated
Vendored
-1
@@ -1 +0,0 @@
|
||||
Usage: createmock [package] [interface ...]
|
||||
Generated
Vendored
-1
@@ -1 +0,0 @@
|
||||
Unknown interface: Frobnicator
|
||||
Generated
Vendored
-1
@@ -1 +0,0 @@
|
||||
Unknown package: foo/bar
|
||||
Godeps/_workspace/src/github.com/smartystreets/goconvey/convey/assertions/oglemock/error_reporter.go
Generated
Vendored
-29
@@ -1,29 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglemock
|
||||
|
||||
// ErrorReporter is an interface that wraps methods for reporting errors that
|
||||
// should cause test failures.
|
||||
type ErrorReporter interface {
|
||||
// Report that some failure (e.g. an unsatisfied expectation) occurred. If
|
||||
// known, fileName and lineNumber should contain information about where it
|
||||
// occurred. The test may continue if the test framework supports it.
|
||||
ReportError(fileName string, lineNumber int, err error)
|
||||
|
||||
// Like ReportError, but the test should be halted immediately. It is assumed
|
||||
// that this method does not return.
|
||||
ReportFatalError(fileName string, lineNumber int, err error)
|
||||
}
|
||||
Generated
Vendored
-59
@@ -1,59 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglemock
|
||||
|
||||
// Expectation is an expectation for zero or more calls to a mock method with
|
||||
// particular arguments or sets of arguments.
|
||||
type Expectation interface {
|
||||
// Times expresses that a matching method call should happen exactly N times.
|
||||
// Times must not be called more than once, and must not be called after
|
||||
// WillOnce or WillRepeatedly.
|
||||
//
|
||||
// The full rules for the cardinality of an expectation are as follows:
|
||||
//
|
||||
// 1. If an explicit cardinality is set with Times(N), then anything other
|
||||
// than exactly N matching calls will cause a test failure.
|
||||
//
|
||||
// 2. Otherwise, if there are any one-time actions set up, then it is
|
||||
// expected there will be at least that many matching calls. If there is
|
||||
// not also a fallback action, then it is expected that there will be
|
||||
// exactly that many.
|
||||
//
|
||||
// 3. Otherwise, if there is a fallback action configured, any number of
|
||||
// matching calls (including zero) is allowed.
|
||||
//
|
||||
// 4. Otherwise, the implicit cardinality is one.
|
||||
//
|
||||
Times(n uint) Expectation
|
||||
|
||||
// WillOnce configures a "one-time action". WillOnce can be called zero or
|
||||
// more times, but must be called after any call to Times and before any call
|
||||
// to WillRepeatedly.
|
||||
//
|
||||
// When matching method calls are made on the mock object, one-time actions
|
||||
// are invoked one per matching call in the order that they were set up until
|
||||
// they are exhausted. Afterward the fallback action, if any, will be used.
|
||||
WillOnce(a Action) Expectation
|
||||
|
||||
// WillRepeatedly configures a "fallback action". WillRepeatedly can be
|
||||
// called zero or one times, and must not be called before Times or WillOnce.
|
||||
//
|
||||
// Once all one-time actions are exhausted (see above), the fallback action
|
||||
// will be invoked for any further method calls. If WillRepeatedly is not
|
||||
// called, the fallback action is implicitly an action that returns zero
|
||||
// values for the method's return values.
|
||||
WillRepeatedly(a Action) Expectation
|
||||
}
|
||||
Generated
Vendored
-329
@@ -1,329 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
// Package generate implements code generation for mock classes. This is an
|
||||
// implementation detail of the createmock command, which you probably want to
|
||||
// use directly instead.
|
||||
package generate
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"errors"
|
||||
"go/ast"
|
||||
"go/parser"
|
||||
"go/printer"
|
||||
"go/token"
|
||||
"io"
|
||||
"reflect"
|
||||
"regexp"
|
||||
"text/template"
|
||||
)
|
||||
|
||||
const tmplStr = `
|
||||
// This file was auto-generated using createmock. See the following page for
|
||||
// more information:
|
||||
//
|
||||
// https://github.com/smartystreets/goconvey/convey/assertions/oglemock
|
||||
//
|
||||
|
||||
package {{.Pkg}}
|
||||
|
||||
import (
|
||||
{{range $identifier, $import := .Imports}}{{$identifier}} "{{$import}}"
|
||||
{{end}}
|
||||
)
|
||||
|
||||
{{range .Interfaces}}
|
||||
{{$interfaceName := printf "Mock%s" .Name}}
|
||||
{{$structName := printf "mock%s" .Name}}
|
||||
|
||||
type {{$interfaceName}} interface {
|
||||
{{getTypeString .}}
|
||||
oglemock.MockObject
|
||||
}
|
||||
|
||||
type {{$structName}} struct {
|
||||
controller oglemock.Controller
|
||||
description string
|
||||
}
|
||||
|
||||
func New{{printf "Mock%s" .Name}}(
|
||||
c oglemock.Controller,
|
||||
desc string) {{$interfaceName}} {
|
||||
return &{{$structName}}{
|
||||
controller: c,
|
||||
description: desc,
|
||||
}
|
||||
}
|
||||
|
||||
func (m *{{$structName}}) Oglemock_Id() uintptr {
|
||||
return uintptr(unsafe.Pointer(m))
|
||||
}
|
||||
|
||||
func (m *{{$structName}}) Oglemock_Description() string {
|
||||
return m.description
|
||||
}
|
||||
|
||||
{{range getMethods .}}
|
||||
{{$funcType := .Type}}
|
||||
{{$inputTypes := getInputs $funcType}}
|
||||
{{$outputTypes := getOutputs $funcType}}
|
||||
|
||||
func (m *{{$structName}}) {{.Name}}({{range $i, $type := $inputTypes}}p{{$i}} {{getInputTypeString $i $funcType}}, {{end}}) ({{range $i, $type := $outputTypes}}o{{$i}} {{getTypeString $type}}, {{end}}) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"{{.Name}}",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{ {{range $i, $type := $inputTypes}}p{{$i}}, {{end}} })
|
||||
|
||||
if len(retVals) != {{len $outputTypes}} {
|
||||
panic(fmt.Sprintf("{{$structName}}.{{.Name}}: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
{{range $i, $type := $outputTypes}}
|
||||
// o{{$i}} {{getTypeString $type}}
|
||||
if retVals[{{$i}}] != nil {
|
||||
o{{$i}} = retVals[{{$i}}].({{getTypeString $type}})
|
||||
}
|
||||
{{end}}
|
||||
|
||||
return
|
||||
}
|
||||
{{end}}
|
||||
{{end}}
|
||||
`
|
||||
|
||||
type tmplArg struct {
|
||||
// The package of the generated code.
|
||||
Pkg string
|
||||
|
||||
// Imports needed by the interfaces.
|
||||
Imports importMap
|
||||
|
||||
// The set of interfaces to mock.
|
||||
Interfaces []reflect.Type
|
||||
}
|
||||
|
||||
var tmpl *template.Template
|
||||
|
||||
func init() {
|
||||
extraFuncs := make(template.FuncMap)
|
||||
extraFuncs["getMethods"] = getMethods
|
||||
extraFuncs["getInputs"] = getInputs
|
||||
extraFuncs["getOutputs"] = getOutputs
|
||||
extraFuncs["getInputTypeString"] = getInputTypeString
|
||||
extraFuncs["getTypeString"] = getTypeString
|
||||
|
||||
tmpl = template.New("code")
|
||||
tmpl.Funcs(extraFuncs)
|
||||
tmpl.Parse(tmplStr)
|
||||
}
|
||||
|
||||
func getInputTypeString(i int, ft reflect.Type) string {
|
||||
numInputs := ft.NumIn()
|
||||
if i == numInputs-1 && ft.IsVariadic() {
|
||||
return "..." + getTypeString(ft.In(i).Elem())
|
||||
}
|
||||
|
||||
return getTypeString(ft.In(i))
|
||||
}
|
||||
|
||||
func getTypeString(t reflect.Type) string {
|
||||
return t.String()
|
||||
}
|
||||
|
||||
func getMethods(it reflect.Type) []reflect.Method {
|
||||
numMethods := it.NumMethod()
|
||||
methods := make([]reflect.Method, numMethods)
|
||||
|
||||
for i := 0; i < numMethods; i++ {
|
||||
methods[i] = it.Method(i)
|
||||
}
|
||||
|
||||
return methods
|
||||
}
|
||||
|
||||
func getInputs(ft reflect.Type) []reflect.Type {
|
||||
numIn := ft.NumIn()
|
||||
inputs := make([]reflect.Type, numIn)
|
||||
|
||||
for i := 0; i < numIn; i++ {
|
||||
inputs[i] = ft.In(i)
|
||||
}
|
||||
|
||||
return inputs
|
||||
}
|
||||
|
||||
func getOutputs(ft reflect.Type) []reflect.Type {
|
||||
numOut := ft.NumOut()
|
||||
outputs := make([]reflect.Type, numOut)
|
||||
|
||||
for i := 0; i < numOut; i++ {
|
||||
outputs[i] = ft.Out(i)
|
||||
}
|
||||
|
||||
return outputs
|
||||
}
|
||||
|
||||
// A map from import identifier to package to use that identifier for,
|
||||
// containing elements for each import needed by a set of mocked interfaces.
|
||||
type importMap map[string]string
|
||||
|
||||
var typePackageIdentifierRegexp = regexp.MustCompile(`^([\pL_0-9]+)\.[\pL_0-9]+$`)
|
||||
|
||||
// Add an import for the supplied type, without recursing.
|
||||
func addImportForType(imports importMap, t reflect.Type) {
|
||||
// If there is no package path, this is a built-in type and we don't need an
|
||||
// import.
|
||||
pkgPath := t.PkgPath()
|
||||
if pkgPath == "" {
|
||||
return
|
||||
}
|
||||
|
||||
// Work around a bug in Go:
|
||||
//
|
||||
// http://code.google.com/p/go/issues/detail?id=2660
|
||||
//
|
||||
var errorPtr *error
|
||||
if t == reflect.TypeOf(errorPtr).Elem() {
|
||||
return
|
||||
}
|
||||
|
||||
// Use the identifier that's part of the type's string representation as the
|
||||
// import identifier. This means that we'll do the right thing for package
|
||||
// "foo/bar" with declaration "package baz".
|
||||
match := typePackageIdentifierRegexp.FindStringSubmatch(t.String())
|
||||
if match == nil {
|
||||
return
|
||||
}
|
||||
|
||||
imports[match[1]] = pkgPath
|
||||
}
|
||||
|
||||
// Add all necessary imports for the type, recursing as appropriate.
|
||||
func addImportsForType(imports importMap, t reflect.Type) {
|
||||
// Add any import needed for the type itself.
|
||||
addImportForType(imports, t)
|
||||
|
||||
// Handle special cases where recursion is needed.
|
||||
switch t.Kind() {
|
||||
case reflect.Array, reflect.Chan, reflect.Ptr, reflect.Slice:
|
||||
addImportsForType(imports, t.Elem())
|
||||
|
||||
case reflect.Func:
|
||||
// Input parameters.
|
||||
for i := 0; i < t.NumIn(); i++ {
|
||||
addImportsForType(imports, t.In(i))
|
||||
}
|
||||
|
||||
// Return values.
|
||||
for i := 0; i < t.NumOut(); i++ {
|
||||
addImportsForType(imports, t.Out(i))
|
||||
}
|
||||
|
||||
case reflect.Map:
|
||||
addImportsForType(imports, t.Key())
|
||||
addImportsForType(imports, t.Elem())
|
||||
}
|
||||
}
|
||||
|
||||
// Add imports for each of the methods of the interface, but not the interface
|
||||
// itself.
|
||||
func addImportsForInterfaceMethods(imports importMap, it reflect.Type) {
|
||||
// Handle each method.
|
||||
for i := 0; i < it.NumMethod(); i++ {
|
||||
m := it.Method(i)
|
||||
addImportsForType(imports, m.Type)
|
||||
}
|
||||
}
|
||||
|
||||
// Given a set of interfaces, return a map from import identifier to package to
|
||||
// use that identifier for, containing elements for each import needed by the
|
||||
// mock versions of those interfaces.
|
||||
func getImports(interfaces []reflect.Type) importMap {
|
||||
imports := make(importMap)
|
||||
for _, it := range interfaces {
|
||||
addImportForType(imports, it)
|
||||
addImportsForInterfaceMethods(imports, it)
|
||||
}
|
||||
|
||||
// Make sure there are imports for other types used by the generated code
|
||||
// itself.
|
||||
imports["fmt"] = "fmt"
|
||||
imports["oglemock"] = "github.com/smartystreets/goconvey/convey/assertions/oglemock"
|
||||
imports["runtime"] = "runtime"
|
||||
imports["unsafe"] = "unsafe"
|
||||
|
||||
return imports
|
||||
}
|
||||
|
||||
// Given a set of interfaces to mock, write out source code for a package named
|
||||
// `pkg` that contains mock implementations of those interfaces.
|
||||
func GenerateMockSource(w io.Writer, pkg string, interfaces []reflect.Type) error {
|
||||
// Sanity-check arguments.
|
||||
if pkg == "" {
|
||||
return errors.New("Package name must be non-empty.")
|
||||
}
|
||||
|
||||
if len(interfaces) == 0 {
|
||||
return errors.New("List of interfaces must be non-empty.")
|
||||
}
|
||||
|
||||
// Make sure each type is indeed an interface.
|
||||
for _, it := range interfaces {
|
||||
if it.Kind() != reflect.Interface {
|
||||
return errors.New("Invalid type: " + it.String())
|
||||
}
|
||||
}
|
||||
|
||||
// Create an appropriate template arg, then execute the template. Write the
|
||||
// raw output into a buffer.
|
||||
var arg tmplArg
|
||||
arg.Pkg = pkg
|
||||
arg.Imports = getImports(interfaces)
|
||||
arg.Interfaces = interfaces
|
||||
|
||||
buf := new(bytes.Buffer)
|
||||
if err := tmpl.Execute(buf, arg); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// Parse the output.
|
||||
fset := token.NewFileSet()
|
||||
astFile, err := parser.ParseFile(fset, pkg+".go", buf, parser.ParseComments)
|
||||
if err != nil {
|
||||
return errors.New("Error parsing generated code: " + err.Error())
|
||||
}
|
||||
|
||||
// Sort the import lines in the AST in the same way that gofmt does.
|
||||
ast.SortImports(fset, astFile)
|
||||
|
||||
// Pretty-print the AST, using the same options that gofmt does by default.
|
||||
cfg := &printer.Config{
|
||||
Mode: printer.UseSpaces | printer.TabIndent,
|
||||
Tabwidth: 8,
|
||||
}
|
||||
|
||||
if err = cfg.Fprint(w, fset, astFile); err != nil {
|
||||
return errors.New("Error pretty printing: " + err.Error())
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
Generated
Vendored
-41
@@ -1,41 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
// Package complicated_pkg contains an interface with lots of interesting
|
||||
// cases, for use in integration testing.
|
||||
package complicated_pkg
|
||||
|
||||
import (
|
||||
"image"
|
||||
"io"
|
||||
"net"
|
||||
|
||||
"github.com/smartystreets/goconvey/convey/assertions/oglemock/generate/test_cases/renamed_pkg"
|
||||
)
|
||||
|
||||
type Byte uint8
|
||||
|
||||
type ComplicatedThing interface {
|
||||
Channels(a chan chan<- <-chan net.Conn) chan int
|
||||
Pointers(a *int, b *net.Conn, c **io.Reader) (*int, error)
|
||||
Functions(a func(int, image.Image) int) func(string, int) net.Conn
|
||||
Maps(a map[string]*int) (map[int]*string, error)
|
||||
Arrays(a [3]string) ([3]int, error)
|
||||
Slices(a []string) ([]int, error)
|
||||
NamedScalarType(a Byte) ([]Byte, error)
|
||||
EmptyInterface(a interface{}) (interface{}, error)
|
||||
RenamedPackage(a tony.SomeUint8Alias)
|
||||
Variadic(a int, b ...net.Conn) int
|
||||
}
|
||||
Generated
Vendored
-312
@@ -1,312 +0,0 @@
|
||||
// This file was auto-generated using createmock. See the following page for
|
||||
// more information:
|
||||
//
|
||||
// https://github.com/smartystreets/goconvey/convey/assertions/oglemock
|
||||
//
|
||||
|
||||
package some_pkg
|
||||
|
||||
import (
|
||||
fmt "fmt"
|
||||
image "image"
|
||||
io "io"
|
||||
net "net"
|
||||
runtime "runtime"
|
||||
unsafe "unsafe"
|
||||
|
||||
oglemock "github.com/smartystreets/goconvey/convey/assertions/oglemock"
|
||||
complicated_pkg "github.com/smartystreets/goconvey/convey/assertions/oglemock/generate/test_cases/complicated_pkg"
|
||||
tony "github.com/smartystreets/goconvey/convey/assertions/oglemock/generate/test_cases/renamed_pkg"
|
||||
)
|
||||
|
||||
type MockComplicatedThing interface {
|
||||
complicated_pkg.ComplicatedThing
|
||||
oglemock.MockObject
|
||||
}
|
||||
|
||||
type mockComplicatedThing struct {
|
||||
controller oglemock.Controller
|
||||
description string
|
||||
}
|
||||
|
||||
func NewMockComplicatedThing(
|
||||
c oglemock.Controller,
|
||||
desc string) MockComplicatedThing {
|
||||
return &mockComplicatedThing{
|
||||
controller: c,
|
||||
description: desc,
|
||||
}
|
||||
}
|
||||
|
||||
func (m *mockComplicatedThing) Oglemock_Id() uintptr {
|
||||
return uintptr(unsafe.Pointer(m))
|
||||
}
|
||||
|
||||
func (m *mockComplicatedThing) Oglemock_Description() string {
|
||||
return m.description
|
||||
}
|
||||
|
||||
func (m *mockComplicatedThing) Arrays(p0 [3]string) (o0 [3]int, o1 error) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Arrays",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0})
|
||||
|
||||
if len(retVals) != 2 {
|
||||
panic(fmt.Sprintf("mockComplicatedThing.Arrays: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 [3]int
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].([3]int)
|
||||
}
|
||||
|
||||
// o1 error
|
||||
if retVals[1] != nil {
|
||||
o1 = retVals[1].(error)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockComplicatedThing) Channels(p0 chan chan<- <-chan net.Conn) (o0 chan int) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Channels",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockComplicatedThing.Channels: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 chan int
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(chan int)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockComplicatedThing) EmptyInterface(p0 interface{}) (o0 interface{}, o1 error) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"EmptyInterface",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0})
|
||||
|
||||
if len(retVals) != 2 {
|
||||
panic(fmt.Sprintf("mockComplicatedThing.EmptyInterface: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 interface {}
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(interface{})
|
||||
}
|
||||
|
||||
// o1 error
|
||||
if retVals[1] != nil {
|
||||
o1 = retVals[1].(error)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockComplicatedThing) Functions(p0 func(int, image.Image) int) (o0 func(string, int) net.Conn) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Functions",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockComplicatedThing.Functions: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 func(string, int) net.Conn
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(func(string, int) net.Conn)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockComplicatedThing) Maps(p0 map[string]*int) (o0 map[int]*string, o1 error) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Maps",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0})
|
||||
|
||||
if len(retVals) != 2 {
|
||||
panic(fmt.Sprintf("mockComplicatedThing.Maps: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 map[int]*string
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(map[int]*string)
|
||||
}
|
||||
|
||||
// o1 error
|
||||
if retVals[1] != nil {
|
||||
o1 = retVals[1].(error)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockComplicatedThing) NamedScalarType(p0 complicated_pkg.Byte) (o0 []complicated_pkg.Byte, o1 error) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"NamedScalarType",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0})
|
||||
|
||||
if len(retVals) != 2 {
|
||||
panic(fmt.Sprintf("mockComplicatedThing.NamedScalarType: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 []complicated_pkg.Byte
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].([]complicated_pkg.Byte)
|
||||
}
|
||||
|
||||
// o1 error
|
||||
if retVals[1] != nil {
|
||||
o1 = retVals[1].(error)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockComplicatedThing) Pointers(p0 *int, p1 *net.Conn, p2 **io.Reader) (o0 *int, o1 error) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Pointers",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0, p1, p2})
|
||||
|
||||
if len(retVals) != 2 {
|
||||
panic(fmt.Sprintf("mockComplicatedThing.Pointers: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 *int
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(*int)
|
||||
}
|
||||
|
||||
// o1 error
|
||||
if retVals[1] != nil {
|
||||
o1 = retVals[1].(error)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockComplicatedThing) RenamedPackage(p0 tony.SomeUint8Alias) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"RenamedPackage",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0})
|
||||
|
||||
if len(retVals) != 0 {
|
||||
panic(fmt.Sprintf("mockComplicatedThing.RenamedPackage: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockComplicatedThing) Slices(p0 []string) (o0 []int, o1 error) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Slices",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0})
|
||||
|
||||
if len(retVals) != 2 {
|
||||
panic(fmt.Sprintf("mockComplicatedThing.Slices: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 []int
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].([]int)
|
||||
}
|
||||
|
||||
// o1 error
|
||||
if retVals[1] != nil {
|
||||
o1 = retVals[1].(error)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockComplicatedThing) Variadic(p0 int, p1 ...net.Conn) (o0 int) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Variadic",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0, p1})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockComplicatedThing.Variadic: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 int
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(int)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
Generated
Vendored
-239
@@ -1,239 +0,0 @@
|
||||
// This file was auto-generated using createmock. See the following page for
|
||||
// more information:
|
||||
//
|
||||
// https://github.com/smartystreets/goconvey/convey/assertions/oglemock
|
||||
//
|
||||
|
||||
package some_pkg
|
||||
|
||||
import (
|
||||
fmt "fmt"
|
||||
image "image"
|
||||
color "image/color"
|
||||
runtime "runtime"
|
||||
unsafe "unsafe"
|
||||
|
||||
oglemock "github.com/smartystreets/goconvey/convey/assertions/oglemock"
|
||||
)
|
||||
|
||||
type MockImage interface {
|
||||
image.Image
|
||||
oglemock.MockObject
|
||||
}
|
||||
|
||||
type mockImage struct {
|
||||
controller oglemock.Controller
|
||||
description string
|
||||
}
|
||||
|
||||
func NewMockImage(
|
||||
c oglemock.Controller,
|
||||
desc string) MockImage {
|
||||
return &mockImage{
|
||||
controller: c,
|
||||
description: desc,
|
||||
}
|
||||
}
|
||||
|
||||
func (m *mockImage) Oglemock_Id() uintptr {
|
||||
return uintptr(unsafe.Pointer(m))
|
||||
}
|
||||
|
||||
func (m *mockImage) Oglemock_Description() string {
|
||||
return m.description
|
||||
}
|
||||
|
||||
func (m *mockImage) At(p0 int, p1 int) (o0 color.Color) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"At",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0, p1})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockImage.At: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 color.Color
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(color.Color)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockImage) Bounds() (o0 image.Rectangle) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Bounds",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockImage.Bounds: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 image.Rectangle
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(image.Rectangle)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockImage) ColorModel() (o0 color.Model) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"ColorModel",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockImage.ColorModel: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 color.Model
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(color.Model)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
type MockPalettedImage interface {
|
||||
image.PalettedImage
|
||||
oglemock.MockObject
|
||||
}
|
||||
|
||||
type mockPalettedImage struct {
|
||||
controller oglemock.Controller
|
||||
description string
|
||||
}
|
||||
|
||||
func NewMockPalettedImage(
|
||||
c oglemock.Controller,
|
||||
desc string) MockPalettedImage {
|
||||
return &mockPalettedImage{
|
||||
controller: c,
|
||||
description: desc,
|
||||
}
|
||||
}
|
||||
|
||||
func (m *mockPalettedImage) Oglemock_Id() uintptr {
|
||||
return uintptr(unsafe.Pointer(m))
|
||||
}
|
||||
|
||||
func (m *mockPalettedImage) Oglemock_Description() string {
|
||||
return m.description
|
||||
}
|
||||
|
||||
func (m *mockPalettedImage) At(p0 int, p1 int) (o0 color.Color) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"At",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0, p1})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockPalettedImage.At: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 color.Color
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(color.Color)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockPalettedImage) Bounds() (o0 image.Rectangle) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Bounds",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockPalettedImage.Bounds: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 image.Rectangle
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(image.Rectangle)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockPalettedImage) ColorIndexAt(p0 int, p1 int) (o0 uint8) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"ColorIndexAt",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0, p1})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockPalettedImage.ColorIndexAt: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 uint8
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(uint8)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockPalettedImage) ColorModel() (o0 color.Model) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"ColorModel",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockPalettedImage.ColorModel: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 color.Model
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(color.Model)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
Generated
Vendored
-128
@@ -1,128 +0,0 @@
|
||||
// This file was auto-generated using createmock. See the following page for
|
||||
// more information:
|
||||
//
|
||||
// https://github.com/smartystreets/goconvey/convey/assertions/oglemock
|
||||
//
|
||||
|
||||
package some_pkg
|
||||
|
||||
import (
|
||||
fmt "fmt"
|
||||
io "io"
|
||||
runtime "runtime"
|
||||
unsafe "unsafe"
|
||||
|
||||
oglemock "github.com/smartystreets/goconvey/convey/assertions/oglemock"
|
||||
)
|
||||
|
||||
type MockReader interface {
|
||||
io.Reader
|
||||
oglemock.MockObject
|
||||
}
|
||||
|
||||
type mockReader struct {
|
||||
controller oglemock.Controller
|
||||
description string
|
||||
}
|
||||
|
||||
func NewMockReader(
|
||||
c oglemock.Controller,
|
||||
desc string) MockReader {
|
||||
return &mockReader{
|
||||
controller: c,
|
||||
description: desc,
|
||||
}
|
||||
}
|
||||
|
||||
func (m *mockReader) Oglemock_Id() uintptr {
|
||||
return uintptr(unsafe.Pointer(m))
|
||||
}
|
||||
|
||||
func (m *mockReader) Oglemock_Description() string {
|
||||
return m.description
|
||||
}
|
||||
|
||||
func (m *mockReader) Read(p0 []uint8) (o0 int, o1 error) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Read",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0})
|
||||
|
||||
if len(retVals) != 2 {
|
||||
panic(fmt.Sprintf("mockReader.Read: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 int
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(int)
|
||||
}
|
||||
|
||||
// o1 error
|
||||
if retVals[1] != nil {
|
||||
o1 = retVals[1].(error)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
type MockWriter interface {
|
||||
io.Writer
|
||||
oglemock.MockObject
|
||||
}
|
||||
|
||||
type mockWriter struct {
|
||||
controller oglemock.Controller
|
||||
description string
|
||||
}
|
||||
|
||||
func NewMockWriter(
|
||||
c oglemock.Controller,
|
||||
desc string) MockWriter {
|
||||
return &mockWriter{
|
||||
controller: c,
|
||||
description: desc,
|
||||
}
|
||||
}
|
||||
|
||||
func (m *mockWriter) Oglemock_Id() uintptr {
|
||||
return uintptr(unsafe.Pointer(m))
|
||||
}
|
||||
|
||||
func (m *mockWriter) Oglemock_Description() string {
|
||||
return m.description
|
||||
}
|
||||
|
||||
func (m *mockWriter) Write(p0 []uint8) (o0 int, o1 error) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Write",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0})
|
||||
|
||||
if len(retVals) != 2 {
|
||||
panic(fmt.Sprintf("mockWriter.Write: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 int
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(int)
|
||||
}
|
||||
|
||||
// o1 error
|
||||
if retVals[1] != nil {
|
||||
o1 = retVals[1].(error)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
Generated
Vendored
-67
@@ -1,67 +0,0 @@
|
||||
// This file was auto-generated using createmock. See the following page for
|
||||
// more information:
|
||||
//
|
||||
// https://github.com/smartystreets/goconvey/convey/assertions/oglemock
|
||||
//
|
||||
|
||||
package some_pkg
|
||||
|
||||
import (
|
||||
fmt "fmt"
|
||||
runtime "runtime"
|
||||
unsafe "unsafe"
|
||||
|
||||
oglemock "github.com/smartystreets/goconvey/convey/assertions/oglemock"
|
||||
tony "github.com/smartystreets/goconvey/convey/assertions/oglemock/generate/test_cases/renamed_pkg"
|
||||
)
|
||||
|
||||
type MockSomeInterface interface {
|
||||
tony.SomeInterface
|
||||
oglemock.MockObject
|
||||
}
|
||||
|
||||
type mockSomeInterface struct {
|
||||
controller oglemock.Controller
|
||||
description string
|
||||
}
|
||||
|
||||
func NewMockSomeInterface(
|
||||
c oglemock.Controller,
|
||||
desc string) MockSomeInterface {
|
||||
return &mockSomeInterface{
|
||||
controller: c,
|
||||
description: desc,
|
||||
}
|
||||
}
|
||||
|
||||
func (m *mockSomeInterface) Oglemock_Id() uintptr {
|
||||
return uintptr(unsafe.Pointer(m))
|
||||
}
|
||||
|
||||
func (m *mockSomeInterface) Oglemock_Description() string {
|
||||
return m.description
|
||||
}
|
||||
|
||||
func (m *mockSomeInterface) DoFoo(p0 int) (o0 int) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"DoFoo",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockSomeInterface.DoFoo: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 int
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(int)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
Generated
Vendored
-24
@@ -1,24 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
// A package that calls itself something different than its package path would
|
||||
// have you believe.
|
||||
package tony
|
||||
|
||||
type SomeUint8Alias uint8
|
||||
|
||||
type SomeInterface interface {
|
||||
DoFoo(a int) int
|
||||
}
|
||||
Generated
Vendored
-181
@@ -1,181 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglemock
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"reflect"
|
||||
"sync"
|
||||
|
||||
"github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
)
|
||||
|
||||
// InternalExpectation is exported for purposes of testing only. You should not
|
||||
// touch it.
|
||||
//
|
||||
// InternalExpectation represents an expectation for zero or more calls to a
|
||||
// mock method, and a set of actions to be taken when those calls are received.
|
||||
type InternalExpectation struct {
|
||||
// The signature of the method to which this expectation is bound, for
|
||||
// checking action types.
|
||||
methodSignature reflect.Type
|
||||
|
||||
// An error reporter to use for reporting errors in the way that expectations
|
||||
// are set.
|
||||
errorReporter ErrorReporter
|
||||
|
||||
// A mutex protecting mutable fields of the struct.
|
||||
mutex sync.Mutex
|
||||
|
||||
// Matchers that the arguments to the mock method must satisfy in order to
|
||||
// match this expectation.
|
||||
ArgMatchers []oglematchers.Matcher
|
||||
|
||||
// The name of the file in which this expectation was expressed.
|
||||
FileName string
|
||||
|
||||
// The line number at which this expectation was expressed.
|
||||
LineNumber int
|
||||
|
||||
// The number of times this expectation should be matched, as explicitly
|
||||
// listed by the user. If there was no explicit number expressed, this is -1.
|
||||
ExpectedNumMatches int
|
||||
|
||||
// Actions to be taken for the first N calls, one per call in order, where N
|
||||
// is the length of this slice.
|
||||
OneTimeActions []Action
|
||||
|
||||
// An action to be taken when the one-time actions have expired, or nil if
|
||||
// there is no such action.
|
||||
FallbackAction Action
|
||||
|
||||
// The number of times this expectation has been matched so far.
|
||||
NumMatches uint
|
||||
}
|
||||
|
||||
// InternalNewExpectation is exported for purposes of testing only. You should
|
||||
// not touch it.
|
||||
func InternalNewExpectation(
|
||||
reporter ErrorReporter,
|
||||
methodSignature reflect.Type,
|
||||
args []interface{},
|
||||
fileName string,
|
||||
lineNumber int) *InternalExpectation {
|
||||
result := &InternalExpectation{}
|
||||
|
||||
// Store fields that can be stored directly.
|
||||
result.methodSignature = methodSignature
|
||||
result.errorReporter = reporter
|
||||
result.FileName = fileName
|
||||
result.LineNumber = lineNumber
|
||||
|
||||
// Set up defaults.
|
||||
result.ExpectedNumMatches = -1
|
||||
result.OneTimeActions = make([]Action, 0)
|
||||
|
||||
// Set up the ArgMatchers slice, using Equals(x) for each x that is not a
|
||||
// matcher itself.
|
||||
result.ArgMatchers = make([]oglematchers.Matcher, len(args))
|
||||
for i, x := range args {
|
||||
if matcher, ok := x.(oglematchers.Matcher); ok {
|
||||
result.ArgMatchers[i] = matcher
|
||||
} else {
|
||||
result.ArgMatchers[i] = oglematchers.Equals(x)
|
||||
}
|
||||
}
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
func (e *InternalExpectation) Times(n uint) Expectation {
|
||||
e.mutex.Lock()
|
||||
defer e.mutex.Unlock()
|
||||
|
||||
// It is illegal to call this more than once.
|
||||
if e.ExpectedNumMatches != -1 {
|
||||
e.reportFatalError("Times called more than once.")
|
||||
return nil
|
||||
}
|
||||
|
||||
// It is illegal to call this after any actions are configured.
|
||||
if len(e.OneTimeActions) != 0 {
|
||||
e.reportFatalError("Times called after WillOnce.")
|
||||
return nil
|
||||
}
|
||||
|
||||
if e.FallbackAction != nil {
|
||||
e.reportFatalError("Times called after WillRepeatedly.")
|
||||
return nil
|
||||
}
|
||||
|
||||
// Make sure the number is reasonable (and will fit in an int).
|
||||
if n > 1000 {
|
||||
e.reportFatalError("Expectation.Times: N must be at most 1000")
|
||||
return nil
|
||||
}
|
||||
|
||||
e.ExpectedNumMatches = int(n)
|
||||
return e
|
||||
}
|
||||
|
||||
func (e *InternalExpectation) WillOnce(a Action) Expectation {
|
||||
e.mutex.Lock()
|
||||
defer e.mutex.Unlock()
|
||||
|
||||
// It is illegal to call this after WillRepeatedly.
|
||||
if e.FallbackAction != nil {
|
||||
e.reportFatalError("WillOnce called after WillRepeatedly.")
|
||||
return nil
|
||||
}
|
||||
|
||||
// Tell the action about the method's signature.
|
||||
if err := a.SetSignature(e.methodSignature); err != nil {
|
||||
e.reportFatalError(fmt.Sprintf("WillOnce given invalid action: %v", err))
|
||||
return nil
|
||||
}
|
||||
|
||||
// Store the action.
|
||||
e.OneTimeActions = append(e.OneTimeActions, a)
|
||||
|
||||
return e
|
||||
}
|
||||
|
||||
func (e *InternalExpectation) WillRepeatedly(a Action) Expectation {
|
||||
e.mutex.Lock()
|
||||
defer e.mutex.Unlock()
|
||||
|
||||
// It is illegal to call this twice.
|
||||
if e.FallbackAction != nil {
|
||||
e.reportFatalError("WillRepeatedly called more than once.")
|
||||
return nil
|
||||
}
|
||||
|
||||
// Tell the action about the method's signature.
|
||||
if err := a.SetSignature(e.methodSignature); err != nil {
|
||||
e.reportFatalError(fmt.Sprintf("WillRepeatedly given invalid action: %v", err))
|
||||
return nil
|
||||
}
|
||||
|
||||
// Store the action.
|
||||
e.FallbackAction = a
|
||||
|
||||
return e
|
||||
}
|
||||
|
||||
func (e *InternalExpectation) reportFatalError(errorText string) {
|
||||
e.errorReporter.ReportFatalError(e.FileName, e.LineNumber, errors.New(errorText))
|
||||
}
|
||||
Generated
Vendored
-73
@@ -1,73 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglemock
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"reflect"
|
||||
)
|
||||
|
||||
// Create an Action that invokes the supplied function, returning whatever it
|
||||
// returns. The signature of the function must match that of the mocked method
|
||||
// exactly.
|
||||
func Invoke(f interface{}) Action {
|
||||
// Make sure f is a function.
|
||||
fv := reflect.ValueOf(f)
|
||||
fk := fv.Kind()
|
||||
|
||||
if fk != reflect.Func {
|
||||
desc := "<nil>"
|
||||
if fk != reflect.Invalid {
|
||||
desc = fv.Type().String()
|
||||
}
|
||||
|
||||
panic(fmt.Sprintf("Invoke: expected function, got %s", desc))
|
||||
}
|
||||
|
||||
return &invokeAction{fv}
|
||||
}
|
||||
|
||||
type invokeAction struct {
|
||||
f reflect.Value
|
||||
}
|
||||
|
||||
func (a *invokeAction) SetSignature(signature reflect.Type) error {
|
||||
// The signature must match exactly.
|
||||
ft := a.f.Type()
|
||||
if ft != signature {
|
||||
return errors.New(fmt.Sprintf("Invoke: expected %v, got %v", signature, ft))
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (a *invokeAction) Invoke(vals []interface{}) []interface{} {
|
||||
// Create a slice of args for the function.
|
||||
in := make([]reflect.Value, len(vals))
|
||||
for i, x := range vals {
|
||||
in[i] = reflect.ValueOf(x)
|
||||
}
|
||||
|
||||
// Call the function and return its return values.
|
||||
out := a.f.Call(in)
|
||||
result := make([]interface{}, len(out))
|
||||
for i, v := range out {
|
||||
result[i] = v.Interface()
|
||||
}
|
||||
|
||||
return result
|
||||
}
|
||||
Generated
Vendored
-30
@@ -1,30 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglemock
|
||||
|
||||
// MockObject is an interface that mock object implementations must conform to
|
||||
// in order to register expectations with and hand off calls to a
|
||||
// MockController. Users should not interact with this interface directly.
|
||||
type MockObject interface {
|
||||
// Oglemock_Id returns an identifier for the mock object that is guaranteed
|
||||
// to be unique within the process at least until the mock object is garbage
|
||||
// collected.
|
||||
Oglemock_Id() uintptr
|
||||
|
||||
// Oglemock_Description returns a description of the mock object that may be
|
||||
// helpful in test failure messages.
|
||||
Oglemock_Description() string
|
||||
}
|
||||
Godeps/_workspace/src/github.com/smartystreets/goconvey/convey/assertions/oglemock/oglemock.goconvey
Generated
Vendored
-2
@@ -1,2 +0,0 @@
|
||||
#ignore
|
||||
-timeout=1s
|
||||
Generated
Vendored
-251
@@ -1,251 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglemock
|
||||
|
||||
import (
|
||||
"errors"
|
||||
"fmt"
|
||||
"math"
|
||||
"reflect"
|
||||
)
|
||||
|
||||
var intType = reflect.TypeOf(int(0))
|
||||
var float64Type = reflect.TypeOf(float64(0))
|
||||
var complex128Type = reflect.TypeOf(complex128(0))
|
||||
|
||||
// Return creates an Action that returns the values passed to Return as
|
||||
// arguments, after suitable legal type conversions. The following rules apply.
|
||||
// Given an argument x to Return and a corresponding type T in the method's
|
||||
// signature, at least one of the following must hold:
|
||||
//
|
||||
// * x is assignable to T. (See "Assignability" in the language spec.) Note
|
||||
// that this in particular applies that x may be a type that implements an
|
||||
// interface T. It also implies that the nil literal can be used if T is a
|
||||
// pointer, function, interface, slice, channel, or map type.
|
||||
//
|
||||
// * T is any numeric type, and x is an int that is in-range for that type.
|
||||
// This facilities using raw integer constants: Return(17).
|
||||
//
|
||||
// * T is a floating-point or complex number type, and x is a float64. This
|
||||
// facilities using raw floating-point constants: Return(17.5).
|
||||
//
|
||||
// * T is a complex number type, and x is a complex128. This facilities using
|
||||
// raw complex constants: Return(17+2i).
|
||||
//
|
||||
func Return(vals ...interface{}) Action {
|
||||
return &returnAction{vals, nil}
|
||||
}
|
||||
|
||||
type returnAction struct {
|
||||
returnVals []interface{}
|
||||
signature reflect.Type
|
||||
}
|
||||
|
||||
func (a *returnAction) Invoke(vals []interface{}) []interface{} {
|
||||
if a.signature == nil {
|
||||
panic("You must first call SetSignature with a valid signature.")
|
||||
}
|
||||
|
||||
res, err := a.buildInvokeResult(a.signature)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
|
||||
return res
|
||||
}
|
||||
|
||||
func (a *returnAction) SetSignature(signature reflect.Type) error {
|
||||
if _, err := a.buildInvokeResult(signature); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
a.signature = signature
|
||||
return nil
|
||||
}
|
||||
|
||||
// A version of Invoke that does error checking, used by both public methods.
|
||||
func (a *returnAction) buildInvokeResult(
|
||||
sig reflect.Type) (res []interface{}, err error) {
|
||||
// Check the length of the return value.
|
||||
numOut := sig.NumOut()
|
||||
numVals := len(a.returnVals)
|
||||
|
||||
if numOut != numVals {
|
||||
err = errors.New(
|
||||
fmt.Sprintf("Return given %d vals; expected %d.", numVals, numOut))
|
||||
return
|
||||
}
|
||||
|
||||
// Attempt to coerce each return value.
|
||||
res = make([]interface{}, numOut)
|
||||
|
||||
for i, val := range a.returnVals {
|
||||
resType := sig.Out(i)
|
||||
res[i], err = a.coerce(val, resType)
|
||||
|
||||
if err != nil {
|
||||
res = nil
|
||||
err = errors.New(fmt.Sprintf("Return: arg %d: %v", i, err))
|
||||
return
|
||||
}
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (a *returnAction) coerce(x interface{}, t reflect.Type) (interface{}, error) {
|
||||
xv := reflect.ValueOf(x)
|
||||
rv := reflect.New(t).Elem()
|
||||
|
||||
// Special case: the language spec says that the predeclared identifier nil
|
||||
// is assignable to pointers, functions, interface, slices, channels, and map
|
||||
// types. However, reflect.ValueOf(nil) returns an invalid value that will
|
||||
// not cooperate below. So handle invalid values here, assuming that they
|
||||
// resulted from Return(nil).
|
||||
if !xv.IsValid() {
|
||||
switch t.Kind() {
|
||||
case reflect.Ptr, reflect.Func, reflect.Interface, reflect.Chan, reflect.Slice, reflect.Map, reflect.UnsafePointer:
|
||||
return rv.Interface(), nil
|
||||
}
|
||||
|
||||
return nil, errors.New(fmt.Sprintf("expected %v, given <nil>", t))
|
||||
}
|
||||
|
||||
// If x is assignable to type t, let the reflect package do the heavy
|
||||
// lifting.
|
||||
if reflect.TypeOf(x).AssignableTo(t) {
|
||||
rv.Set(xv)
|
||||
return rv.Interface(), nil
|
||||
}
|
||||
|
||||
// Handle numeric types as described in the documentation on Return.
|
||||
switch {
|
||||
case xv.Type() == intType && a.isNumeric(t):
|
||||
return a.coerceInt(xv.Int(), t)
|
||||
|
||||
case xv.Type() == float64Type && (a.isFloatingPoint(t) || a.isComplex(t)):
|
||||
return a.coerceFloat(xv.Float(), t)
|
||||
|
||||
case xv.Type() == complex128Type && a.isComplex(t):
|
||||
return a.coerceComplex(xv.Complex(), t)
|
||||
}
|
||||
|
||||
// The value wasn't of a legal type.
|
||||
return nil, errors.New(fmt.Sprintf("expected %v, given %v", t, xv.Type()))
|
||||
}
|
||||
|
||||
func (a *returnAction) isNumeric(t reflect.Type) bool {
|
||||
return (t.Kind() >= reflect.Int && t.Kind() <= reflect.Uint64) ||
|
||||
a.isFloatingPoint(t) ||
|
||||
a.isComplex(t)
|
||||
}
|
||||
|
||||
func (a *returnAction) isFloatingPoint(t reflect.Type) bool {
|
||||
return t.Kind() == reflect.Float32 || t.Kind() == reflect.Float64
|
||||
}
|
||||
|
||||
func (a *returnAction) isComplex(t reflect.Type) bool {
|
||||
return t.Kind() == reflect.Complex64 || t.Kind() == reflect.Complex128
|
||||
}
|
||||
|
||||
func (a *returnAction) coerceInt(x int64, t reflect.Type) (interface{}, error) {
|
||||
k := t.Kind()
|
||||
|
||||
// Floating point and complex numbers: promote appropriately.
|
||||
if a.isFloatingPoint(t) || a.isComplex(t) {
|
||||
return a.coerceFloat(float64(x), t)
|
||||
}
|
||||
|
||||
// Integers: range check.
|
||||
var min, max int64
|
||||
unsigned := false
|
||||
|
||||
switch k {
|
||||
case reflect.Int8:
|
||||
min = math.MinInt8
|
||||
max = math.MaxInt8
|
||||
|
||||
case reflect.Int16:
|
||||
min = math.MinInt16
|
||||
max = math.MaxInt16
|
||||
|
||||
case reflect.Int32:
|
||||
min = math.MinInt32
|
||||
max = math.MaxInt32
|
||||
|
||||
case reflect.Int64:
|
||||
min = math.MinInt64
|
||||
max = math.MaxInt64
|
||||
|
||||
case reflect.Uint:
|
||||
unsigned = true
|
||||
min = 0
|
||||
max = math.MaxUint32
|
||||
|
||||
case reflect.Uint8:
|
||||
unsigned = true
|
||||
min = 0
|
||||
max = math.MaxUint8
|
||||
|
||||
case reflect.Uint16:
|
||||
unsigned = true
|
||||
min = 0
|
||||
max = math.MaxUint16
|
||||
|
||||
case reflect.Uint32:
|
||||
unsigned = true
|
||||
min = 0
|
||||
max = math.MaxUint32
|
||||
|
||||
case reflect.Uint64:
|
||||
unsigned = true
|
||||
min = 0
|
||||
max = math.MaxInt64
|
||||
|
||||
default:
|
||||
panic(fmt.Sprintf("Unexpected type: %v", t))
|
||||
}
|
||||
|
||||
if x < min || x > max {
|
||||
return nil, errors.New("int value out of range")
|
||||
}
|
||||
|
||||
rv := reflect.New(t).Elem()
|
||||
if unsigned {
|
||||
rv.SetUint(uint64(x))
|
||||
} else {
|
||||
rv.SetInt(x)
|
||||
}
|
||||
|
||||
return rv.Interface(), nil
|
||||
}
|
||||
|
||||
func (a *returnAction) coerceFloat(x float64, t reflect.Type) (interface{}, error) {
|
||||
// Promote complex numbers.
|
||||
if a.isComplex(t) {
|
||||
return a.coerceComplex(complex(x, 0), t)
|
||||
}
|
||||
|
||||
rv := reflect.New(t).Elem()
|
||||
rv.SetFloat(x)
|
||||
return rv.Interface(), nil
|
||||
}
|
||||
|
||||
func (a *returnAction) coerceComplex(x complex128, t reflect.Type) (interface{}, error) {
|
||||
rv := reflect.New(t).Elem()
|
||||
rv.SetComplex(x)
|
||||
return rv.Interface(), nil
|
||||
}
|
||||
Generated
Vendored
-6
@@ -1,6 +0,0 @@
|
||||
This directory contains sample code generated with the `createmock` command. For
|
||||
example, the file `mock_io.go` can be regenerated with:
|
||||
|
||||
createmock io Reader > sample/mock_io/mock_io.go
|
||||
|
||||
The files are also used by `integration_test.go`.
|
||||
Generated
Vendored
-72
@@ -1,72 +0,0 @@
|
||||
// This file was auto-generated using createmock. See the following page for
|
||||
// more information:
|
||||
//
|
||||
// https://github.com/smartystreets/goconvey/convey/assertions/oglemock
|
||||
//
|
||||
|
||||
package mock_io
|
||||
|
||||
import (
|
||||
fmt "fmt"
|
||||
io "io"
|
||||
runtime "runtime"
|
||||
unsafe "unsafe"
|
||||
|
||||
oglemock "github.com/smartystreets/goconvey/convey/assertions/oglemock"
|
||||
)
|
||||
|
||||
type MockReader interface {
|
||||
io.Reader
|
||||
oglemock.MockObject
|
||||
}
|
||||
|
||||
type mockReader struct {
|
||||
controller oglemock.Controller
|
||||
description string
|
||||
}
|
||||
|
||||
func NewMockReader(
|
||||
c oglemock.Controller,
|
||||
desc string) MockReader {
|
||||
return &mockReader{
|
||||
controller: c,
|
||||
description: desc,
|
||||
}
|
||||
}
|
||||
|
||||
func (m *mockReader) Oglemock_Id() uintptr {
|
||||
return uintptr(unsafe.Pointer(m))
|
||||
}
|
||||
|
||||
func (m *mockReader) Oglemock_Description() string {
|
||||
return m.description
|
||||
}
|
||||
|
||||
func (m *mockReader) Read(p0 []uint8) (o0 int, o1 error) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Read",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0})
|
||||
|
||||
if len(retVals) != 2 {
|
||||
panic(fmt.Sprintf("mockReader.Read: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 int
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(int)
|
||||
}
|
||||
|
||||
// o1 error
|
||||
if retVals[1] != nil {
|
||||
o1 = retVals[1].(error)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
Generated
-5
@@ -1,5 +0,0 @@
|
||||
*.6
|
||||
6.out
|
||||
_obj/
|
||||
_test/
|
||||
_testmain.go
|
||||
Generated
Vendored
-202
@@ -1,202 +0,0 @@
|
||||
|
||||
Apache License
|
||||
Version 2.0, January 2004
|
||||
http://www.apache.org/licenses/
|
||||
|
||||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||
|
||||
1. Definitions.
|
||||
|
||||
"License" shall mean the terms and conditions for use, reproduction,
|
||||
and distribution as defined by Sections 1 through 9 of this document.
|
||||
|
||||
"Licensor" shall mean the copyright owner or entity authorized by
|
||||
the copyright owner that is granting the License.
|
||||
|
||||
"Legal Entity" shall mean the union of the acting entity and all
|
||||
other entities that control, are controlled by, or are under common
|
||||
control with that entity. For the purposes of this definition,
|
||||
"control" means (i) the power, direct or indirect, to cause the
|
||||
direction or management of such entity, whether by contract or
|
||||
otherwise, or (ii) ownership of fifty percent (50%) or more of the
|
||||
outstanding shares, or (iii) beneficial ownership of such entity.
|
||||
|
||||
"You" (or "Your") shall mean an individual or Legal Entity
|
||||
exercising permissions granted by this License.
|
||||
|
||||
"Source" form shall mean the preferred form for making modifications,
|
||||
including but not limited to software source code, documentation
|
||||
source, and configuration files.
|
||||
|
||||
"Object" form shall mean any form resulting from mechanical
|
||||
transformation or translation of a Source form, including but
|
||||
not limited to compiled object code, generated documentation,
|
||||
and conversions to other media types.
|
||||
|
||||
"Work" shall mean the work of authorship, whether in Source or
|
||||
Object form, made available under the License, as indicated by a
|
||||
copyright notice that is included in or attached to the work
|
||||
(an example is provided in the Appendix below).
|
||||
|
||||
"Derivative Works" shall mean any work, whether in Source or Object
|
||||
form, that is based on (or derived from) the Work and for which the
|
||||
editorial revisions, annotations, elaborations, or other modifications
|
||||
represent, as a whole, an original work of authorship. For the purposes
|
||||
of this License, Derivative Works shall not include works that remain
|
||||
separable from, or merely link (or bind by name) to the interfaces of,
|
||||
the Work and Derivative Works thereof.
|
||||
|
||||
"Contribution" shall mean any work of authorship, including
|
||||
the original version of the Work and any modifications or additions
|
||||
to that Work or Derivative Works thereof, that is intentionally
|
||||
submitted to Licensor for inclusion in the Work by the copyright owner
|
||||
or by an individual or Legal Entity authorized to submit on behalf of
|
||||
the copyright owner. For the purposes of this definition, "submitted"
|
||||
means any form of electronic, verbal, or written communication sent
|
||||
to the Licensor or its representatives, including but not limited to
|
||||
communication on electronic mailing lists, source code control systems,
|
||||
and issue tracking systems that are managed by, or on behalf of, the
|
||||
Licensor for the purpose of discussing and improving the Work, but
|
||||
excluding communication that is conspicuously marked or otherwise
|
||||
designated in writing by the copyright owner as "Not a Contribution."
|
||||
|
||||
"Contributor" shall mean Licensor and any individual or Legal Entity
|
||||
on behalf of whom a Contribution has been received by Licensor and
|
||||
subsequently incorporated within the Work.
|
||||
|
||||
2. Grant of Copyright License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
copyright license to reproduce, prepare Derivative Works of,
|
||||
publicly display, publicly perform, sublicense, and distribute the
|
||||
Work and such Derivative Works in Source or Object form.
|
||||
|
||||
3. Grant of Patent License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
(except as stated in this section) patent license to make, have made,
|
||||
use, offer to sell, sell, import, and otherwise transfer the Work,
|
||||
where such license applies only to those patent claims licensable
|
||||
by such Contributor that are necessarily infringed by their
|
||||
Contribution(s) alone or by combination of their Contribution(s)
|
||||
with the Work to which such Contribution(s) was submitted. If You
|
||||
institute patent litigation against any entity (including a
|
||||
cross-claim or counterclaim in a lawsuit) alleging that the Work
|
||||
or a Contribution incorporated within the Work constitutes direct
|
||||
or contributory patent infringement, then any patent licenses
|
||||
granted to You under this License for that Work shall terminate
|
||||
as of the date such litigation is filed.
|
||||
|
||||
4. Redistribution. You may reproduce and distribute copies of the
|
||||
Work or Derivative Works thereof in any medium, with or without
|
||||
modifications, and in Source or Object form, provided that You
|
||||
meet the following conditions:
|
||||
|
||||
(a) You must give any other recipients of the Work or
|
||||
Derivative Works a copy of this License; and
|
||||
|
||||
(b) You must cause any modified files to carry prominent notices
|
||||
stating that You changed the files; and
|
||||
|
||||
(c) You must retain, in the Source form of any Derivative Works
|
||||
that You distribute, all copyright, patent, trademark, and
|
||||
attribution notices from the Source form of the Work,
|
||||
excluding those notices that do not pertain to any part of
|
||||
the Derivative Works; and
|
||||
|
||||
(d) If the Work includes a "NOTICE" text file as part of its
|
||||
distribution, then any Derivative Works that You distribute must
|
||||
include a readable copy of the attribution notices contained
|
||||
within such NOTICE file, excluding those notices that do not
|
||||
pertain to any part of the Derivative Works, in at least one
|
||||
of the following places: within a NOTICE text file distributed
|
||||
as part of the Derivative Works; within the Source form or
|
||||
documentation, if provided along with the Derivative Works; or,
|
||||
within a display generated by the Derivative Works, if and
|
||||
wherever such third-party notices normally appear. The contents
|
||||
of the NOTICE file are for informational purposes only and
|
||||
do not modify the License. You may add Your own attribution
|
||||
notices within Derivative Works that You distribute, alongside
|
||||
or as an addendum to the NOTICE text from the Work, provided
|
||||
that such additional attribution notices cannot be construed
|
||||
as modifying the License.
|
||||
|
||||
You may add Your own copyright statement to Your modifications and
|
||||
may provide additional or different license terms and conditions
|
||||
for use, reproduction, or distribution of Your modifications, or
|
||||
for any such Derivative Works as a whole, provided Your use,
|
||||
reproduction, and distribution of the Work otherwise complies with
|
||||
the conditions stated in this License.
|
||||
|
||||
5. Submission of Contributions. Unless You explicitly state otherwise,
|
||||
any Contribution intentionally submitted for inclusion in the Work
|
||||
by You to the Licensor shall be under the terms and conditions of
|
||||
this License, without any additional terms or conditions.
|
||||
Notwithstanding the above, nothing herein shall supersede or modify
|
||||
the terms of any separate license agreement you may have executed
|
||||
with Licensor regarding such Contributions.
|
||||
|
||||
6. Trademarks. This License does not grant permission to use the trade
|
||||
names, trademarks, service marks, or product names of the Licensor,
|
||||
except as required for reasonable and customary use in describing the
|
||||
origin of the Work and reproducing the content of the NOTICE file.
|
||||
|
||||
7. Disclaimer of Warranty. Unless required by applicable law or
|
||||
agreed to in writing, Licensor provides the Work (and each
|
||||
Contributor provides its Contributions) on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
implied, including, without limitation, any warranties or conditions
|
||||
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
|
||||
PARTICULAR PURPOSE. You are solely responsible for determining the
|
||||
appropriateness of using or redistributing the Work and assume any
|
||||
risks associated with Your exercise of permissions under this License.
|
||||
|
||||
8. Limitation of Liability. In no event and under no legal theory,
|
||||
whether in tort (including negligence), contract, or otherwise,
|
||||
unless required by applicable law (such as deliberate and grossly
|
||||
negligent acts) or agreed to in writing, shall any Contributor be
|
||||
liable to You for damages, including any direct, indirect, special,
|
||||
incidental, or consequential damages of any character arising as a
|
||||
result of this License or out of the use or inability to use the
|
||||
Work (including but not limited to damages for loss of goodwill,
|
||||
work stoppage, computer failure or malfunction, or any and all
|
||||
other commercial damages or losses), even if such Contributor
|
||||
has been advised of the possibility of such damages.
|
||||
|
||||
9. Accepting Warranty or Additional Liability. While redistributing
|
||||
the Work or Derivative Works thereof, You may choose to offer,
|
||||
and charge a fee for, acceptance of support, warranty, indemnity,
|
||||
or other liability obligations and/or rights consistent with this
|
||||
License. However, in accepting such obligations, You may act only
|
||||
on Your own behalf and on Your sole responsibility, not on behalf
|
||||
of any other Contributor, and only if You agree to indemnify,
|
||||
defend, and hold each Contributor harmless for any liability
|
||||
incurred by, or claims asserted against, such Contributor by reason
|
||||
of your accepting any such warranty or additional liability.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
|
||||
APPENDIX: How to apply the Apache License to your work.
|
||||
|
||||
To apply the Apache License to your work, attach the following
|
||||
boilerplate notice, with the fields enclosed by brackets "[]"
|
||||
replaced with your own identifying information. (Don't include
|
||||
the brackets!) The text should be enclosed in the appropriate
|
||||
comment syntax for the file format. We also recommend that a
|
||||
file or class name and description of purpose be included on the
|
||||
same "printed page" as the copyright notice for easier
|
||||
identification within third-party archives.
|
||||
|
||||
Copyright [yyyy] [name of copyright owner]
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
Generated
Vendored
-149
@@ -1,149 +0,0 @@
|
||||
`ogletest` is a unit testing framework for Go with the following features:
|
||||
|
||||
* An extensive and extensible set of matchers for expressing expectations.
|
||||
* Automatic failure messages; no need to say `t.Errorf("Expected %v, got
|
||||
%v"...)`.
|
||||
* Clean, readable output that tells you exactly what you need to know.
|
||||
* Built-in support for mocking through the [oglemock][] package.
|
||||
* Style and semantics similar to [Google Test][googletest] and
|
||||
[Google JS Test][google-js-test].
|
||||
|
||||
It integrates with Go's built-in `testing` package, so it works with the
|
||||
`go test` command, and even with other types of test within your package. Unlike
|
||||
the `testing` package which offers only basic capabilities for signalling
|
||||
failures, it offers ways to express expectations and get nice failure messages
|
||||
automatically.
|
||||
|
||||
|
||||
Installation
|
||||
------------
|
||||
|
||||
First, make sure you have installed Go 1.0.2 or newer. See
|
||||
[here][golang-install] for instructions.
|
||||
|
||||
Use the following command to install `ogletest` and its dependencies, and to
|
||||
keep them up to date:
|
||||
|
||||
go get -u github.com/smartystreets/goconvey/convey/assertions/ogletest
|
||||
|
||||
|
||||
Documentation
|
||||
-------------
|
||||
|
||||
See [here][reference] for package documentation hosted on GoPkgDoc containing an
|
||||
exhaustive list of exported symbols. Alternatively, you can install the package
|
||||
and then use `go doc`:
|
||||
|
||||
go doc github.com/smartystreets/goconvey/convey/assertions/ogletest
|
||||
|
||||
An important part of `ogletest` is its use of matchers provided by the
|
||||
[oglematchers][matcher-reference] package. See that package's documentation
|
||||
for information on the built-in matchers available, and check out the
|
||||
`oglematchers.Matcher` interface if you want to define your own.
|
||||
|
||||
|
||||
Example
|
||||
-------
|
||||
|
||||
Let's say you have a function in your package `people` with the following
|
||||
signature:
|
||||
|
||||
```go
|
||||
// GetRandomPerson returns the name and phone number of Tony, Dennis, or Scott.
|
||||
func GetRandomPerson() (name, phone string) {
|
||||
[...]
|
||||
}
|
||||
```
|
||||
|
||||
A silly function, but it will do for an example. You can write a couple of tests
|
||||
for it as follows:
|
||||
|
||||
```go
|
||||
package people
|
||||
|
||||
import (
|
||||
"github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
"github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
"testing"
|
||||
)
|
||||
|
||||
// Give ogletest a chance to run your tests when invoked by 'go test'.
|
||||
func TestOgletest(t *testing.T) { ogletest.RunTests(t) }
|
||||
|
||||
// Create a test suite, which groups together logically related test methods
|
||||
// (defined below). You can share common setup and teardown code here; see the
|
||||
// package docs for more info.
|
||||
type PeopleTest struct {}
|
||||
func init() { ogletest.RegisterTestSuite(&PeopleTest{}) }
|
||||
|
||||
func (t *PeopleTest) ReturnsCorrectNames() {
|
||||
// Call the function a few times, and make sure it never strays from the set
|
||||
// of expected names.
|
||||
for i := 0; i < 25; i++ {
|
||||
name, _ := GetRandomPerson()
|
||||
ogletest.ExpectThat(name, oglematchers.AnyOf("Tony", "Dennis", "Scott"))
|
||||
}
|
||||
}
|
||||
|
||||
func (t *PeopleTest) FormatsPhoneNumbersCorrectly() {
|
||||
// Call the function a few times, and make sure it returns phone numbers in a
|
||||
// standard US format.
|
||||
for i := 0; i < 25; i++ {
|
||||
_, phone := GetRandomPerson()
|
||||
ogletest.ExpectThat(phone, oglematchers.MatchesRegexp(`^\(\d{3}\) \d{3}-\d{4}$`))
|
||||
}
|
||||
```
|
||||
|
||||
Note that test control functions (`RunTests`, `ExpectThat`, and so on) are part
|
||||
of the `ogletest` package, whereas built-in matchers (`AnyOf`, `MatchesRegexp`,
|
||||
and more) are part of the [oglematchers][matcher-reference] library. You can of
|
||||
course use dot imports so that you don't need to prefix each function with its
|
||||
package name:
|
||||
|
||||
```go
|
||||
import (
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
```
|
||||
|
||||
If you save the test in a file whose name ends in `_test.go`, you can run your
|
||||
tests by simply invoking the following in your package directory:
|
||||
|
||||
go test
|
||||
|
||||
Here's what the failure output of ogletest looks like, if your function's
|
||||
implementation is bad.
|
||||
|
||||
[----------] Running tests from PeopleTest
|
||||
[ RUN ] PeopleTest.FormatsPhoneNumbersCorrectly
|
||||
people_test.go:32:
|
||||
Expected: matches regexp "^\(\d{3}\) \d{3}-\d{4}$"
|
||||
Actual: +1 800 555 5555
|
||||
|
||||
[ FAILED ] PeopleTest.FormatsPhoneNumbersCorrectly
|
||||
[ RUN ] PeopleTest.ReturnsCorrectNames
|
||||
people_test.go:23:
|
||||
Expected: or(Tony, Dennis, Scott)
|
||||
Actual: Bart
|
||||
|
||||
[ FAILED ] PeopleTest.ReturnsCorrectNames
|
||||
[----------] Finished with tests from PeopleTest
|
||||
|
||||
And if the test passes:
|
||||
|
||||
[----------] Running tests from PeopleTest
|
||||
[ RUN ] PeopleTest.FormatsPhoneNumbersCorrectly
|
||||
[ OK ] PeopleTest.FormatsPhoneNumbersCorrectly
|
||||
[ RUN ] PeopleTest.ReturnsCorrectNames
|
||||
[ OK ] PeopleTest.ReturnsCorrectNames
|
||||
[----------] Finished with tests from PeopleTest
|
||||
|
||||
|
||||
[reference]: http://gopkgdoc.appspot.com/pkg/github.com/smartystreets/goconvey/convey/assertions/ogletest
|
||||
[matcher-reference]: http://gopkgdoc.appspot.com/pkg/github.com/smartystreets/goconvey/convey/assertions/oglematchers
|
||||
[golang-install]: http://golang.org/doc/install.html
|
||||
[googletest]: http://code.google.com/p/googletest/
|
||||
[google-js-test]: http://code.google.com/p/google-js-test/
|
||||
[howtowrite]: http://golang.org/doc/code.html
|
||||
[oglemock]: https://github.com/smartystreets/goconvey/convey/assertions/oglemock
|
||||
Godeps/_workspace/src/github.com/smartystreets/goconvey/convey/assertions/ogletest/assert_aliases.go
Generated
Vendored
-124
@@ -1,124 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package ogletest
|
||||
|
||||
import (
|
||||
"github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
)
|
||||
|
||||
// AssertEq(e, a) is equivalent to AssertThat(a, oglematchers.Equals(e)).
|
||||
func AssertEq(expected, actual interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(actual, oglematchers.Equals(expected), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
|
||||
matcherErr := res.MatchResult()
|
||||
if matcherErr != nil {
|
||||
panic(&assertThatError{})
|
||||
}
|
||||
|
||||
return res
|
||||
}
|
||||
|
||||
// AssertNe(e, a) is equivalent to AssertThat(a, oglematchers.Not(oglematchers.Equals(e))).
|
||||
func AssertNe(expected, actual interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(actual, oglematchers.Not(oglematchers.Equals(expected)), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
|
||||
matcherErr := res.MatchResult()
|
||||
if matcherErr != nil {
|
||||
panic(&assertThatError{})
|
||||
}
|
||||
|
||||
return res
|
||||
}
|
||||
|
||||
// AssertLt(x, y) is equivalent to AssertThat(x, oglematchers.LessThan(y)).
|
||||
func AssertLt(x, y interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(x, oglematchers.LessThan(y), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
|
||||
matcherErr := res.MatchResult()
|
||||
if matcherErr != nil {
|
||||
panic(&assertThatError{})
|
||||
}
|
||||
|
||||
return res
|
||||
}
|
||||
|
||||
// AssertLe(x, y) is equivalent to AssertThat(x, oglematchers.LessOrEqual(y)).
|
||||
func AssertLe(x, y interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(x, oglematchers.LessOrEqual(y), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
|
||||
matcherErr := res.MatchResult()
|
||||
if matcherErr != nil {
|
||||
panic(&assertThatError{})
|
||||
}
|
||||
|
||||
return res
|
||||
}
|
||||
|
||||
// AssertGt(x, y) is equivalent to AssertThat(x, oglematchers.GreaterThan(y)).
|
||||
func AssertGt(x, y interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(x, oglematchers.GreaterThan(y), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
|
||||
matcherErr := res.MatchResult()
|
||||
if matcherErr != nil {
|
||||
panic(&assertThatError{})
|
||||
}
|
||||
|
||||
return res
|
||||
}
|
||||
|
||||
// AssertGe(x, y) is equivalent to AssertThat(x, oglematchers.GreaterOrEqual(y)).
|
||||
func AssertGe(x, y interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(x, oglematchers.GreaterOrEqual(y), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
|
||||
matcherErr := res.MatchResult()
|
||||
if matcherErr != nil {
|
||||
panic(&assertThatError{})
|
||||
}
|
||||
|
||||
return res
|
||||
}
|
||||
|
||||
// AssertTrue(b) is equivalent to AssertThat(b, oglematchers.Equals(true)).
|
||||
func AssertTrue(b interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(b, oglematchers.Equals(true), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
|
||||
matcherErr := res.MatchResult()
|
||||
if matcherErr != nil {
|
||||
panic(&assertThatError{})
|
||||
}
|
||||
|
||||
return res
|
||||
}
|
||||
|
||||
// AssertFalse(b) is equivalent to AssertThat(b, oglematchers.Equals(false)).
|
||||
func AssertFalse(b interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(b, oglematchers.Equals(false), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
|
||||
matcherErr := res.MatchResult()
|
||||
if matcherErr != nil {
|
||||
panic(&assertThatError{})
|
||||
}
|
||||
|
||||
return res
|
||||
}
|
||||
Generated
Vendored
-49
@@ -1,49 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package ogletest
|
||||
|
||||
import (
|
||||
"github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
)
|
||||
|
||||
// AssertThat is identical to ExpectThat, except that in the event of failure
|
||||
// it halts the currently running test immediately. It is thus useful for
|
||||
// things like bounds checking:
|
||||
//
|
||||
// someSlice := [...]
|
||||
// AssertEq(1, len(someSlice)) // Protects next line from panicking.
|
||||
// ExpectEq("taco", someSlice[0])
|
||||
//
|
||||
func AssertThat(
|
||||
x interface{},
|
||||
m oglematchers.Matcher,
|
||||
errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(x, m, errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
|
||||
matcherErr := res.MatchResult()
|
||||
if matcherErr != nil {
|
||||
panic(&assertThatError{})
|
||||
}
|
||||
|
||||
return res
|
||||
}
|
||||
|
||||
// assertThatError is a sentinel type that is used in a conspiracy between
|
||||
// AssertThat and runTests. If runTests sees a *assertThatError as the value
|
||||
// given to a panic() call, it will avoid printing the panic error.
|
||||
type assertThatError struct {
|
||||
}
|
||||
Generated
Vendored
-51
@@ -1,51 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
// Package ogletest provides a framework for writing expressive unit tests. It
|
||||
// integrates with the builtin testing package, so it works with the gotest
|
||||
// command. Unlike the testing package which offers only basic capabilities for
|
||||
// signalling failures, it offers ways to express expectations and get nice
|
||||
// failure messages automatically.
|
||||
//
|
||||
// For example:
|
||||
//
|
||||
// ////////////////////////////////////////////////////////////////////////
|
||||
// // testing package test
|
||||
// ////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// someStr, err := ComputeSomeString()
|
||||
// if err != nil {
|
||||
// t.Errorf("ComputeSomeString: expected nil error, got %v", err)
|
||||
// }
|
||||
//
|
||||
// !strings.Contains(someStr, "foo") {
|
||||
// t.Errorf("ComputeSomeString: expected substring foo, got %v", someStr)
|
||||
// }
|
||||
//
|
||||
// ////////////////////////////////////////////////////////////////////////
|
||||
// // ogletest test
|
||||
// ////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// someStr, err := ComputeSomeString()
|
||||
// ExpectEq(nil, err)
|
||||
// ExpectThat(someStr, HasSubstr("foo")
|
||||
//
|
||||
// Failure messages require no work from the user, and look like the following:
|
||||
//
|
||||
// foo_test.go:103:
|
||||
// Expected: has substring "foo"
|
||||
// Actual: "bar baz"
|
||||
//
|
||||
package ogletest
|
||||
Godeps/_workspace/src/github.com/smartystreets/goconvey/convey/assertions/ogletest/expect_aliases.go
Generated
Vendored
-85
@@ -1,85 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package ogletest
|
||||
|
||||
import (
|
||||
"path"
|
||||
"runtime"
|
||||
|
||||
"github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
)
|
||||
|
||||
func getCallerForAlias() (fileName string, lineNumber int) {
|
||||
_, fileName, lineNumber, _ = runtime.Caller(2)
|
||||
fileName = path.Base(fileName)
|
||||
return
|
||||
}
|
||||
|
||||
// ExpectEq(e, a) is equivalent to ExpectThat(a, oglematchers.Equals(e)).
|
||||
func ExpectEq(expected, actual interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(actual, oglematchers.Equals(expected), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
return res
|
||||
}
|
||||
|
||||
// ExpectNe(e, a) is equivalent to ExpectThat(a, oglematchers.Not(oglematchers.Equals(e))).
|
||||
func ExpectNe(expected, actual interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(actual, oglematchers.Not(oglematchers.Equals(expected)), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
return res
|
||||
}
|
||||
|
||||
// ExpectLt(x, y) is equivalent to ExpectThat(x, oglematchers.LessThan(y)).
|
||||
func ExpectLt(x, y interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(x, oglematchers.LessThan(y), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
return res
|
||||
}
|
||||
|
||||
// ExpectLe(x, y) is equivalent to ExpectThat(x, oglematchers.LessOrEqual(y)).
|
||||
func ExpectLe(x, y interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(x, oglematchers.LessOrEqual(y), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
return res
|
||||
}
|
||||
|
||||
// ExpectGt(x, y) is equivalent to ExpectThat(x, oglematchers.GreaterThan(y)).
|
||||
func ExpectGt(x, y interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(x, oglematchers.GreaterThan(y), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
return res
|
||||
}
|
||||
|
||||
// ExpectGe(x, y) is equivalent to ExpectThat(x, oglematchers.GreaterOrEqual(y)).
|
||||
func ExpectGe(x, y interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(x, oglematchers.GreaterOrEqual(y), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
return res
|
||||
}
|
||||
|
||||
// ExpectTrue(b) is equivalent to ExpectThat(b, oglematchers.Equals(true)).
|
||||
func ExpectTrue(b interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(b, oglematchers.Equals(true), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
return res
|
||||
}
|
||||
|
||||
// ExpectFalse(b) is equivalent to ExpectThat(b, oglematchers.Equals(false)).
|
||||
func ExpectFalse(b interface{}, errorParts ...interface{}) ExpectationResult {
|
||||
res := ExpectThat(b, oglematchers.Equals(false), errorParts...)
|
||||
res.SetCaller(getCallerForAlias())
|
||||
return res
|
||||
}
|
||||
Generated
Vendored
-60
@@ -1,60 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package ogletest
|
||||
|
||||
import (
|
||||
"runtime"
|
||||
|
||||
"github.com/smartystreets/goconvey/convey/assertions/oglemock"
|
||||
)
|
||||
|
||||
// ExpectCall expresses an expectation that the method of the given name
|
||||
// should be called on the supplied mock object. It returns a function that
|
||||
// should be called with the expected arguments, matchers for the arguments,
|
||||
// or a mix of both.
|
||||
//
|
||||
// For example:
|
||||
//
|
||||
// mockWriter := [...]
|
||||
// ogletest.ExpectCall(mockWriter, "Write")(oglematchers.ElementsAre(0x1))
|
||||
// .WillOnce(oglemock.Return(1, nil))
|
||||
//
|
||||
// This is a shortcut for calling i.MockController.ExpectCall, where i is the
|
||||
// TestInfo struct for the currently-running test. Unlike that direct approach,
|
||||
// this function automatically sets the correct file name and line number for
|
||||
// the expectation.
|
||||
func ExpectCall(o oglemock.MockObject, method string) oglemock.PartialExpecation {
|
||||
// Get information about the call site.
|
||||
_, file, lineNumber, ok := runtime.Caller(1)
|
||||
if !ok {
|
||||
panic("ExpectCall: runtime.Caller")
|
||||
}
|
||||
|
||||
// Grab the current test info.
|
||||
info := currentlyRunningTest
|
||||
if info == nil {
|
||||
panic("ExpectCall: no test info.")
|
||||
}
|
||||
|
||||
// Grab the mock controller.
|
||||
controller := currentlyRunningTest.MockController
|
||||
if controller == nil {
|
||||
panic("ExpectCall: no mock controller.")
|
||||
}
|
||||
|
||||
// Report the expectation.
|
||||
return controller.ExpectCall(o, method, file, lineNumber)
|
||||
}
|
||||
Generated
Vendored
-141
@@ -1,141 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package ogletest
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"path"
|
||||
"reflect"
|
||||
"runtime"
|
||||
|
||||
"github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
)
|
||||
|
||||
// ExpectationResult is an interface returned by ExpectThat that allows callers
|
||||
// to get information about the result of the expectation and set their own
|
||||
// custom information. This is not useful to the average consumer, but may be
|
||||
// helpful if you're writing widely used test utility functions.
|
||||
type ExpectationResult interface {
|
||||
// SetCaller updates the file name and line number associated with the
|
||||
// expectation. This allows, for example, a utility function to express that
|
||||
// *its* caller should have its line number printed if the expectation fails,
|
||||
// instead of the line number of the ExpectThat call within the utility
|
||||
// function.
|
||||
SetCaller(fileName string, lineNumber int)
|
||||
|
||||
// MatchResult returns the result returned by the expectation's matcher for
|
||||
// the supplied candidate.
|
||||
MatchResult() error
|
||||
}
|
||||
|
||||
// ExpectThat confirms that the supplied matcher matches the value x, adding a
|
||||
// failure record to the currently running test if it does not. If additional
|
||||
// parameters are supplied, the first will be used as a format string for the
|
||||
// later ones, and the user-supplied error message will be added to the test
|
||||
// output in the event of a failure.
|
||||
//
|
||||
// For example:
|
||||
//
|
||||
// ExpectThat(userName, Equals("jacobsa"))
|
||||
// ExpectThat(users[i], Equals("jacobsa"), "while processing user %d", i)
|
||||
//
|
||||
func ExpectThat(
|
||||
x interface{},
|
||||
m oglematchers.Matcher,
|
||||
errorParts ...interface{}) ExpectationResult {
|
||||
res := &expectationResultImpl{}
|
||||
|
||||
// Get information about the call site.
|
||||
_, file, lineNumber, ok := runtime.Caller(1)
|
||||
if !ok {
|
||||
panic("ExpectThat: runtime.Caller")
|
||||
}
|
||||
|
||||
// Assemble the user error, if any.
|
||||
userError := ""
|
||||
if len(errorParts) != 0 {
|
||||
v := reflect.ValueOf(errorParts[0])
|
||||
if v.Kind() != reflect.String {
|
||||
panic(fmt.Sprintf("ExpectThat: invalid format string type %v", v.Kind()))
|
||||
}
|
||||
|
||||
userError = fmt.Sprintf(v.String(), errorParts[1:]...)
|
||||
}
|
||||
|
||||
// Grab the current test info.
|
||||
info := currentlyRunningTest
|
||||
if info == nil {
|
||||
panic("ExpectThat: no test info.")
|
||||
}
|
||||
|
||||
// Check whether the value matches.
|
||||
matcherErr := m.Matches(x)
|
||||
res.matchError = matcherErr
|
||||
|
||||
// Return immediately on success.
|
||||
if matcherErr == nil {
|
||||
return res
|
||||
}
|
||||
|
||||
// Form an appropriate failure message. Make sure that the expected and
|
||||
// actual values align properly.
|
||||
var record failureRecord
|
||||
relativeClause := ""
|
||||
if matcherErr.Error() != "" {
|
||||
relativeClause = fmt.Sprintf(", %s", matcherErr.Error())
|
||||
}
|
||||
|
||||
record.GeneratedError = fmt.Sprintf(
|
||||
"Expected: %s\nActual: %v%s",
|
||||
m.Description(),
|
||||
x,
|
||||
relativeClause)
|
||||
|
||||
// Record additional failure info.
|
||||
record.FileName = path.Base(file)
|
||||
record.LineNumber = lineNumber
|
||||
record.UserError = userError
|
||||
|
||||
// Store the failure.
|
||||
info.mutex.Lock()
|
||||
defer info.mutex.Unlock()
|
||||
|
||||
info.failureRecords = append(info.failureRecords, &record)
|
||||
res.failureRecord = &record
|
||||
|
||||
return res
|
||||
}
|
||||
|
||||
type expectationResultImpl struct {
|
||||
// The failure record created by the expectation, or nil if none.
|
||||
failureRecord *failureRecord
|
||||
|
||||
// The result of the matcher.
|
||||
matchError error
|
||||
}
|
||||
|
||||
func (r *expectationResultImpl) SetCaller(fileName string, lineNumber int) {
|
||||
if r.failureRecord == nil {
|
||||
return
|
||||
}
|
||||
|
||||
r.failureRecord.FileName = fileName
|
||||
r.failureRecord.LineNumber = lineNumber
|
||||
}
|
||||
|
||||
func (r *expectationResultImpl) MatchResult() error {
|
||||
return r.matchError
|
||||
}
|
||||
Generated
Vendored
-65
@@ -1,65 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package ogletest
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"reflect"
|
||||
"runtime"
|
||||
"sort"
|
||||
)
|
||||
|
||||
func getLine(m reflect.Method) int {
|
||||
pc := m.Func.Pointer()
|
||||
|
||||
f := runtime.FuncForPC(pc)
|
||||
if f == nil {
|
||||
panic(fmt.Sprintf("Couldn't get runtime func for method (pc=%d): %v", pc, m))
|
||||
}
|
||||
|
||||
_, line := f.FileLine(pc)
|
||||
return line
|
||||
}
|
||||
|
||||
type sortableMethodSet []reflect.Method
|
||||
|
||||
func (s sortableMethodSet) Len() int {
|
||||
return len(s)
|
||||
}
|
||||
|
||||
func (s sortableMethodSet) Less(i, j int) bool {
|
||||
return getLine(s[i]) < getLine(s[j])
|
||||
}
|
||||
|
||||
func (s sortableMethodSet) Swap(i, j int) {
|
||||
s[i], s[j] = s[j], s[i]
|
||||
}
|
||||
|
||||
// Given a type t, return all of the methods of t sorted such that source file
|
||||
// order is preserved. Order across files is undefined. Order within lines is
|
||||
// undefined.
|
||||
func getMethodsInSourceOrder(t reflect.Type) []reflect.Method {
|
||||
// Build the list of methods.
|
||||
methods := sortableMethodSet{}
|
||||
for i := 0; i < t.NumMethod(); i++ {
|
||||
methods = append(methods, t.Method(i))
|
||||
}
|
||||
|
||||
// Sort it.
|
||||
sort.Sort(methods)
|
||||
|
||||
return methods
|
||||
}
|
||||
Godeps/_workspace/src/github.com/smartystreets/goconvey/convey/assertions/ogletest/ogletest.goconvey
Generated
Vendored
-2
@@ -1,2 +0,0 @@
|
||||
#ignore
|
||||
-timeout=1s
|
||||
Generated
Vendored
-85
@@ -1,85 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package ogletest
|
||||
|
||||
// RegisterTestSuite tells ogletest about a test suite containing tests that it
|
||||
// should run. Any exported method on the type pointed to by the supplied
|
||||
// prototype value will be treated as test methods, with the exception of the
|
||||
// following methods (which need not be present):
|
||||
//
|
||||
// * SetUpTestSuite() -- called exactly once, before the first test method is
|
||||
// run. The receiver of this method will be a zero value of the test suite
|
||||
// type, and is not shared with any other methods. Use this method to set
|
||||
// up any necessary global state shared by all of the test methods.
|
||||
//
|
||||
// * TearDownTestSuite() -- called exactly once, after the last test method
|
||||
// is run. The receiver of this method will be a zero value of the test
|
||||
// suite type, and is not shared with any other methods. Use this method to
|
||||
// clean up after any necessary global state shared by all of the test
|
||||
// methods.
|
||||
//
|
||||
// * SetUp(testInfo) -- called before each test method is invoked, with the
|
||||
// same receiver as that test method, and with a TestInfo arg. At the time
|
||||
// this method is invoked, the receiver is a zero value for the test suite
|
||||
// type. Use this method for common setup code that works on data not
|
||||
// shared across tests.
|
||||
//
|
||||
// * TearDown() -- called after each test method is invoked, with the same
|
||||
// receiver as that test method. Use this method for common cleanup code
|
||||
// that works on data not shared across tests.
|
||||
//
|
||||
// Each test method is invoked on a different receiver, which is initially a
|
||||
// zero value of the test suite type.
|
||||
//
|
||||
// Example:
|
||||
//
|
||||
// // Some value that is needed by the tests but is expensive to compute.
|
||||
// var someExpensiveThing uint
|
||||
//
|
||||
// type FooTest struct {
|
||||
// // Path to a temporary file used by the tests. Each test gets a
|
||||
// // different temporary file.
|
||||
// tempFile string
|
||||
// }
|
||||
// func init() { ogletest.RegisterTestSuite(&FooTest{}) }
|
||||
//
|
||||
// func (t *FooTest) SetUpTestSuite() {
|
||||
// someExpensiveThing = ComputeSomeExpensiveThing()
|
||||
// }
|
||||
//
|
||||
// func (t *FooTest) SetUp() {
|
||||
// t.tempFile = CreateTempFile()
|
||||
// }
|
||||
//
|
||||
// func (t *FooTest) TearDown() {
|
||||
// DeleteTempFile(t.tempFile)
|
||||
// }
|
||||
//
|
||||
// func (t *FooTest) FrobinicatorIsSuccessfullyTweaked() {
|
||||
// res := DoSomethingWithExpensiveThing(someExpensiveThing, t.tempFile)
|
||||
// ExpectThat(res, Equals(true))
|
||||
// }
|
||||
//
|
||||
func RegisterTestSuite(p interface{}) {
|
||||
if p == nil {
|
||||
panic("RegisterTestSuite called with nil suite.")
|
||||
}
|
||||
|
||||
testSuites = append(testSuites, p)
|
||||
}
|
||||
|
||||
// The set of test suites previously registered.
|
||||
var testSuites = make([]interface{}, 0)
|
||||
Generated
Vendored
-336
@@ -1,336 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package ogletest
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"flag"
|
||||
"fmt"
|
||||
"path"
|
||||
"reflect"
|
||||
"regexp"
|
||||
"runtime"
|
||||
"sync"
|
||||
"testing"
|
||||
"time"
|
||||
)
|
||||
|
||||
var testFilter = flag.String("ogletest.run", "", "Regexp for matching tests to run.")
|
||||
|
||||
// runTestsOnce protects RunTests from executing multiple times.
|
||||
var runTestsOnce sync.Once
|
||||
|
||||
func isAssertThatError(x interface{}) bool {
|
||||
_, ok := x.(*assertThatError)
|
||||
return ok
|
||||
}
|
||||
|
||||
// runTest runs a single test, returning a slice of failure records for that test.
|
||||
func runTest(suite interface{}, method reflect.Method) (failures []*failureRecord) {
|
||||
suiteValue := reflect.ValueOf(suite)
|
||||
suiteType := suiteValue.Type()
|
||||
|
||||
// Set up a clean slate for this test. Make sure to reset it after everything
|
||||
// below is finished, so we don't accidentally use it elsewhere.
|
||||
currentlyRunningTest = newTestInfo()
|
||||
defer func() {
|
||||
currentlyRunningTest = nil
|
||||
}()
|
||||
|
||||
// Create a receiver.
|
||||
suiteInstance := reflect.New(suiteType.Elem())
|
||||
|
||||
// Run the SetUp method, paying attention to whether it panics.
|
||||
setUpPanicked := runWithProtection(
|
||||
func() {
|
||||
runMethodIfExists(suiteInstance, "SetUp", currentlyRunningTest)
|
||||
},
|
||||
)
|
||||
|
||||
// Run the test method itself, but only if the SetUp method didn't panic.
|
||||
// (This includes AssertThat errors.)
|
||||
if !setUpPanicked {
|
||||
runWithProtection(
|
||||
func() {
|
||||
runMethodIfExists(suiteInstance, method.Name)
|
||||
},
|
||||
)
|
||||
}
|
||||
|
||||
// Run the TearDown method unconditionally.
|
||||
runWithProtection(
|
||||
func() {
|
||||
runMethodIfExists(suiteInstance, "TearDown")
|
||||
},
|
||||
)
|
||||
|
||||
// Tell the mock controller for the tests to report any errors it's sitting
|
||||
// on.
|
||||
currentlyRunningTest.MockController.Finish()
|
||||
|
||||
return currentlyRunningTest.failureRecords
|
||||
}
|
||||
|
||||
// RunTests runs the test suites registered with ogletest, communicating
|
||||
// failures to the supplied testing.T object. This is the bridge between
|
||||
// ogletest and the testing package (and gotest); you should ensure that it's
|
||||
// called at least once by creating a gotest-compatible test function and
|
||||
// calling it there.
|
||||
//
|
||||
// For example:
|
||||
//
|
||||
// import (
|
||||
// "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
// "testing"
|
||||
// )
|
||||
//
|
||||
// func TestOgletest(t *testing.T) {
|
||||
// ogletest.RunTests(t)
|
||||
// }
|
||||
//
|
||||
func RunTests(t *testing.T) {
|
||||
runTestsOnce.Do(func() { runTestsInternal(t) })
|
||||
}
|
||||
|
||||
// runTestsInternal does the real work of RunTests, which simply wraps it in a
|
||||
// sync.Once.
|
||||
func runTestsInternal(t *testing.T) {
|
||||
// Process each registered suite.
|
||||
for _, suite := range testSuites {
|
||||
val := reflect.ValueOf(suite)
|
||||
typ := val.Type()
|
||||
suiteName := typ.Elem().Name()
|
||||
|
||||
// Grab methods for the suite, filtering them to just the ones that we
|
||||
// don't need to skip.
|
||||
testMethods := filterMethods(suiteName, getMethodsInSourceOrder(typ))
|
||||
|
||||
// Is there anything left to do?
|
||||
if len(testMethods) == 0 {
|
||||
continue
|
||||
}
|
||||
|
||||
fmt.Printf("[----------] Running tests from %s\n", suiteName)
|
||||
|
||||
// Run the SetUpTestSuite method, if any.
|
||||
runMethodIfExists(val, "SetUpTestSuite")
|
||||
|
||||
// Run each method.
|
||||
for _, method := range testMethods {
|
||||
// Print a banner for the start of this test.
|
||||
fmt.Printf("[ RUN ] %s.%s\n", suiteName, method.Name)
|
||||
|
||||
// Run the test.
|
||||
startTime := time.Now()
|
||||
failures := runTest(suite, method)
|
||||
runDuration := time.Since(startTime)
|
||||
|
||||
// Print any failures, and mark the test as having failed if there are any.
|
||||
for _, record := range failures {
|
||||
t.Fail()
|
||||
userErrorSection := ""
|
||||
if record.UserError != "" {
|
||||
userErrorSection = record.UserError + "\n"
|
||||
}
|
||||
|
||||
fmt.Printf(
|
||||
"%s:%d:\n%s\n%s\n",
|
||||
record.FileName,
|
||||
record.LineNumber,
|
||||
record.GeneratedError,
|
||||
userErrorSection)
|
||||
}
|
||||
|
||||
// Print a banner for the end of the test.
|
||||
bannerMessage := "[ OK ]"
|
||||
if len(failures) != 0 {
|
||||
bannerMessage = "[ FAILED ]"
|
||||
}
|
||||
|
||||
// Print a summary of the time taken, if long enough.
|
||||
var timeMessage string
|
||||
if runDuration >= 25*time.Millisecond {
|
||||
timeMessage = fmt.Sprintf(" (%s)", runDuration.String())
|
||||
}
|
||||
|
||||
fmt.Printf(
|
||||
"%s %s.%s%s\n",
|
||||
bannerMessage,
|
||||
suiteName,
|
||||
method.Name,
|
||||
timeMessage)
|
||||
}
|
||||
|
||||
// Run the TearDownTestSuite method, if any.
|
||||
runMethodIfExists(val, "TearDownTestSuite")
|
||||
|
||||
fmt.Printf("[----------] Finished with tests from %s\n", suiteName)
|
||||
}
|
||||
}
|
||||
|
||||
// Run the supplied function, catching panics (including AssertThat errors) and
|
||||
// reporting them to the currently-running test as appropriate. Return true iff
|
||||
// the function panicked.
|
||||
func runWithProtection(f func()) (panicked bool) {
|
||||
defer func() {
|
||||
// If the test didn't panic, we're done.
|
||||
r := recover()
|
||||
if r == nil {
|
||||
return
|
||||
}
|
||||
|
||||
panicked = true
|
||||
|
||||
// We modify the currently running test below.
|
||||
currentlyRunningTest.mutex.Lock()
|
||||
defer currentlyRunningTest.mutex.Unlock()
|
||||
|
||||
// If the function panicked (and the panic was not due to an AssertThat
|
||||
// failure), add a failure for the panic.
|
||||
if !isAssertThatError(r) {
|
||||
// The stack looks like this:
|
||||
//
|
||||
// <this deferred function>
|
||||
// panic(r)
|
||||
// <function that called panic>
|
||||
//
|
||||
_, fileName, lineNumber, ok := runtime.Caller(2)
|
||||
var panicRecord failureRecord
|
||||
if ok {
|
||||
panicRecord.FileName = path.Base(fileName)
|
||||
panicRecord.LineNumber = lineNumber
|
||||
}
|
||||
|
||||
panicRecord.GeneratedError = fmt.Sprintf(
|
||||
"panic: %v\n\n%s", r, formatPanicStack())
|
||||
|
||||
currentlyRunningTest.failureRecords = append(
|
||||
currentlyRunningTest.failureRecords,
|
||||
&panicRecord)
|
||||
}
|
||||
}()
|
||||
|
||||
f()
|
||||
return
|
||||
}
|
||||
|
||||
func runMethodIfExists(v reflect.Value, name string, args ...interface{}) {
|
||||
method := v.MethodByName(name)
|
||||
if method.Kind() == reflect.Invalid {
|
||||
return
|
||||
}
|
||||
|
||||
if method.Type().NumIn() != len(args) {
|
||||
panic(fmt.Sprintf(
|
||||
"%s: expected %d args, actually %d.",
|
||||
name,
|
||||
len(args),
|
||||
method.Type().NumIn()))
|
||||
}
|
||||
|
||||
// Create a slice of reflect.Values to pass to the method. Simultaneously
|
||||
// check types.
|
||||
argVals := make([]reflect.Value, len(args))
|
||||
for i, arg := range args {
|
||||
argVal := reflect.ValueOf(arg)
|
||||
|
||||
if argVal.Type() != method.Type().In(i) {
|
||||
panic(fmt.Sprintf(
|
||||
"%s: expected arg %d to have type %v.",
|
||||
name,
|
||||
i,
|
||||
argVal.Type()))
|
||||
}
|
||||
|
||||
argVals[i] = argVal
|
||||
}
|
||||
|
||||
method.Call(argVals)
|
||||
}
|
||||
|
||||
func formatPanicStack() string {
|
||||
buf := new(bytes.Buffer)
|
||||
|
||||
// Walk the stack from top to bottom.
|
||||
panicPassed := false
|
||||
for i := 0; ; i++ {
|
||||
pc, file, line, ok := runtime.Caller(i)
|
||||
if !ok {
|
||||
break
|
||||
}
|
||||
|
||||
// Choose a function name to display.
|
||||
funcName := "(unknown)"
|
||||
if f := runtime.FuncForPC(pc); f != nil {
|
||||
funcName = f.Name()
|
||||
}
|
||||
|
||||
// Avoid stack frames at panic and above.
|
||||
if funcName == "runtime.panic" {
|
||||
panicPassed = true
|
||||
continue
|
||||
}
|
||||
|
||||
if !panicPassed {
|
||||
continue
|
||||
}
|
||||
|
||||
// Stop if we've gotten as far as the test runner code.
|
||||
if funcName == "github.com/smartystreets/goconvey/convey/assertions/ogletest.runMethodIfExists" {
|
||||
break
|
||||
}
|
||||
|
||||
// Add an entry for this frame.
|
||||
fmt.Fprintf(buf, "%s\n\t%s:%d\n", funcName, file, line)
|
||||
}
|
||||
|
||||
return buf.String()
|
||||
}
|
||||
|
||||
func filterMethods(suiteName string, in []reflect.Method) (out []reflect.Method) {
|
||||
for _, m := range in {
|
||||
// Skip set up, tear down, and unexported methods.
|
||||
if isSpecialMethod(m.Name) || !isExportedMethod(m.Name) {
|
||||
continue
|
||||
}
|
||||
|
||||
// Has the user told us to skip this method?
|
||||
fullName := fmt.Sprintf("%s.%s", suiteName, m.Name)
|
||||
matched, err := regexp.MatchString(*testFilter, fullName)
|
||||
if err != nil {
|
||||
panic("Invalid value for --ogletest.run: " + err.Error())
|
||||
}
|
||||
|
||||
if !matched {
|
||||
continue
|
||||
}
|
||||
|
||||
out = append(out, m)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func isSpecialMethod(name string) bool {
|
||||
return (name == "SetUpTestSuite") ||
|
||||
(name == "TearDownTestSuite") ||
|
||||
(name == "SetUp") ||
|
||||
(name == "TearDown")
|
||||
}
|
||||
|
||||
func isExportedMethod(name string) bool {
|
||||
return len(name) > 0 && name[0] >= 'A' && name[0] <= 'Z'
|
||||
}
|
||||
Generated
Vendored
-228
@@ -1,228 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
func TestFailingTest(t *testing.T) { RunTests(t) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Usual failures
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type FailingTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&FailingTest{}) }
|
||||
|
||||
func (t *FailingTest) TearDown() {
|
||||
fmt.Println("TearDown running.")
|
||||
}
|
||||
|
||||
func (t *FailingTest) PassingMethod() {
|
||||
}
|
||||
|
||||
func (t *FailingTest) Equals() {
|
||||
ExpectThat(17, Equals(17.5))
|
||||
ExpectThat(17, Equals("taco"))
|
||||
}
|
||||
|
||||
func (t *FailingTest) LessThan() {
|
||||
ExpectThat(18, LessThan(17))
|
||||
ExpectThat(18, LessThan("taco"))
|
||||
}
|
||||
|
||||
func (t *FailingTest) HasSubstr() {
|
||||
ExpectThat("taco", HasSubstr("ac"))
|
||||
ExpectThat(17, HasSubstr("ac"))
|
||||
}
|
||||
|
||||
func (t *FailingTest) ExpectWithUserErrorMessages() {
|
||||
ExpectThat(17, Equals(19), "foo bar: %d", 112)
|
||||
ExpectEq(17, 17.5, "foo bar: %d", 112)
|
||||
ExpectLe(17, 16.9, "foo bar: %d", 112)
|
||||
ExpectLt(17, 16.9, "foo bar: %d", 112)
|
||||
ExpectGe(17, 17.1, "foo bar: %d", 112)
|
||||
ExpectGt(17, "taco", "foo bar: %d", 112)
|
||||
ExpectNe(17, 17.0, "foo bar: %d", 112)
|
||||
ExpectFalse(true, "foo bar: %d", 112)
|
||||
ExpectTrue(false, "foo bar: %d", 112)
|
||||
}
|
||||
|
||||
func (t *FailingTest) AssertWithUserErrorMessages() {
|
||||
AssertThat(17, Equals(19), "foo bar: %d", 112)
|
||||
}
|
||||
|
||||
func (t *FailingTest) ModifiedExpectation() {
|
||||
ExpectThat(17, HasSubstr("ac")).SetCaller("foo.go", 112)
|
||||
ExpectEq(17, 19).SetCaller("bar.go", 117)
|
||||
}
|
||||
|
||||
func (t *FailingTest) ExpectationAliases() {
|
||||
ExpectEq(17, 17.5)
|
||||
ExpectEq("taco", 17.5)
|
||||
|
||||
ExpectLe(17, 16.9)
|
||||
ExpectLt(17, 16.9)
|
||||
ExpectLt(17, "taco")
|
||||
|
||||
ExpectGe(17, 17.1)
|
||||
ExpectGt(17, 17.1)
|
||||
ExpectGt(17, "taco")
|
||||
|
||||
ExpectNe(17, 17.0)
|
||||
ExpectNe(17, "taco")
|
||||
|
||||
ExpectFalse(true)
|
||||
ExpectFalse("taco")
|
||||
|
||||
ExpectTrue(false)
|
||||
ExpectTrue("taco")
|
||||
}
|
||||
|
||||
func (t *FailingTest) AssertThatFailure() {
|
||||
AssertThat(17, Equals(19))
|
||||
panic("Shouldn't get here.")
|
||||
}
|
||||
|
||||
func (t *FailingTest) AssertEqFailure() {
|
||||
AssertEq(19, 17)
|
||||
panic("Shouldn't get here.")
|
||||
}
|
||||
|
||||
func (t *FailingTest) AssertNeFailure() {
|
||||
AssertNe(19, 19)
|
||||
panic("Shouldn't get here.")
|
||||
}
|
||||
|
||||
func (t *FailingTest) AssertLeFailure() {
|
||||
AssertLe(19, 17)
|
||||
panic("Shouldn't get here.")
|
||||
}
|
||||
|
||||
func (t *FailingTest) AssertLtFailure() {
|
||||
AssertLt(19, 17)
|
||||
panic("Shouldn't get here.")
|
||||
}
|
||||
|
||||
func (t *FailingTest) AssertGeFailure() {
|
||||
AssertGe(17, 19)
|
||||
panic("Shouldn't get here.")
|
||||
}
|
||||
|
||||
func (t *FailingTest) AssertGtFailure() {
|
||||
AssertGt(17, 19)
|
||||
panic("Shouldn't get here.")
|
||||
}
|
||||
|
||||
func (t *FailingTest) AssertTrueFailure() {
|
||||
AssertTrue("taco")
|
||||
panic("Shouldn't get here.")
|
||||
}
|
||||
|
||||
func (t *FailingTest) AssertFalseFailure() {
|
||||
AssertFalse("taco")
|
||||
panic("Shouldn't get here.")
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Expectation failure during SetUp
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type ExpectFailDuringSetUpTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&ExpectFailDuringSetUpTest{}) }
|
||||
|
||||
func (t *ExpectFailDuringSetUpTest) SetUp(i *TestInfo) {
|
||||
ExpectFalse(true)
|
||||
}
|
||||
|
||||
func (t *ExpectFailDuringSetUpTest) TearDown() {
|
||||
fmt.Println("TearDown running.")
|
||||
}
|
||||
|
||||
func (t *ExpectFailDuringSetUpTest) PassingMethod() {
|
||||
fmt.Println("Method running.")
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Assertion failure during SetUp
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type AssertFailDuringSetUpTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&AssertFailDuringSetUpTest{}) }
|
||||
|
||||
func (t *AssertFailDuringSetUpTest) SetUp(i *TestInfo) {
|
||||
AssertFalse(true)
|
||||
}
|
||||
|
||||
func (t *AssertFailDuringSetUpTest) TearDown() {
|
||||
fmt.Println("TearDown running.")
|
||||
}
|
||||
|
||||
func (t *AssertFailDuringSetUpTest) PassingMethod() {
|
||||
fmt.Println("Method running.")
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Expectation failure during TearDown
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type ExpectFailDuringTearDownTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&ExpectFailDuringTearDownTest{}) }
|
||||
|
||||
func (t *ExpectFailDuringTearDownTest) SetUp(i *TestInfo) {
|
||||
fmt.Println("SetUp running.")
|
||||
}
|
||||
|
||||
func (t *ExpectFailDuringTearDownTest) TearDown() {
|
||||
ExpectFalse(true)
|
||||
}
|
||||
|
||||
func (t *ExpectFailDuringTearDownTest) PassingMethod() {
|
||||
fmt.Println("Method running.")
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Assertion failure during TearDown
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type AssertFailDuringTearDownTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&AssertFailDuringTearDownTest{}) }
|
||||
|
||||
func (t *AssertFailDuringTearDownTest) SetUp(i *TestInfo) {
|
||||
fmt.Println("SetUp running.")
|
||||
}
|
||||
|
||||
func (t *AssertFailDuringTearDownTest) TearDown() {
|
||||
AssertFalse(true)
|
||||
}
|
||||
|
||||
func (t *AssertFailDuringTearDownTest) PassingMethod() {
|
||||
fmt.Println("Method running.")
|
||||
}
|
||||
Generated
Vendored
-79
@@ -1,79 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
func TestFiltered(t *testing.T) { RunTests(t) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Partially filtered out
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type PartiallyFilteredTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&PartiallyFilteredTest{}) }
|
||||
|
||||
func (t *PartiallyFilteredTest) PassingTestFoo() {
|
||||
ExpectThat(19, Equals(19))
|
||||
}
|
||||
|
||||
func (t *PartiallyFilteredTest) PassingTestBar() {
|
||||
ExpectThat(17, Equals(17))
|
||||
}
|
||||
|
||||
func (t *PartiallyFilteredTest) PartiallyFilteredTestFoo() {
|
||||
ExpectThat(18, LessThan(17))
|
||||
}
|
||||
|
||||
func (t *PartiallyFilteredTest) PartiallyFilteredTestBar() {
|
||||
ExpectThat("taco", HasSubstr("blah"))
|
||||
}
|
||||
|
||||
func (t *PartiallyFilteredTest) PartiallyFilteredTestBaz() {
|
||||
ExpectThat(18, LessThan(17))
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Completely filtered out
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type CompletelyFilteredTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&CompletelyFilteredTest{}) }
|
||||
|
||||
func (t *CompletelyFilteredTest) SetUpTestSuite() {
|
||||
fmt.Println("SetUpTestSuite run!")
|
||||
}
|
||||
|
||||
func (t *CompletelyFilteredTest) TearDownTestSuite() {
|
||||
fmt.Println("TearDownTestSuite run!")
|
||||
}
|
||||
|
||||
func (t *PartiallyFilteredTest) SomePassingTest() {
|
||||
ExpectThat(19, Equals(19))
|
||||
}
|
||||
|
||||
func (t *PartiallyFilteredTest) SomeFailingTest() {
|
||||
ExpectThat(19, Equals(17))
|
||||
}
|
||||
Generated
Vendored
-266
@@ -1,266 +0,0 @@
|
||||
[----------] Running tests from FailingTest
|
||||
[ RUN ] FailingTest.PassingMethod
|
||||
TearDown running.
|
||||
[ OK ] FailingTest.PassingMethod
|
||||
[ RUN ] FailingTest.Equals
|
||||
TearDown running.
|
||||
failing_test.go:44:
|
||||
Expected: 17.5
|
||||
Actual: 17
|
||||
|
||||
failing_test.go:45:
|
||||
Expected: taco
|
||||
Actual: 17, which is not a string
|
||||
|
||||
[ FAILED ] FailingTest.Equals
|
||||
[ RUN ] FailingTest.LessThan
|
||||
TearDown running.
|
||||
failing_test.go:49:
|
||||
Expected: less than 17
|
||||
Actual: 18
|
||||
|
||||
failing_test.go:50:
|
||||
Expected: less than "taco"
|
||||
Actual: 18, which is not comparable
|
||||
|
||||
[ FAILED ] FailingTest.LessThan
|
||||
[ RUN ] FailingTest.HasSubstr
|
||||
TearDown running.
|
||||
failing_test.go:55:
|
||||
Expected: has substring "ac"
|
||||
Actual: 17, which is not a string
|
||||
|
||||
[ FAILED ] FailingTest.HasSubstr
|
||||
[ RUN ] FailingTest.ExpectWithUserErrorMessages
|
||||
TearDown running.
|
||||
failing_test.go:59:
|
||||
Expected: 19
|
||||
Actual: 17
|
||||
foo bar: 112
|
||||
|
||||
failing_test.go:60:
|
||||
Expected: 17
|
||||
Actual: 17.5
|
||||
foo bar: 112
|
||||
|
||||
failing_test.go:61:
|
||||
Expected: less than or equal to 16.9
|
||||
Actual: 17
|
||||
foo bar: 112
|
||||
|
||||
failing_test.go:62:
|
||||
Expected: less than 16.9
|
||||
Actual: 17
|
||||
foo bar: 112
|
||||
|
||||
failing_test.go:63:
|
||||
Expected: greater than or equal to 17.1
|
||||
Actual: 17
|
||||
foo bar: 112
|
||||
|
||||
failing_test.go:64:
|
||||
Expected: greater than "taco"
|
||||
Actual: 17, which is not comparable
|
||||
foo bar: 112
|
||||
|
||||
failing_test.go:65:
|
||||
Expected: not(17)
|
||||
Actual: 17
|
||||
foo bar: 112
|
||||
|
||||
failing_test.go:66:
|
||||
Expected: false
|
||||
Actual: true
|
||||
foo bar: 112
|
||||
|
||||
failing_test.go:67:
|
||||
Expected: true
|
||||
Actual: false
|
||||
foo bar: 112
|
||||
|
||||
[ FAILED ] FailingTest.ExpectWithUserErrorMessages
|
||||
[ RUN ] FailingTest.AssertWithUserErrorMessages
|
||||
TearDown running.
|
||||
failing_test.go:71:
|
||||
Expected: 19
|
||||
Actual: 17
|
||||
foo bar: 112
|
||||
|
||||
[ FAILED ] FailingTest.AssertWithUserErrorMessages
|
||||
[ RUN ] FailingTest.ModifiedExpectation
|
||||
TearDown running.
|
||||
foo.go:112:
|
||||
Expected: has substring "ac"
|
||||
Actual: 17, which is not a string
|
||||
|
||||
bar.go:117:
|
||||
Expected: 17
|
||||
Actual: 19
|
||||
|
||||
[ FAILED ] FailingTest.ModifiedExpectation
|
||||
[ RUN ] FailingTest.ExpectationAliases
|
||||
TearDown running.
|
||||
failing_test.go:80:
|
||||
Expected: 17
|
||||
Actual: 17.5
|
||||
|
||||
failing_test.go:81:
|
||||
Expected: taco
|
||||
Actual: 17.5, which is not a string
|
||||
|
||||
failing_test.go:83:
|
||||
Expected: less than or equal to 16.9
|
||||
Actual: 17
|
||||
|
||||
failing_test.go:84:
|
||||
Expected: less than 16.9
|
||||
Actual: 17
|
||||
|
||||
failing_test.go:85:
|
||||
Expected: less than "taco"
|
||||
Actual: 17, which is not comparable
|
||||
|
||||
failing_test.go:87:
|
||||
Expected: greater than or equal to 17.1
|
||||
Actual: 17
|
||||
|
||||
failing_test.go:88:
|
||||
Expected: greater than 17.1
|
||||
Actual: 17
|
||||
|
||||
failing_test.go:89:
|
||||
Expected: greater than "taco"
|
||||
Actual: 17, which is not comparable
|
||||
|
||||
failing_test.go:91:
|
||||
Expected: not(17)
|
||||
Actual: 17
|
||||
|
||||
failing_test.go:92:
|
||||
Expected: not(17)
|
||||
Actual: taco, which is not numeric
|
||||
|
||||
failing_test.go:94:
|
||||
Expected: false
|
||||
Actual: true
|
||||
|
||||
failing_test.go:95:
|
||||
Expected: false
|
||||
Actual: taco, which is not a bool
|
||||
|
||||
failing_test.go:97:
|
||||
Expected: true
|
||||
Actual: false
|
||||
|
||||
failing_test.go:98:
|
||||
Expected: true
|
||||
Actual: taco, which is not a bool
|
||||
|
||||
[ FAILED ] FailingTest.ExpectationAliases
|
||||
[ RUN ] FailingTest.AssertThatFailure
|
||||
TearDown running.
|
||||
failing_test.go:102:
|
||||
Expected: 19
|
||||
Actual: 17
|
||||
|
||||
[ FAILED ] FailingTest.AssertThatFailure
|
||||
[ RUN ] FailingTest.AssertEqFailure
|
||||
TearDown running.
|
||||
failing_test.go:107:
|
||||
Expected: 19
|
||||
Actual: 17
|
||||
|
||||
[ FAILED ] FailingTest.AssertEqFailure
|
||||
[ RUN ] FailingTest.AssertNeFailure
|
||||
TearDown running.
|
||||
failing_test.go:112:
|
||||
Expected: not(19)
|
||||
Actual: 19
|
||||
|
||||
[ FAILED ] FailingTest.AssertNeFailure
|
||||
[ RUN ] FailingTest.AssertLeFailure
|
||||
TearDown running.
|
||||
failing_test.go:117:
|
||||
Expected: less than or equal to 17
|
||||
Actual: 19
|
||||
|
||||
[ FAILED ] FailingTest.AssertLeFailure
|
||||
[ RUN ] FailingTest.AssertLtFailure
|
||||
TearDown running.
|
||||
failing_test.go:122:
|
||||
Expected: less than 17
|
||||
Actual: 19
|
||||
|
||||
[ FAILED ] FailingTest.AssertLtFailure
|
||||
[ RUN ] FailingTest.AssertGeFailure
|
||||
TearDown running.
|
||||
failing_test.go:127:
|
||||
Expected: greater than or equal to 19
|
||||
Actual: 17
|
||||
|
||||
[ FAILED ] FailingTest.AssertGeFailure
|
||||
[ RUN ] FailingTest.AssertGtFailure
|
||||
TearDown running.
|
||||
failing_test.go:132:
|
||||
Expected: greater than 19
|
||||
Actual: 17
|
||||
|
||||
[ FAILED ] FailingTest.AssertGtFailure
|
||||
[ RUN ] FailingTest.AssertTrueFailure
|
||||
TearDown running.
|
||||
failing_test.go:137:
|
||||
Expected: true
|
||||
Actual: taco, which is not a bool
|
||||
|
||||
[ FAILED ] FailingTest.AssertTrueFailure
|
||||
[ RUN ] FailingTest.AssertFalseFailure
|
||||
TearDown running.
|
||||
failing_test.go:142:
|
||||
Expected: false
|
||||
Actual: taco, which is not a bool
|
||||
|
||||
[ FAILED ] FailingTest.AssertFalseFailure
|
||||
[----------] Finished with tests from FailingTest
|
||||
[----------] Running tests from ExpectFailDuringSetUpTest
|
||||
[ RUN ] ExpectFailDuringSetUpTest.PassingMethod
|
||||
Method running.
|
||||
TearDown running.
|
||||
failing_test.go:156:
|
||||
Expected: false
|
||||
Actual: true
|
||||
|
||||
[ FAILED ] ExpectFailDuringSetUpTest.PassingMethod
|
||||
[----------] Finished with tests from ExpectFailDuringSetUpTest
|
||||
[----------] Running tests from AssertFailDuringSetUpTest
|
||||
[ RUN ] AssertFailDuringSetUpTest.PassingMethod
|
||||
TearDown running.
|
||||
failing_test.go:177:
|
||||
Expected: false
|
||||
Actual: true
|
||||
|
||||
[ FAILED ] AssertFailDuringSetUpTest.PassingMethod
|
||||
[----------] Finished with tests from AssertFailDuringSetUpTest
|
||||
[----------] Running tests from ExpectFailDuringTearDownTest
|
||||
[ RUN ] ExpectFailDuringTearDownTest.PassingMethod
|
||||
SetUp running.
|
||||
Method running.
|
||||
failing_test.go:202:
|
||||
Expected: false
|
||||
Actual: true
|
||||
|
||||
[ FAILED ] ExpectFailDuringTearDownTest.PassingMethod
|
||||
[----------] Finished with tests from ExpectFailDuringTearDownTest
|
||||
[----------] Running tests from AssertFailDuringTearDownTest
|
||||
[ RUN ] AssertFailDuringTearDownTest.PassingMethod
|
||||
SetUp running.
|
||||
Method running.
|
||||
failing_test.go:223:
|
||||
Expected: false
|
||||
Actual: true
|
||||
|
||||
[ FAILED ] AssertFailDuringTearDownTest.PassingMethod
|
||||
[----------] Finished with tests from AssertFailDuringTearDownTest
|
||||
--- FAIL: somepkg (1.23 seconds)
|
||||
FAIL
|
||||
exit status 1
|
||||
FAIL somepkg 1.234s
|
||||
Generated
Vendored
-20
@@ -1,20 +0,0 @@
|
||||
[----------] Running tests from PartiallyFilteredTest
|
||||
[ RUN ] PartiallyFilteredTest.PassingTestBar
|
||||
[ OK ] PartiallyFilteredTest.PassingTestBar
|
||||
[ RUN ] PartiallyFilteredTest.PartiallyFilteredTestBar
|
||||
filtered_test.go:49:
|
||||
Expected: has substring "blah"
|
||||
Actual: taco
|
||||
|
||||
[ FAILED ] PartiallyFilteredTest.PartiallyFilteredTestBar
|
||||
[ RUN ] PartiallyFilteredTest.PartiallyFilteredTestBaz
|
||||
filtered_test.go:53:
|
||||
Expected: less than 17
|
||||
Actual: 18
|
||||
|
||||
[ FAILED ] PartiallyFilteredTest.PartiallyFilteredTestBaz
|
||||
[----------] Finished with tests from PartiallyFilteredTest
|
||||
--- FAIL: somepkg (1.23 seconds)
|
||||
FAIL
|
||||
exit status 1
|
||||
FAIL somepkg 1.234s
|
||||
Generated
Vendored
-25
@@ -1,25 +0,0 @@
|
||||
[----------] Running tests from MockTest
|
||||
[ RUN ] MockTest.ExpectationSatisfied
|
||||
[ OK ] MockTest.ExpectationSatisfied
|
||||
[ RUN ] MockTest.MockExpectationNotSatisfied
|
||||
/some/path/mock_test.go:56:
|
||||
Unsatisfied expectation; expected At to be called at least 1 times; called 0 times.
|
||||
|
||||
[ FAILED ] MockTest.MockExpectationNotSatisfied
|
||||
[ RUN ] MockTest.ExpectCallForUnknownMethod
|
||||
/some/path/mock_test.go:61:
|
||||
Unknown method: FooBar
|
||||
|
||||
[ FAILED ] MockTest.ExpectCallForUnknownMethod
|
||||
[ RUN ] MockTest.UnexpectedCall
|
||||
/some/path/mock_test.go:65:
|
||||
Unexpected call to At with args: [11 23]
|
||||
|
||||
[ FAILED ] MockTest.UnexpectedCall
|
||||
[ RUN ] MockTest.InvokeFunction
|
||||
[ OK ] MockTest.InvokeFunction
|
||||
[----------] Finished with tests from MockTest
|
||||
--- FAIL: somepkg (1.23 seconds)
|
||||
FAIL
|
||||
exit status 1
|
||||
FAIL somepkg 1.234s
|
||||
Generated
Vendored
-2
@@ -1,2 +0,0 @@
|
||||
PASS
|
||||
ok somepkg 1.234s
|
||||
Generated
Vendored
-23
@@ -1,23 +0,0 @@
|
||||
[----------] Running tests from PanickingTest
|
||||
[ RUN ] PanickingTest.PanickingTest
|
||||
TearDown running.
|
||||
panicking_test.go:44:
|
||||
panic: foobar
|
||||
|
||||
github.com/smartystreets/goconvey/convey/assertions/ogletest/somepkg_test.(*PanickingTest).PanickingTest
|
||||
some_file.txt:0
|
||||
reflect.Value.call
|
||||
some_file.txt:0
|
||||
reflect.Value.Call
|
||||
some_file.txt:0
|
||||
|
||||
|
||||
[ FAILED ] PanickingTest.PanickingTest
|
||||
[ RUN ] PanickingTest.ZzzSomeOtherTest
|
||||
TearDown running.
|
||||
[ OK ] PanickingTest.ZzzSomeOtherTest
|
||||
[----------] Finished with tests from PanickingTest
|
||||
--- FAIL: somepkg (1.23 seconds)
|
||||
FAIL
|
||||
exit status 1
|
||||
FAIL somepkg 1.234s
|
||||
Generated
Vendored
-14
@@ -1,14 +0,0 @@
|
||||
[----------] Running tests from PassingTest
|
||||
[ RUN ] PassingTest.EmptyTestMethod
|
||||
[ OK ] PassingTest.EmptyTestMethod
|
||||
[ RUN ] PassingTest.SuccessfullMatches
|
||||
[ OK ] PassingTest.SuccessfullMatches
|
||||
[ RUN ] PassingTest.ExpectAliases
|
||||
[ OK ] PassingTest.ExpectAliases
|
||||
[ RUN ] PassingTest.AssertAliases
|
||||
[ OK ] PassingTest.AssertAliases
|
||||
[ RUN ] PassingTest.SlowTest
|
||||
[ OK ] PassingTest.SlowTest (1234ms)
|
||||
[----------] Finished with tests from PassingTest
|
||||
PASS
|
||||
ok somepkg 1.234s
|
||||
Generated
Vendored
-14
@@ -1,14 +0,0 @@
|
||||
[----------] Running tests from RunTwiceTest
|
||||
[ RUN ] RunTwiceTest.PassingMethod
|
||||
[ OK ] RunTwiceTest.PassingMethod
|
||||
[ RUN ] RunTwiceTest.FailingMethod
|
||||
run_twice_test.go:46:
|
||||
Expected: 17.5
|
||||
Actual: 17
|
||||
|
||||
[ FAILED ] RunTwiceTest.FailingMethod
|
||||
[----------] Finished with tests from RunTwiceTest
|
||||
--- FAIL: somepkg (1.23 seconds)
|
||||
FAIL
|
||||
exit status 1
|
||||
FAIL somepkg 1.234s
|
||||
Generated
Vendored
-12
@@ -1,12 +0,0 @@
|
||||
[----------] Running tests from UnexportedTest
|
||||
[ RUN ] UnexportedTest.SomeTest
|
||||
unexported_test.go:42:
|
||||
Expected: 4
|
||||
Actual: 3
|
||||
|
||||
[ FAILED ] UnexportedTest.SomeTest
|
||||
[----------] Finished with tests from UnexportedTest
|
||||
--- FAIL: somepkg (1.23 seconds)
|
||||
FAIL
|
||||
exit status 1
|
||||
FAIL somepkg 1.234s
|
||||
Generated
Vendored
-82
@@ -1,82 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"image/color"
|
||||
"testing"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
"github.com/smartystreets/goconvey/convey/assertions/oglemock"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
"github.com/smartystreets/goconvey/convey/assertions/ogletest/test_cases/mock_image"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type MockTest struct {
|
||||
controller oglemock.Controller
|
||||
image mock_image.MockImage
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&MockTest{}) }
|
||||
func TestMockTest(t *testing.T) { RunTests(t) }
|
||||
|
||||
func (t *MockTest) SetUp(i *TestInfo) {
|
||||
t.controller = i.MockController
|
||||
t.image = mock_image.NewMockImage(t.controller, "some mock image")
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *MockTest) ExpectationSatisfied() {
|
||||
ExpectCall(t.image, "At")(11, GreaterThan(19)).
|
||||
WillOnce(oglemock.Return(color.Gray{0}))
|
||||
|
||||
ExpectThat(t.image.At(11, 23), IdenticalTo(color.Gray{0}))
|
||||
}
|
||||
|
||||
func (t *MockTest) MockExpectationNotSatisfied() {
|
||||
ExpectCall(t.image, "At")(11, GreaterThan(19)).
|
||||
WillOnce(oglemock.Return(color.Gray{0}))
|
||||
}
|
||||
|
||||
func (t *MockTest) ExpectCallForUnknownMethod() {
|
||||
ExpectCall(t.image, "FooBar")(11)
|
||||
}
|
||||
|
||||
func (t *MockTest) UnexpectedCall() {
|
||||
t.image.At(11, 23)
|
||||
}
|
||||
|
||||
func (t *MockTest) InvokeFunction() {
|
||||
var suppliedX, suppliedY int
|
||||
f := func(x, y int) color.Color {
|
||||
suppliedX = x
|
||||
suppliedY = y
|
||||
return color.Gray{17}
|
||||
}
|
||||
|
||||
ExpectCall(t.image, "At")(Any(), Any()).
|
||||
WillOnce(oglemock.Invoke(f))
|
||||
|
||||
ExpectThat(t.image.At(-1, 12), IdenticalTo(color.Gray{17}))
|
||||
ExpectEq(-1, suppliedX)
|
||||
ExpectEq(12, suppliedY)
|
||||
}
|
||||
Generated
Vendored
-116
@@ -1,116 +0,0 @@
|
||||
// This file was auto-generated using createmock. See the following page for
|
||||
// more information:
|
||||
//
|
||||
// https://github.com/smartystreets/goconvey/convey/assertions/oglemock
|
||||
//
|
||||
|
||||
package mock_image
|
||||
|
||||
import (
|
||||
fmt "fmt"
|
||||
image "image"
|
||||
color "image/color"
|
||||
runtime "runtime"
|
||||
unsafe "unsafe"
|
||||
|
||||
oglemock "github.com/smartystreets/goconvey/convey/assertions/oglemock"
|
||||
)
|
||||
|
||||
type MockImage interface {
|
||||
image.Image
|
||||
oglemock.MockObject
|
||||
}
|
||||
|
||||
type mockImage struct {
|
||||
controller oglemock.Controller
|
||||
description string
|
||||
}
|
||||
|
||||
func NewMockImage(
|
||||
c oglemock.Controller,
|
||||
desc string) MockImage {
|
||||
return &mockImage{
|
||||
controller: c,
|
||||
description: desc,
|
||||
}
|
||||
}
|
||||
|
||||
func (m *mockImage) Oglemock_Id() uintptr {
|
||||
return uintptr(unsafe.Pointer(m))
|
||||
}
|
||||
|
||||
func (m *mockImage) Oglemock_Description() string {
|
||||
return m.description
|
||||
}
|
||||
|
||||
func (m *mockImage) At(p0 int, p1 int) (o0 color.Color) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"At",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{p0, p1})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockImage.At: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 color.Color
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(color.Color)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockImage) Bounds() (o0 image.Rectangle) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"Bounds",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockImage.Bounds: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 image.Rectangle
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(image.Rectangle)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (m *mockImage) ColorModel() (o0 color.Model) {
|
||||
// Get a file name and line number for the caller.
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
|
||||
// Hand the call off to the controller, which does most of the work.
|
||||
retVals := m.controller.HandleMethodCall(
|
||||
m,
|
||||
"ColorModel",
|
||||
file,
|
||||
line,
|
||||
[]interface{}{})
|
||||
|
||||
if len(retVals) != 1 {
|
||||
panic(fmt.Sprintf("mockImage.ColorModel: invalid return values: %v", retVals))
|
||||
}
|
||||
|
||||
// o0 color.Model
|
||||
if retVals[0] != nil {
|
||||
o0 = retVals[0].(color.Model)
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
Generated
Vendored
-41
@@ -1,41 +0,0 @@
|
||||
// Copyright 2012 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
func TestNoCases(t *testing.T) { RunTests(t) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type NoCasesTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&NoCasesTest{}) }
|
||||
|
||||
func (t *NoCasesTest) SetUpTestSuite() {
|
||||
fmt.Println("SetUpTestSuite run!")
|
||||
}
|
||||
|
||||
func (t *NoCasesTest) TearDownTestSuite() {
|
||||
fmt.Println("TearDownTestSuite run!")
|
||||
}
|
||||
Generated
Vendored
-49
@@ -1,49 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type PanickingTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&PanickingTest{}) }
|
||||
func TestPanickingTest(t *testing.T) { RunTests(t) }
|
||||
|
||||
func (t *PanickingTest) TearDown() {
|
||||
fmt.Println("TearDown running.")
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *PanickingTest) PanickingTest() {
|
||||
panic("foobar")
|
||||
}
|
||||
|
||||
func (t *PanickingTest) ZzzSomeOtherTest() {
|
||||
ExpectThat(17, Equals(17.0))
|
||||
}
|
||||
Generated
Vendored
-88
@@ -1,88 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"testing"
|
||||
"time"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type PassingTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&PassingTest{}) }
|
||||
func TestPassingTest(t *testing.T) { RunTests(t) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *PassingTest) EmptyTestMethod() {
|
||||
}
|
||||
|
||||
func (t *PassingTest) SuccessfullMatches() {
|
||||
ExpectThat(17, Equals(17.0))
|
||||
ExpectThat(16.9, LessThan(17))
|
||||
ExpectThat("taco", HasSubstr("ac"))
|
||||
|
||||
AssertThat(17, Equals(17.0))
|
||||
AssertThat(16.9, LessThan(17))
|
||||
AssertThat("taco", HasSubstr("ac"))
|
||||
}
|
||||
|
||||
func (t *PassingTest) ExpectAliases() {
|
||||
ExpectEq(17, 17.0)
|
||||
|
||||
ExpectLe(17, 17.0)
|
||||
ExpectLe(17, 18.0)
|
||||
ExpectLt(17, 18.0)
|
||||
|
||||
ExpectGe(17, 17.0)
|
||||
ExpectGe(17, 16.0)
|
||||
ExpectGt(17, 16.0)
|
||||
|
||||
ExpectNe(17, 18.0)
|
||||
|
||||
ExpectTrue(true)
|
||||
ExpectFalse(false)
|
||||
}
|
||||
|
||||
func (t *PassingTest) AssertAliases() {
|
||||
AssertEq(17, 17.0)
|
||||
|
||||
AssertLe(17, 17.0)
|
||||
AssertLe(17, 18.0)
|
||||
AssertLt(17, 18.0)
|
||||
|
||||
AssertGe(17, 17.0)
|
||||
AssertGe(17, 16.0)
|
||||
AssertGt(17, 16.0)
|
||||
|
||||
AssertNe(17, 18.0)
|
||||
|
||||
AssertTrue(true)
|
||||
AssertFalse(false)
|
||||
}
|
||||
|
||||
func (t *PassingTest) SlowTest() {
|
||||
time.Sleep(37 * time.Millisecond)
|
||||
}
|
||||
Generated
Vendored
-47
@@ -1,47 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"testing"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type RunTwiceTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&RunTwiceTest{}) }
|
||||
|
||||
// Set up two helpers that call RunTests. The test should still only be run
|
||||
// once.
|
||||
func TestOgletest(t *testing.T) { RunTests(t) }
|
||||
func TestOgletest2(t *testing.T) { RunTests(t) }
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *RunTwiceTest) PassingMethod() {
|
||||
}
|
||||
|
||||
func (t *RunTwiceTest) FailingMethod() {
|
||||
ExpectThat(17, Equals(17.5))
|
||||
}
|
||||
Generated
Vendored
-43
@@ -1,43 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package oglematchers_test
|
||||
|
||||
import (
|
||||
"testing"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/oglematchers"
|
||||
. "github.com/smartystreets/goconvey/convey/assertions/ogletest"
|
||||
)
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Helpers
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
type UnexportedTest struct {
|
||||
}
|
||||
|
||||
func init() { RegisterTestSuite(&UnexportedTest{}) }
|
||||
func TestUnexportedTest(t *testing.T) { RunTests(t) }
|
||||
|
||||
func (t *UnexportedTest) someUnexportedMethod() {
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
// Tests
|
||||
////////////////////////////////////////////////////////////////////////
|
||||
|
||||
func (t *UnexportedTest) SomeTest() {
|
||||
ExpectThat(3, Equals(4))
|
||||
}
|
||||
Generated
Vendored
-100
@@ -1,100 +0,0 @@
|
||||
// Copyright 2011 Aaron Jacobs. All Rights Reserved.
|
||||
// Author: aaronjjacobs@gmail.com (Aaron Jacobs)
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
|
||||
package ogletest
|
||||
|
||||
import (
|
||||
"sync"
|
||||
|
||||
"github.com/smartystreets/goconvey/convey/assertions/oglemock"
|
||||
)
|
||||
|
||||
// TestInfo represents information about a currently running or previously-run
|
||||
// test.
|
||||
type TestInfo struct {
|
||||
// A mock controller that is set up to report errors to the ogletest test
|
||||
// runner. This can be used for setting up mock expectations and handling
|
||||
// mock calls. The Finish method should not be run by the user; ogletest will
|
||||
// do that automatically after the test's TearDown method is run.
|
||||
//
|
||||
// Note that this feature is still experimental, and is subject to change.
|
||||
MockController oglemock.Controller
|
||||
|
||||
// A mutex protecting shared state.
|
||||
mutex sync.RWMutex
|
||||
|
||||
// A set of failure records that the test has produced.
|
||||
failureRecords []*failureRecord // Protected by mutex
|
||||
}
|
||||
|
||||
// currentlyRunningTest is the state for the currently running test, if any.
|
||||
var currentlyRunningTest *TestInfo
|
||||
|
||||
// newTestInfo creates a valid but empty TestInfo struct.
|
||||
func newTestInfo() *TestInfo {
|
||||
info := &TestInfo{}
|
||||
info.failureRecords = make([]*failureRecord, 0)
|
||||
info.MockController = oglemock.NewController(&testInfoErrorReporter{info})
|
||||
return info
|
||||
}
|
||||
|
||||
// failureRecord represents a single failed expectation for a test.
|
||||
type failureRecord struct {
|
||||
// The file name within which the expectation failed, e.g. "foo_test.go".
|
||||
FileName string
|
||||
|
||||
// The line number at which the expectation failed.
|
||||
LineNumber int
|
||||
|
||||
// The error generated by the testing framework. For example:
|
||||
//
|
||||
// Expected: 17
|
||||
// Actual: "taco", which is not numeric
|
||||
//
|
||||
GeneratedError string
|
||||
|
||||
// A user-specified string to print out with the error, if any.
|
||||
UserError string
|
||||
}
|
||||
|
||||
// testInfoErrorReporter is an oglemock.ErrorReporter that writes failure
|
||||
// records into a test info struct.
|
||||
type testInfoErrorReporter struct {
|
||||
testInfo *TestInfo
|
||||
}
|
||||
|
||||
func (r *testInfoErrorReporter) ReportError(
|
||||
fileName string,
|
||||
lineNumber int,
|
||||
err error) {
|
||||
r.testInfo.mutex.Lock()
|
||||
defer r.testInfo.mutex.Unlock()
|
||||
|
||||
record := &failureRecord{
|
||||
FileName: fileName,
|
||||
LineNumber: lineNumber,
|
||||
GeneratedError: err.Error(),
|
||||
}
|
||||
|
||||
r.testInfo.failureRecords = append(r.testInfo.failureRecords, record)
|
||||
}
|
||||
|
||||
func (r *testInfoErrorReporter) ReportFatalError(
|
||||
fileName string,
|
||||
lineNumber int,
|
||||
err error) {
|
||||
r.ReportError(fileName, lineNumber, err)
|
||||
panic(&assertThatError{})
|
||||
}
|
||||
Generated
Vendored
-53
@@ -1,53 +0,0 @@
|
||||
package assertions
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestShouldPanic(t *testing.T) {
|
||||
fail(t, so(func() {}, ShouldPanic, 1), "This assertion requires exactly 0 comparison values (you provided 1).")
|
||||
fail(t, so(func() {}, ShouldPanic, 1, 2, 3), "This assertion requires exactly 0 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(1, ShouldPanic), shouldUseVoidNiladicFunction)
|
||||
fail(t, so(func(i int) {}, ShouldPanic), shouldUseVoidNiladicFunction)
|
||||
fail(t, so(func() int { panic("hi") }, ShouldPanic), shouldUseVoidNiladicFunction)
|
||||
|
||||
fail(t, so(func() {}, ShouldPanic), shouldHavePanicked)
|
||||
pass(t, so(func() { panic("hi") }, ShouldPanic))
|
||||
}
|
||||
|
||||
func TestShouldNotPanic(t *testing.T) {
|
||||
fail(t, so(func() {}, ShouldNotPanic, 1), "This assertion requires exactly 0 comparison values (you provided 1).")
|
||||
fail(t, so(func() {}, ShouldNotPanic, 1, 2, 3), "This assertion requires exactly 0 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(1, ShouldNotPanic), shouldUseVoidNiladicFunction)
|
||||
fail(t, so(func(i int) {}, ShouldNotPanic), shouldUseVoidNiladicFunction)
|
||||
|
||||
fail(t, so(func() { panic("hi") }, ShouldNotPanic), fmt.Sprintf(shouldNotHavePanicked, "hi"))
|
||||
pass(t, so(func() {}, ShouldNotPanic))
|
||||
}
|
||||
|
||||
func TestShouldPanicWith(t *testing.T) {
|
||||
fail(t, so(func() {}, ShouldPanicWith), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(func() {}, ShouldPanicWith, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(1, ShouldPanicWith, 1), shouldUseVoidNiladicFunction)
|
||||
fail(t, so(func(i int) {}, ShouldPanicWith, "hi"), shouldUseVoidNiladicFunction)
|
||||
fail(t, so(func() {}, ShouldPanicWith, "bye"), shouldHavePanicked)
|
||||
fail(t, so(func() { panic("hi") }, ShouldPanicWith, "bye"), "bye|hi|Expected func() to panic with 'bye' (but it panicked with 'hi')!")
|
||||
|
||||
pass(t, so(func() { panic("hi") }, ShouldPanicWith, "hi"))
|
||||
}
|
||||
|
||||
func TestShouldNotPanicWith(t *testing.T) {
|
||||
fail(t, so(func() {}, ShouldNotPanicWith), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(func() {}, ShouldNotPanicWith, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(1, ShouldNotPanicWith, 1), shouldUseVoidNiladicFunction)
|
||||
fail(t, so(func(i int) {}, ShouldNotPanicWith, "hi"), shouldUseVoidNiladicFunction)
|
||||
fail(t, so(func() { panic("hi") }, ShouldNotPanicWith, "hi"), "Expected func() NOT to panic with 'hi' (but it did)!")
|
||||
|
||||
pass(t, so(func() {}, ShouldNotPanicWith, "bye"))
|
||||
pass(t, so(func() { panic("hi") }, ShouldNotPanicWith, "bye"))
|
||||
}
|
||||
Generated
Vendored
-145
@@ -1,145 +0,0 @@
|
||||
package assertions
|
||||
|
||||
import "testing"
|
||||
|
||||
func TestShouldBeGreaterThan(t *testing.T) {
|
||||
fail(t, so(1, ShouldBeGreaterThan), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(1, ShouldBeGreaterThan, 0, 0), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
|
||||
pass(t, so(1, ShouldBeGreaterThan, 0))
|
||||
pass(t, so(1.1, ShouldBeGreaterThan, 1))
|
||||
pass(t, so(1, ShouldBeGreaterThan, uint(0)))
|
||||
pass(t, so("b", ShouldBeGreaterThan, "a"))
|
||||
|
||||
fail(t, so(0, ShouldBeGreaterThan, 1), "Expected '0' to be greater than '1' (but it wasn't)!")
|
||||
fail(t, so(1, ShouldBeGreaterThan, 1.1), "Expected '1' to be greater than '1.1' (but it wasn't)!")
|
||||
fail(t, so(uint(0), ShouldBeGreaterThan, 1.1), "Expected '0' to be greater than '1.1' (but it wasn't)!")
|
||||
fail(t, so("a", ShouldBeGreaterThan, "b"), "Expected 'a' to be greater than 'b' (but it wasn't)!")
|
||||
}
|
||||
|
||||
func TestShouldBeGreaterThanOrEqual(t *testing.T) {
|
||||
fail(t, so(1, ShouldBeGreaterThanOrEqualTo), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(1, ShouldBeGreaterThanOrEqualTo, 0, 0), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
|
||||
pass(t, so(1, ShouldBeGreaterThanOrEqualTo, 1))
|
||||
pass(t, so(1.1, ShouldBeGreaterThanOrEqualTo, 1.1))
|
||||
pass(t, so(1, ShouldBeGreaterThanOrEqualTo, uint(1)))
|
||||
pass(t, so("b", ShouldBeGreaterThanOrEqualTo, "b"))
|
||||
|
||||
pass(t, so(1, ShouldBeGreaterThanOrEqualTo, 0))
|
||||
pass(t, so(1.1, ShouldBeGreaterThanOrEqualTo, 1))
|
||||
pass(t, so(1, ShouldBeGreaterThanOrEqualTo, uint(0)))
|
||||
pass(t, so("b", ShouldBeGreaterThanOrEqualTo, "a"))
|
||||
|
||||
fail(t, so(0, ShouldBeGreaterThanOrEqualTo, 1), "Expected '0' to be greater than or equal to '1' (but it wasn't)!")
|
||||
fail(t, so(1, ShouldBeGreaterThanOrEqualTo, 1.1), "Expected '1' to be greater than or equal to '1.1' (but it wasn't)!")
|
||||
fail(t, so(uint(0), ShouldBeGreaterThanOrEqualTo, 1.1), "Expected '0' to be greater than or equal to '1.1' (but it wasn't)!")
|
||||
fail(t, so("a", ShouldBeGreaterThanOrEqualTo, "b"), "Expected 'a' to be greater than or equal to 'b' (but it wasn't)!")
|
||||
}
|
||||
|
||||
func TestShouldBeLessThan(t *testing.T) {
|
||||
fail(t, so(1, ShouldBeLessThan), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(1, ShouldBeLessThan, 0, 0), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
|
||||
pass(t, so(0, ShouldBeLessThan, 1))
|
||||
pass(t, so(1, ShouldBeLessThan, 1.1))
|
||||
pass(t, so(uint(0), ShouldBeLessThan, 1))
|
||||
pass(t, so("a", ShouldBeLessThan, "b"))
|
||||
|
||||
fail(t, so(1, ShouldBeLessThan, 0), "Expected '1' to be less than '0' (but it wasn't)!")
|
||||
fail(t, so(1.1, ShouldBeLessThan, 1), "Expected '1.1' to be less than '1' (but it wasn't)!")
|
||||
fail(t, so(1.1, ShouldBeLessThan, uint(0)), "Expected '1.1' to be less than '0' (but it wasn't)!")
|
||||
fail(t, so("b", ShouldBeLessThan, "a"), "Expected 'b' to be less than 'a' (but it wasn't)!")
|
||||
}
|
||||
|
||||
func TestShouldBeLessThanOrEqualTo(t *testing.T) {
|
||||
fail(t, so(1, ShouldBeLessThanOrEqualTo), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(1, ShouldBeLessThanOrEqualTo, 0, 0), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
|
||||
pass(t, so(1, ShouldBeLessThanOrEqualTo, 1))
|
||||
pass(t, so(1.1, ShouldBeLessThanOrEqualTo, 1.1))
|
||||
pass(t, so(uint(1), ShouldBeLessThanOrEqualTo, 1))
|
||||
pass(t, so("b", ShouldBeLessThanOrEqualTo, "b"))
|
||||
|
||||
pass(t, so(0, ShouldBeLessThanOrEqualTo, 1))
|
||||
pass(t, so(1, ShouldBeLessThanOrEqualTo, 1.1))
|
||||
pass(t, so(uint(0), ShouldBeLessThanOrEqualTo, 1))
|
||||
pass(t, so("a", ShouldBeLessThanOrEqualTo, "b"))
|
||||
|
||||
fail(t, so(1, ShouldBeLessThanOrEqualTo, 0), "Expected '1' to be less than '0' (but it wasn't)!")
|
||||
fail(t, so(1.1, ShouldBeLessThanOrEqualTo, 1), "Expected '1.1' to be less than '1' (but it wasn't)!")
|
||||
fail(t, so(1.1, ShouldBeLessThanOrEqualTo, uint(0)), "Expected '1.1' to be less than '0' (but it wasn't)!")
|
||||
fail(t, so("b", ShouldBeLessThanOrEqualTo, "a"), "Expected 'b' to be less than 'a' (but it wasn't)!")
|
||||
}
|
||||
|
||||
func TestShouldBeBetween(t *testing.T) {
|
||||
fail(t, so(1, ShouldBeBetween), "This assertion requires exactly 2 comparison values (you provided 0).")
|
||||
fail(t, so(1, ShouldBeBetween, 1, 2, 3), "This assertion requires exactly 2 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(4, ShouldBeBetween, 1, 1), "The lower and upper bounds must be different values (they were both '1').")
|
||||
|
||||
fail(t, so(7, ShouldBeBetween, 8, 12), "Expected '7' to be between '8' and '12' (but it wasn't)!")
|
||||
fail(t, so(8, ShouldBeBetween, 8, 12), "Expected '8' to be between '8' and '12' (but it wasn't)!")
|
||||
pass(t, so(9, ShouldBeBetween, 8, 12))
|
||||
pass(t, so(10, ShouldBeBetween, 8, 12))
|
||||
pass(t, so(11, ShouldBeBetween, 8, 12))
|
||||
fail(t, so(12, ShouldBeBetween, 8, 12), "Expected '12' to be between '8' and '12' (but it wasn't)!")
|
||||
fail(t, so(13, ShouldBeBetween, 8, 12), "Expected '13' to be between '8' and '12' (but it wasn't)!")
|
||||
|
||||
pass(t, so(1, ShouldBeBetween, 2, 0))
|
||||
fail(t, so(-1, ShouldBeBetween, 2, 0), "Expected '-1' to be between '0' and '2' (but it wasn't)!")
|
||||
}
|
||||
|
||||
func TestShouldNotBeBetween(t *testing.T) {
|
||||
fail(t, so(1, ShouldNotBeBetween), "This assertion requires exactly 2 comparison values (you provided 0).")
|
||||
fail(t, so(1, ShouldNotBeBetween, 1, 2, 3), "This assertion requires exactly 2 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(4, ShouldNotBeBetween, 1, 1), "The lower and upper bounds must be different values (they were both '1').")
|
||||
|
||||
pass(t, so(7, ShouldNotBeBetween, 8, 12))
|
||||
pass(t, so(8, ShouldNotBeBetween, 8, 12))
|
||||
fail(t, so(9, ShouldNotBeBetween, 8, 12), "Expected '9' NOT to be between '8' and '12' (but it was)!")
|
||||
fail(t, so(10, ShouldNotBeBetween, 8, 12), "Expected '10' NOT to be between '8' and '12' (but it was)!")
|
||||
fail(t, so(11, ShouldNotBeBetween, 8, 12), "Expected '11' NOT to be between '8' and '12' (but it was)!")
|
||||
pass(t, so(12, ShouldNotBeBetween, 8, 12))
|
||||
pass(t, so(13, ShouldNotBeBetween, 8, 12))
|
||||
|
||||
pass(t, so(-1, ShouldNotBeBetween, 2, 0))
|
||||
fail(t, so(1, ShouldNotBeBetween, 2, 0), "Expected '1' NOT to be between '0' and '2' (but it was)!")
|
||||
}
|
||||
|
||||
func TestShouldBeBetweenOrEqual(t *testing.T) {
|
||||
fail(t, so(1, ShouldBeBetweenOrEqual), "This assertion requires exactly 2 comparison values (you provided 0).")
|
||||
fail(t, so(1, ShouldBeBetweenOrEqual, 1, 2, 3), "This assertion requires exactly 2 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(4, ShouldBeBetweenOrEqual, 1, 1), "The lower and upper bounds must be different values (they were both '1').")
|
||||
|
||||
fail(t, so(7, ShouldBeBetweenOrEqual, 8, 12), "Expected '7' to be between '8' and '12' or equal to one of them (but it wasn't)!")
|
||||
pass(t, so(8, ShouldBeBetweenOrEqual, 8, 12))
|
||||
pass(t, so(9, ShouldBeBetweenOrEqual, 8, 12))
|
||||
pass(t, so(10, ShouldBeBetweenOrEqual, 8, 12))
|
||||
pass(t, so(11, ShouldBeBetweenOrEqual, 8, 12))
|
||||
pass(t, so(12, ShouldBeBetweenOrEqual, 8, 12))
|
||||
fail(t, so(13, ShouldBeBetweenOrEqual, 8, 12), "Expected '13' to be between '8' and '12' or equal to one of them (but it wasn't)!")
|
||||
|
||||
pass(t, so(1, ShouldBeBetweenOrEqual, 2, 0))
|
||||
fail(t, so(-1, ShouldBeBetweenOrEqual, 2, 0), "Expected '-1' to be between '0' and '2' or equal to one of them (but it wasn't)!")
|
||||
}
|
||||
|
||||
func TestShouldNotBeBetweenOrEqual(t *testing.T) {
|
||||
fail(t, so(1, ShouldNotBeBetweenOrEqual), "This assertion requires exactly 2 comparison values (you provided 0).")
|
||||
fail(t, so(1, ShouldNotBeBetweenOrEqual, 1, 2, 3), "This assertion requires exactly 2 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(4, ShouldNotBeBetweenOrEqual, 1, 1), "The lower and upper bounds must be different values (they were both '1').")
|
||||
|
||||
pass(t, so(7, ShouldNotBeBetweenOrEqual, 8, 12))
|
||||
fail(t, so(8, ShouldNotBeBetweenOrEqual, 8, 12), "Expected '8' NOT to be between '8' and '12' or equal to one of them (but it was)!")
|
||||
fail(t, so(9, ShouldNotBeBetweenOrEqual, 8, 12), "Expected '9' NOT to be between '8' and '12' or equal to one of them (but it was)!")
|
||||
fail(t, so(10, ShouldNotBeBetweenOrEqual, 8, 12), "Expected '10' NOT to be between '8' and '12' or equal to one of them (but it was)!")
|
||||
fail(t, so(11, ShouldNotBeBetweenOrEqual, 8, 12), "Expected '11' NOT to be between '8' and '12' or equal to one of them (but it was)!")
|
||||
fail(t, so(12, ShouldNotBeBetweenOrEqual, 8, 12), "Expected '12' NOT to be between '8' and '12' or equal to one of them (but it was)!")
|
||||
pass(t, so(13, ShouldNotBeBetweenOrEqual, 8, 12))
|
||||
|
||||
pass(t, so(-1, ShouldNotBeBetweenOrEqual, 2, 0))
|
||||
fail(t, so(1, ShouldNotBeBetweenOrEqual, 2, 0), "Expected '1' NOT to be between '0' and '2' or equal to one of them (but it was)!")
|
||||
}
|
||||
Generated
Vendored
-38
@@ -1,38 +0,0 @@
|
||||
package assertions
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"testing"
|
||||
|
||||
"github.com/smartystreets/goconvey/convey/reporting"
|
||||
)
|
||||
|
||||
func TestSerializerCreatesSerializedVersionOfAssertionResult(t *testing.T) {
|
||||
thing1 := Thing1{"Hi"}
|
||||
thing2 := Thing2{"Bye"}
|
||||
message := "Super-hip failure message."
|
||||
serializer := newSerializer()
|
||||
|
||||
actualResult := serializer.serialize(thing1, thing2, message)
|
||||
|
||||
expectedResult, _ := json.Marshal(reporting.FailureView{
|
||||
Message: message,
|
||||
Expected: fmt.Sprintf("%+v", thing1),
|
||||
Actual: fmt.Sprintf("%+v", thing2),
|
||||
})
|
||||
|
||||
if actualResult != string(expectedResult) {
|
||||
t.Errorf("\nExpected: %s\nActual: %s", string(expectedResult), actualResult)
|
||||
}
|
||||
|
||||
actualResult = serializer.serializeDetailed(thing1, thing2, message)
|
||||
expectedResult, _ = json.Marshal(reporting.FailureView{
|
||||
Message: message,
|
||||
Expected: fmt.Sprintf("%#v", thing1),
|
||||
Actual: fmt.Sprintf("%#v", thing2),
|
||||
})
|
||||
if actualResult != string(expectedResult) {
|
||||
t.Errorf("\nExpected: %s\nActual: %s", string(expectedResult), actualResult)
|
||||
}
|
||||
}
|
||||
Generated
Vendored
-102
@@ -1,102 +0,0 @@
|
||||
package assertions
|
||||
|
||||
import "testing"
|
||||
|
||||
func TestShouldStartWith(t *testing.T) {
|
||||
serializer = newFakeSerializer()
|
||||
|
||||
fail(t, so("", ShouldStartWith), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so("", ShouldStartWith, "asdf", "asdf"), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
|
||||
pass(t, so("", ShouldStartWith, ""))
|
||||
fail(t, so("", ShouldStartWith, "x"), "x||Expected '' to start with 'x' (but it didn't)!")
|
||||
pass(t, so("abc", ShouldStartWith, "abc"))
|
||||
fail(t, so("abc", ShouldStartWith, "abcd"), "abcd|abc|Expected 'abc' to start with 'abcd' (but it didn't)!")
|
||||
|
||||
pass(t, so("superman", ShouldStartWith, "super"))
|
||||
fail(t, so("superman", ShouldStartWith, "bat"), "bat|sup...|Expected 'superman' to start with 'bat' (but it didn't)!")
|
||||
fail(t, so("superman", ShouldStartWith, "man"), "man|sup...|Expected 'superman' to start with 'man' (but it didn't)!")
|
||||
|
||||
fail(t, so(1, ShouldStartWith, 2), "Both arguments to this assertion must be strings (you provided int and int).")
|
||||
}
|
||||
|
||||
func TestShouldNotStartWith(t *testing.T) {
|
||||
fail(t, so("", ShouldNotStartWith), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so("", ShouldNotStartWith, "asdf", "asdf"), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
|
||||
fail(t, so("", ShouldNotStartWith, ""), "Expected '<empty>' NOT to start with '<empty>' (but it did)!")
|
||||
fail(t, so("superman", ShouldNotStartWith, "super"), "Expected 'superman' NOT to start with 'super' (but it did)!")
|
||||
pass(t, so("superman", ShouldNotStartWith, "bat"))
|
||||
pass(t, so("superman", ShouldNotStartWith, "man"))
|
||||
|
||||
fail(t, so(1, ShouldNotStartWith, 2), "Both arguments to this assertion must be strings (you provided int and int).")
|
||||
}
|
||||
|
||||
func TestShouldEndWith(t *testing.T) {
|
||||
serializer = newFakeSerializer()
|
||||
|
||||
fail(t, so("", ShouldEndWith), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so("", ShouldEndWith, "", ""), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
|
||||
pass(t, so("", ShouldEndWith, ""))
|
||||
fail(t, so("", ShouldEndWith, "z"), "z||Expected '' to end with 'z' (but it didn't)!")
|
||||
pass(t, so("xyz", ShouldEndWith, "xyz"))
|
||||
fail(t, so("xyz", ShouldEndWith, "wxyz"), "wxyz|xyz|Expected 'xyz' to end with 'wxyz' (but it didn't)!")
|
||||
|
||||
pass(t, so("superman", ShouldEndWith, "man"))
|
||||
fail(t, so("superman", ShouldEndWith, "super"), "super|...erman|Expected 'superman' to end with 'super' (but it didn't)!")
|
||||
fail(t, so("superman", ShouldEndWith, "blah"), "blah|...rman|Expected 'superman' to end with 'blah' (but it didn't)!")
|
||||
|
||||
fail(t, so(1, ShouldEndWith, 2), "Both arguments to this assertion must be strings (you provided int and int).")
|
||||
}
|
||||
|
||||
func TestShouldNotEndWith(t *testing.T) {
|
||||
fail(t, so("", ShouldNotEndWith), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so("", ShouldNotEndWith, "", ""), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
|
||||
fail(t, so("", ShouldNotEndWith, ""), "Expected '<empty>' NOT to end with '<empty>' (but it did)!")
|
||||
fail(t, so("superman", ShouldNotEndWith, "man"), "Expected 'superman' NOT to end with 'man' (but it did)!")
|
||||
pass(t, so("superman", ShouldNotEndWith, "super"))
|
||||
|
||||
fail(t, so(1, ShouldNotEndWith, 2), "Both arguments to this assertion must be strings (you provided int and int).")
|
||||
}
|
||||
|
||||
func TestShouldContainSubstring(t *testing.T) {
|
||||
serializer = newFakeSerializer()
|
||||
|
||||
fail(t, so("asdf", ShouldContainSubstring), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so("asdf", ShouldContainSubstring, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(123, ShouldContainSubstring, 23), "Both arguments to this assertion must be strings (you provided int and int).")
|
||||
|
||||
pass(t, so("asdf", ShouldContainSubstring, "sd"))
|
||||
fail(t, so("qwer", ShouldContainSubstring, "sd"), "sd|qwer|Expected 'qwer' to contain substring 'sd' (but it didn't)!")
|
||||
}
|
||||
|
||||
func TestShouldNotContainSubstring(t *testing.T) {
|
||||
fail(t, so("asdf", ShouldNotContainSubstring), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so("asdf", ShouldNotContainSubstring, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(123, ShouldNotContainSubstring, 23), "Both arguments to this assertion must be strings (you provided int and int).")
|
||||
|
||||
pass(t, so("qwer", ShouldNotContainSubstring, "sd"))
|
||||
fail(t, so("asdf", ShouldNotContainSubstring, "sd"), "Expected 'asdf' NOT to contain substring 'sd' (but it didn't)!")
|
||||
}
|
||||
|
||||
func TestShouldBeBlank(t *testing.T) {
|
||||
serializer = newFakeSerializer()
|
||||
|
||||
fail(t, so("", ShouldBeBlank, "adsf"), "This assertion requires exactly 0 comparison values (you provided 1).")
|
||||
fail(t, so(1, ShouldBeBlank), "The argument to this assertion must be a string (you provided int).")
|
||||
|
||||
fail(t, so("asdf", ShouldBeBlank), "|asdf|Expected 'asdf' to be blank (but it wasn't)!")
|
||||
pass(t, so("", ShouldBeBlank))
|
||||
}
|
||||
|
||||
func TestShouldNotBeBlank(t *testing.T) {
|
||||
fail(t, so("", ShouldNotBeBlank, "adsf"), "This assertion requires exactly 0 comparison values (you provided 1).")
|
||||
fail(t, so(1, ShouldNotBeBlank), "The argument to this assertion must be a string (you provided int).")
|
||||
|
||||
fail(t, so("", ShouldNotBeBlank), "Expected value to NOT be blank (but it was)!")
|
||||
pass(t, so("asdf", ShouldNotBeBlank))
|
||||
}
|
||||
Generated
Vendored
-159
@@ -1,159 +0,0 @@
|
||||
package assertions
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"testing"
|
||||
"time"
|
||||
)
|
||||
|
||||
func TestShouldHappenBefore(t *testing.T) {
|
||||
fail(t, so(0, ShouldHappenBefore), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(0, ShouldHappenBefore, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(0, ShouldHappenBefore, 1), shouldUseTimes)
|
||||
fail(t, so(0, ShouldHappenBefore, time.Now()), shouldUseTimes)
|
||||
fail(t, so(time.Now(), ShouldHappenBefore, 0), shouldUseTimes)
|
||||
|
||||
fail(t, so(january3, ShouldHappenBefore, january1), fmt.Sprintf("Expected '%s' to happen before '%s' (it happened '48h0m0s' after)!", pretty(january3), pretty(january1)))
|
||||
fail(t, so(january3, ShouldHappenBefore, january3), fmt.Sprintf("Expected '%s' to happen before '%s' (it happened '0' after)!", pretty(january3), pretty(january3)))
|
||||
pass(t, so(january1, ShouldHappenBefore, january3))
|
||||
}
|
||||
|
||||
func TestShouldHappenOnOrBefore(t *testing.T) {
|
||||
fail(t, so(0, ShouldHappenOnOrBefore), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(0, ShouldHappenOnOrBefore, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(0, ShouldHappenOnOrBefore, 1), shouldUseTimes)
|
||||
fail(t, so(0, ShouldHappenOnOrBefore, time.Now()), shouldUseTimes)
|
||||
fail(t, so(time.Now(), ShouldHappenOnOrBefore, 0), shouldUseTimes)
|
||||
|
||||
fail(t, so(january3, ShouldHappenOnOrBefore, january1), fmt.Sprintf("Expected '%s' to happen before '%s' (it happened '48h0m0s' after)!", pretty(january3), pretty(january1)))
|
||||
pass(t, so(january3, ShouldHappenOnOrBefore, january3))
|
||||
pass(t, so(january1, ShouldHappenOnOrBefore, january3))
|
||||
}
|
||||
|
||||
func TestShouldHappenAfter(t *testing.T) {
|
||||
fail(t, so(0, ShouldHappenAfter), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(0, ShouldHappenAfter, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(0, ShouldHappenAfter, 1), shouldUseTimes)
|
||||
fail(t, so(0, ShouldHappenAfter, time.Now()), shouldUseTimes)
|
||||
fail(t, so(time.Now(), ShouldHappenAfter, 0), shouldUseTimes)
|
||||
|
||||
fail(t, so(january1, ShouldHappenAfter, january2), fmt.Sprintf("Expected '%s' to happen after '%s' (it happened '24h0m0s' before)!", pretty(january1), pretty(january2)))
|
||||
fail(t, so(january1, ShouldHappenAfter, january1), fmt.Sprintf("Expected '%s' to happen after '%s' (it happened '0' before)!", pretty(january1), pretty(january1)))
|
||||
pass(t, so(january3, ShouldHappenAfter, january1))
|
||||
}
|
||||
|
||||
func TestShouldHappenOnOrAfter(t *testing.T) {
|
||||
fail(t, so(0, ShouldHappenOnOrAfter), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(0, ShouldHappenOnOrAfter, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(0, ShouldHappenOnOrAfter, 1), shouldUseTimes)
|
||||
fail(t, so(0, ShouldHappenOnOrAfter, time.Now()), shouldUseTimes)
|
||||
fail(t, so(time.Now(), ShouldHappenOnOrAfter, 0), shouldUseTimes)
|
||||
|
||||
fail(t, so(january1, ShouldHappenOnOrAfter, january2), fmt.Sprintf("Expected '%s' to happen after '%s' (it happened '24h0m0s' before)!", pretty(january1), pretty(january2)))
|
||||
pass(t, so(january1, ShouldHappenOnOrAfter, january1))
|
||||
pass(t, so(january3, ShouldHappenOnOrAfter, january1))
|
||||
}
|
||||
|
||||
func TestShouldHappenBetween(t *testing.T) {
|
||||
fail(t, so(0, ShouldHappenBetween), "This assertion requires exactly 2 comparison values (you provided 0).")
|
||||
fail(t, so(0, ShouldHappenBetween, 1, 2, 3), "This assertion requires exactly 2 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(0, ShouldHappenBetween, 1, 2), shouldUseTimes)
|
||||
fail(t, so(0, ShouldHappenBetween, time.Now(), time.Now()), shouldUseTimes)
|
||||
fail(t, so(time.Now(), ShouldHappenBetween, 0, time.Now()), shouldUseTimes)
|
||||
fail(t, so(time.Now(), ShouldHappenBetween, time.Now(), 9), shouldUseTimes)
|
||||
|
||||
fail(t, so(january1, ShouldHappenBetween, january2, january4), fmt.Sprintf("Expected '%s' to happen between '%s' and '%s' (it happened '24h0m0s' outside threshold)!", pretty(january1), pretty(january2), pretty(january4)))
|
||||
fail(t, so(january2, ShouldHappenBetween, january2, january4), fmt.Sprintf("Expected '%s' to happen between '%s' and '%s' (it happened '0' outside threshold)!", pretty(january2), pretty(january2), pretty(january4)))
|
||||
pass(t, so(january3, ShouldHappenBetween, january2, january4))
|
||||
fail(t, so(january4, ShouldHappenBetween, january2, january4), fmt.Sprintf("Expected '%s' to happen between '%s' and '%s' (it happened '0' outside threshold)!", pretty(january4), pretty(january2), pretty(january4)))
|
||||
fail(t, so(january5, ShouldHappenBetween, january2, january4), fmt.Sprintf("Expected '%s' to happen between '%s' and '%s' (it happened '24h0m0s' outside threshold)!", pretty(january5), pretty(january2), pretty(january4)))
|
||||
}
|
||||
|
||||
func TestShouldHappenOnOrBetween(t *testing.T) {
|
||||
fail(t, so(0, ShouldHappenOnOrBetween), "This assertion requires exactly 2 comparison values (you provided 0).")
|
||||
fail(t, so(0, ShouldHappenOnOrBetween, 1, 2, 3), "This assertion requires exactly 2 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(0, ShouldHappenOnOrBetween, 1, time.Now()), shouldUseTimes)
|
||||
fail(t, so(0, ShouldHappenOnOrBetween, time.Now(), 1), shouldUseTimes)
|
||||
fail(t, so(time.Now(), ShouldHappenOnOrBetween, 0, 1), shouldUseTimes)
|
||||
|
||||
fail(t, so(january1, ShouldHappenOnOrBetween, january2, january4), fmt.Sprintf("Expected '%s' to happen between '%s' and '%s' (it happened '24h0m0s' outside threshold)!", pretty(january1), pretty(january2), pretty(january4)))
|
||||
pass(t, so(january2, ShouldHappenOnOrBetween, january2, january4))
|
||||
pass(t, so(january3, ShouldHappenOnOrBetween, january2, january4))
|
||||
pass(t, so(january4, ShouldHappenOnOrBetween, january2, january4))
|
||||
fail(t, so(january5, ShouldHappenOnOrBetween, january2, january4), fmt.Sprintf("Expected '%s' to happen between '%s' and '%s' (it happened '24h0m0s' outside threshold)!", pretty(january5), pretty(january2), pretty(january4)))
|
||||
}
|
||||
|
||||
func TestShouldNotHappenOnOrBetween(t *testing.T) {
|
||||
fail(t, so(0, ShouldNotHappenOnOrBetween), "This assertion requires exactly 2 comparison values (you provided 0).")
|
||||
fail(t, so(0, ShouldNotHappenOnOrBetween, 1, 2, 3), "This assertion requires exactly 2 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(0, ShouldNotHappenOnOrBetween, 1, time.Now()), shouldUseTimes)
|
||||
fail(t, so(0, ShouldNotHappenOnOrBetween, time.Now(), 1), shouldUseTimes)
|
||||
fail(t, so(time.Now(), ShouldNotHappenOnOrBetween, 0, 1), shouldUseTimes)
|
||||
|
||||
pass(t, so(january1, ShouldNotHappenOnOrBetween, january2, january4))
|
||||
fail(t, so(january2, ShouldNotHappenOnOrBetween, january2, january4), fmt.Sprintf("Expected '%s' to NOT happen on or between '%s' and '%s' (but it did)!", pretty(january2), pretty(january2), pretty(january4)))
|
||||
fail(t, so(january3, ShouldNotHappenOnOrBetween, january2, january4), fmt.Sprintf("Expected '%s' to NOT happen on or between '%s' and '%s' (but it did)!", pretty(january3), pretty(january2), pretty(january4)))
|
||||
fail(t, so(january4, ShouldNotHappenOnOrBetween, january2, january4), fmt.Sprintf("Expected '%s' to NOT happen on or between '%s' and '%s' (but it did)!", pretty(january4), pretty(january2), pretty(january4)))
|
||||
pass(t, so(january5, ShouldNotHappenOnOrBetween, january2, january4))
|
||||
}
|
||||
|
||||
func TestShouldHappenWithin(t *testing.T) {
|
||||
fail(t, so(0, ShouldHappenWithin), "This assertion requires exactly 2 comparison values (you provided 0).")
|
||||
fail(t, so(0, ShouldHappenWithin, 1, 2, 3), "This assertion requires exactly 2 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(0, ShouldHappenWithin, 1, 2), shouldUseDurationAndTime)
|
||||
fail(t, so(0, ShouldHappenWithin, oneDay, time.Now()), shouldUseDurationAndTime)
|
||||
fail(t, so(time.Now(), ShouldHappenWithin, 0, time.Now()), shouldUseDurationAndTime)
|
||||
|
||||
fail(t, so(january1, ShouldHappenWithin, oneDay, january3), fmt.Sprintf("Expected '%s' to happen between '%s' and '%s' (it happened '24h0m0s' outside threshold)!", pretty(january1), pretty(january2), pretty(january4)))
|
||||
pass(t, so(january2, ShouldHappenWithin, oneDay, january3))
|
||||
pass(t, so(january3, ShouldHappenWithin, oneDay, january3))
|
||||
pass(t, so(january4, ShouldHappenWithin, oneDay, january3))
|
||||
fail(t, so(january5, ShouldHappenWithin, oneDay, january3), fmt.Sprintf("Expected '%s' to happen between '%s' and '%s' (it happened '24h0m0s' outside threshold)!", pretty(january5), pretty(january2), pretty(january4)))
|
||||
}
|
||||
|
||||
func TestShouldNotHappenWithin(t *testing.T) {
|
||||
fail(t, so(0, ShouldNotHappenWithin), "This assertion requires exactly 2 comparison values (you provided 0).")
|
||||
fail(t, so(0, ShouldNotHappenWithin, 1, 2, 3), "This assertion requires exactly 2 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(0, ShouldNotHappenWithin, 1, 2), shouldUseDurationAndTime)
|
||||
fail(t, so(0, ShouldNotHappenWithin, oneDay, time.Now()), shouldUseDurationAndTime)
|
||||
fail(t, so(time.Now(), ShouldNotHappenWithin, 0, time.Now()), shouldUseDurationAndTime)
|
||||
|
||||
pass(t, so(january1, ShouldNotHappenWithin, oneDay, january3))
|
||||
fail(t, so(january2, ShouldNotHappenWithin, oneDay, january3), fmt.Sprintf("Expected '%s' to NOT happen on or between '%s' and '%s' (but it did)!", pretty(january2), pretty(january2), pretty(january4)))
|
||||
fail(t, so(january3, ShouldNotHappenWithin, oneDay, january3), fmt.Sprintf("Expected '%s' to NOT happen on or between '%s' and '%s' (but it did)!", pretty(january3), pretty(january2), pretty(january4)))
|
||||
fail(t, so(january4, ShouldNotHappenWithin, oneDay, january3), fmt.Sprintf("Expected '%s' to NOT happen on or between '%s' and '%s' (but it did)!", pretty(january4), pretty(january2), pretty(january4)))
|
||||
pass(t, so(january5, ShouldNotHappenWithin, oneDay, january3))
|
||||
}
|
||||
|
||||
func TestShouldBeChronological(t *testing.T) {
|
||||
fail(t, so(0, ShouldBeChronological, 1, 2, 3), "This assertion requires exactly 0 comparison values (you provided 3).")
|
||||
fail(t, so(0, ShouldBeChronological), shouldUseTimeSlice)
|
||||
fail(t, so([]time.Time{january5, january1}, ShouldBeChronological),
|
||||
"The 'Time' at index [1] should have happened after the previous one (but it didn't!):\n [0]: 2013-01-05 00:00:00 +0000 UTC\n [1]: 2013-01-01 00:00:00 +0000 UTC (see, it happened before!)")
|
||||
|
||||
pass(t, so([]time.Time{january1, january2, january3, january4, january5}, ShouldBeChronological))
|
||||
}
|
||||
|
||||
const layout = "2006-01-02 15:04"
|
||||
|
||||
var january1, _ = time.Parse(layout, "2013-01-01 00:00")
|
||||
var january2, _ = time.Parse(layout, "2013-01-02 00:00")
|
||||
var january3, _ = time.Parse(layout, "2013-01-03 00:00")
|
||||
var january4, _ = time.Parse(layout, "2013-01-04 00:00")
|
||||
var january5, _ = time.Parse(layout, "2013-01-05 00:00")
|
||||
|
||||
var oneDay, _ = time.ParseDuration("24h0m0s")
|
||||
var twoDays, _ = time.ParseDuration("48h0m0s")
|
||||
|
||||
func pretty(t time.Time) string {
|
||||
return fmt.Sprintf("%v", t)
|
||||
}
|
||||
Generated
Vendored
-76
@@ -1,76 +0,0 @@
|
||||
package assertions
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"io"
|
||||
"net/http"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func TestShouldHaveSameTypeAs(t *testing.T) {
|
||||
serializer = newFakeSerializer()
|
||||
|
||||
fail(t, so(1, ShouldHaveSameTypeAs), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(1, ShouldHaveSameTypeAs, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(nil, ShouldHaveSameTypeAs, 0), "int|<nil>|Expected '<nil>' to be: 'int' (but was: '<nil>')!")
|
||||
fail(t, so(1, ShouldHaveSameTypeAs, "asdf"), "string|int|Expected '1' to be: 'string' (but was: 'int')!")
|
||||
|
||||
pass(t, so(1, ShouldHaveSameTypeAs, 0))
|
||||
pass(t, so(nil, ShouldHaveSameTypeAs, nil))
|
||||
}
|
||||
|
||||
func TestShouldNotHaveSameTypeAs(t *testing.T) {
|
||||
fail(t, so(1, ShouldNotHaveSameTypeAs), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(1, ShouldNotHaveSameTypeAs, 1, 2, 3), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(1, ShouldNotHaveSameTypeAs, 0), "Expected '1' to NOT be: 'int' (but it was)!")
|
||||
fail(t, so(nil, ShouldNotHaveSameTypeAs, nil), "Expected '<nil>' to NOT be: '<nil>' (but it was)!")
|
||||
|
||||
pass(t, so(nil, ShouldNotHaveSameTypeAs, 0))
|
||||
pass(t, so(1, ShouldNotHaveSameTypeAs, "asdf"))
|
||||
}
|
||||
|
||||
func TestShouldImplement(t *testing.T) {
|
||||
var ioReader *io.Reader = nil
|
||||
var response http.Response = http.Response{}
|
||||
var responsePtr *http.Response = new(http.Response)
|
||||
var reader = bytes.NewBufferString("")
|
||||
|
||||
fail(t, so(reader, ShouldImplement), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(reader, ShouldImplement, ioReader, ioReader), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
fail(t, so(reader, ShouldImplement, ioReader, ioReader, ioReader), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(reader, ShouldImplement, "foo"), shouldCompareWithInterfacePointer)
|
||||
fail(t, so(reader, ShouldImplement, 1), shouldCompareWithInterfacePointer)
|
||||
fail(t, so(reader, ShouldImplement, nil), shouldCompareWithInterfacePointer)
|
||||
|
||||
fail(t, so(nil, ShouldImplement, ioReader), shouldNotBeNilActual)
|
||||
fail(t, so(1, ShouldImplement, ioReader), "Expected: 'io.Reader interface support'\nActual: '*int' does not implement the interface!")
|
||||
|
||||
fail(t, so(response, ShouldImplement, ioReader), "Expected: 'io.Reader interface support'\nActual: '*http.Response' does not implement the interface!")
|
||||
fail(t, so(responsePtr, ShouldImplement, ioReader), "Expected: 'io.Reader interface support'\nActual: '*http.Response' does not implement the interface!")
|
||||
pass(t, so(reader, ShouldImplement, ioReader))
|
||||
pass(t, so(reader, ShouldImplement, (*io.Reader)(nil)))
|
||||
}
|
||||
|
||||
func TestShouldNotImplement(t *testing.T) {
|
||||
var ioReader *io.Reader = nil
|
||||
var response http.Response = http.Response{}
|
||||
var responsePtr *http.Response = new(http.Response)
|
||||
var reader io.Reader = bytes.NewBufferString("")
|
||||
|
||||
fail(t, so(reader, ShouldNotImplement), "This assertion requires exactly 1 comparison values (you provided 0).")
|
||||
fail(t, so(reader, ShouldNotImplement, ioReader, ioReader), "This assertion requires exactly 1 comparison values (you provided 2).")
|
||||
fail(t, so(reader, ShouldNotImplement, ioReader, ioReader, ioReader), "This assertion requires exactly 1 comparison values (you provided 3).")
|
||||
|
||||
fail(t, so(reader, ShouldNotImplement, "foo"), shouldCompareWithInterfacePointer)
|
||||
fail(t, so(reader, ShouldNotImplement, 1), shouldCompareWithInterfacePointer)
|
||||
fail(t, so(reader, ShouldNotImplement, nil), shouldCompareWithInterfacePointer)
|
||||
|
||||
fail(t, so(reader, ShouldNotImplement, ioReader), "Expected '*bytes.Buffer'\nto NOT implement 'io.Reader' (but it did)!")
|
||||
fail(t, so(nil, ShouldNotImplement, ioReader), shouldNotBeNilActual)
|
||||
pass(t, so(1, ShouldNotImplement, ioReader))
|
||||
pass(t, so(response, ShouldNotImplement, ioReader))
|
||||
pass(t, so(responsePtr, ShouldNotImplement, ioReader))
|
||||
}
|
||||
Generated
Vendored
-75
@@ -1,75 +0,0 @@
|
||||
package assertions
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"path"
|
||||
"runtime"
|
||||
"strings"
|
||||
"testing"
|
||||
)
|
||||
|
||||
func pass(t *testing.T, result string) {
|
||||
if result != success {
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
base := path.Base(file)
|
||||
t.Errorf("Expectation should have passed but failed (see %s: line %d): '%s'", base, line, result)
|
||||
}
|
||||
}
|
||||
|
||||
func fail(t *testing.T, actual string, expected string) {
|
||||
actual = format(actual)
|
||||
expected = format(expected)
|
||||
|
||||
if actual != expected {
|
||||
if actual == "" {
|
||||
actual = "(empty)"
|
||||
}
|
||||
_, file, line, _ := runtime.Caller(1)
|
||||
base := path.Base(file)
|
||||
t.Errorf("Expectation should have failed but passed (see %s: line %d). \nExpected: %s\nActual: %s\n",
|
||||
base, line, expected, actual)
|
||||
}
|
||||
}
|
||||
func format(message string) string {
|
||||
message = strings.Replace(message, "\n", " ", -1)
|
||||
for strings.Contains(message, " ") {
|
||||
message = strings.Replace(message, " ", " ", -1)
|
||||
}
|
||||
return message
|
||||
}
|
||||
|
||||
type Thing1 struct {
|
||||
a string
|
||||
}
|
||||
type Thing2 struct {
|
||||
a string
|
||||
}
|
||||
|
||||
type Thinger interface {
|
||||
Hi()
|
||||
}
|
||||
|
||||
type Thing struct{}
|
||||
|
||||
func (self *Thing) Hi() {}
|
||||
|
||||
type IntAlias int
|
||||
type StringAlias string
|
||||
type StringSliceAlias []string
|
||||
type StringStringMapAlias map[string]string
|
||||
|
||||
/******** FakeSerialzier ********/
|
||||
|
||||
type fakeSerializer struct{}
|
||||
|
||||
func (self *fakeSerializer) serialize(expected, actual interface{}, message string) string {
|
||||
return fmt.Sprintf("%v|%v|%s", expected, actual, message)
|
||||
}
|
||||
|
||||
func (self *fakeSerializer) serializeDetailed(expected, actual interface{}, message string) string {
|
||||
return fmt.Sprintf("%v|%v|%s", expected, actual, message)
|
||||
}
|
||||
|
||||
func newFakeSerializer() *fakeSerializer {
|
||||
return new(fakeSerializer)
|
||||
}
|
||||
@@ -355,6 +355,25 @@ global_api_key = -1
|
||||
# global limit on number of logged in users.
|
||||
global_session = -1
|
||||
|
||||
#################################### Alerting ######################################
|
||||
# docs about alerting can be found in /docs/sources/alerting/
|
||||
# __.-/|
|
||||
# \`o_O'
|
||||
# =( )= +----------------------------+
|
||||
# U| | Alerting is still in alpha |
|
||||
# /\ /\ / | +----------------------------+
|
||||
# ) /^\) ^\/ _)\ |
|
||||
# ) /^\/ _) \ |
|
||||
# ) _ / / _) \___|_
|
||||
# /\ )/\/ || | )_)\___,|))
|
||||
# < > |(,,) )__) |
|
||||
# || / \)___)\
|
||||
# | \____( )___) )____
|
||||
# \______(_______;;;)__;;;)
|
||||
|
||||
[alerting]
|
||||
enabled = false
|
||||
|
||||
#################################### Internal Grafana Metrics ##########################
|
||||
# Metrics available at HTTP API Url /api/metrics
|
||||
[metrics]
|
||||
@@ -369,3 +388,18 @@ prefix = prod.grafana.%(instance_name)s.
|
||||
|
||||
[grafana_net]
|
||||
url = https://grafana.net
|
||||
|
||||
#################################### External image storage ##########################
|
||||
[external_image_storage]
|
||||
# You can choose between (s3, webdav or internal)
|
||||
provider = s3
|
||||
|
||||
[external_image_storage.s3]
|
||||
bucket_url =
|
||||
access_key =
|
||||
secret_key =
|
||||
|
||||
[external_image_storage.webdav]
|
||||
url =
|
||||
username =
|
||||
password =
|
||||
|
||||
@@ -301,6 +301,25 @@ check_for_updates = true
|
||||
;enabled = false
|
||||
;path = /var/lib/grafana/dashboards
|
||||
|
||||
#################################### Alerting ######################################
|
||||
# docs about alerting can be found in /docs/sources/alerting/
|
||||
# __.-/|
|
||||
# \`o_O'
|
||||
# =( )= +----------------------------+
|
||||
# U| | Alerting is still in alpha |
|
||||
# /\ /\ / | +----------------------------+
|
||||
# ) /^\) ^\/ _)\ |
|
||||
# ) /^\/ _) \ |
|
||||
# ) _ / / _) \___|_
|
||||
# /\ )/\/ || | )_)\___,|))
|
||||
# < > |(,,) )__) |
|
||||
# || / \)___)\
|
||||
# | \____( )___) )____
|
||||
# \______(_______;;;)__;;;)
|
||||
|
||||
[alerting]
|
||||
enabled = false
|
||||
|
||||
#################################### Internal Grafana Metrics ##########################
|
||||
# Metrics available at HTTP API Url /api/metrics
|
||||
[metrics]
|
||||
@@ -320,3 +339,19 @@ check_for_updates = true
|
||||
# Url used to to import dashboards directly from Grafana.net
|
||||
[grafana_net]
|
||||
;url = https://grafana.net
|
||||
|
||||
#################################### External image storage ##########################
|
||||
[external_image_storage]
|
||||
# Used for uploading images to public servers so they can be included in slack/email messages.
|
||||
# you can choose between (s3, webdav or internal)
|
||||
;provider = s3
|
||||
|
||||
[external_image_storage.s3]
|
||||
;bucket_url =
|
||||
;access_key =
|
||||
;secret_key =
|
||||
|
||||
[external_image_storage.webdav]
|
||||
;url =
|
||||
;username =
|
||||
;password =
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user