<commit_before>package zapdriver

import (
	"runtime"
	"sync/atomic"
	"testing"

	"github.com/stretchr/testify/require"

	"github.com/stretchr/testify/assert"
	"go.uber.org/zap"
	"go.uber.org/zap/zapcore"
	"go.uber.org/zap/zaptest/observer"
)

func TestWithLabels(t *testing.T) {
	fields := []zap.Field{
		zap.String("hello", "world"),
		Label("one", "value"),
		Label("two", "value"),
	}

	labels := newLabels()
	labels.store = map[string]string{"one": "value", "two": "value"}

	want := []zap.Field{
		zap.String("hello", "world"),
		zap.Object("labels", labels),
	}

	assert.Equal(t, want, (&core{}).withLabels(fields))
}

func TestExtractLabels(t *testing.T) {
	var lbls *labels
	c := &core{zapcore.NewNopCore(), newLabels(), newLabels()}

	fields := []zap.Field{
		zap.String("hello", "world"),
		Label("one", "world"),
		Label("two", "worlds"),
	}

	lbls, fields = c.extractLabels(fields)

	require.Len(t, lbls.store, 2)

	lbls.mutex.RLock()
	assert.Equal(t, "world", lbls.store["one"])
	assert.Equal(t, "worlds", lbls.store["two"])
	lbls.mutex.RUnlock()

	require.Len(t, fields, 1)
	assert.Equal(t, zap.String("hello", "world"), fields[0])
}

func TestWithSourceLocation(t *testing.T) {
	fields := []zap.Field{zap.String("hello", "world")}
	pc, file, line, ok := runtime.Caller(0)
	ent := zapcore.Entry{Caller: zapcore.NewEntryCaller(pc, file, line, ok)}

	want := []zap.Field{
		zap.String("hello", "world"),
		zap.Object(sourceKey, newSource(pc, file, line, ok)),
	}

	assert.Equal(t, want, (&core{}).withSourceLocation(ent, fields))
}

func TestWithSourceLocation_DoesNotOverwrite(t *testing.T) {
	fields := []zap.Field{zap.String(sourceKey, "world")}
	pc, file, line, ok := runtime.Caller(0)
	ent := zapcore.Entry{Caller: zapcore.NewEntryCaller(pc, file, line, ok)}

	want := []zap.Field{
		zap.String(sourceKey, "world"),
	}

	assert.Equal(t, want, (&core{}).withSourceLocation(ent, fields))
}

func TestWithSourceLocation_OnlyWhenDefined(t *testing.T) {
	fields := []zap.Field{zap.String("hello", "world")}
	pc, file, line, ok := runtime.Caller(0)
	ent := zapcore.Entry{Caller: zapcore.NewEntryCaller(pc, file, line, ok)}
	ent.Caller.Defined = false

	want := []zap.Field{
		zap.String("hello", "world"),
	}

	assert.Equal(t, want, (&core{}).withSourceLocation(ent, fields))
}

func TestWrite(t *testing.T) {
	temp := newLabels()
	temp.store = map[string]string{"one": "1", "two": "2"}

	debugcore, logs := observer.New(zapcore.DebugLevel)
	core := &core{debugcore, newLabels(), temp}

	fields := []zap.Field{
		zap.String("hello", "world"),
		Label("one", "value"),
		Label("two", "value"),
	}

	err := core.Write(zapcore.Entry{}, fields)
	require.NoError(t, err)

	assert.NotNil(t, logs.All()[0].ContextMap()["labels"])
}

func TestWriteConcurrent(t *testing.T) {
	temp := newLabels()
	temp.store = map[string]string{"one": "1", "two": "2"}
	goRoutines := 8
	counter := int32(10000)

	debugcore, logs := observer.New(zapcore.DebugLevel)
	core := &core{debugcore, newLabels(), temp}

	fields := []zap.Field{
		zap.String("hello", "world"),
		Label("one", "value"),
		Label("two", "value"),
	}

	for i := 0; i < goRoutines; i++ {
		go func() {
			for atomic.AddInt32(&counter, -1) > 0 {
				err := core.Write(zapcore.Entry{}, fields)
				require.NoError(t, err)
			}
		}()
	}

	assert.NotNil(t, logs.All()[0].ContextMap()["labels"])
}

func TestWithAndWrite(t *testing.T) {
	debugcore, logs := observer.New(zapcore.DebugLevel)
	core := zapcore.Core(&core{debugcore, newLabels(), newLabels()})

	core = core.With([]zapcore.Field{Label("one", "world")})
	err := core.Write(zapcore.Entry{}, []zapcore.Field{Label("two", "worlds")})
	require.NoError(t, err)

	labels := logs.All()[0].ContextMap()["labels"].(map[string]interface{})

	assert.Equal(t, "world", labels["one"])
	assert.Equal(t, "worlds", labels["two"])
}

func TestWithAndWrite_MultipleEntries(t *testing.T) {
	debugcore, logs := observer.New(zapcore.DebugLevel)
	core := zapcore.Core(&core{debugcore, newLabels(), newLabels()})

	core = core.With([]zapcore.Field{Label("one", "world")})
	err := core.Write(zapcore.Entry{}, []zapcore.Field{Label("two", "worlds")})
	require.NoError(t, err)

	labels := logs.All()[0].ContextMap()["labels"].(map[string]interface{})
	require.Len(t, labels, 2)

	assert.Equal(t, "world", labels["one"])
	assert.Equal(t, "worlds", labels["two"])

	err = core.Write(zapcore.Entry{}, []zapcore.Field{Label("three", "worlds")})
	require.NoError(t, err)

	labels = logs.All()[1].ContextMap()["labels"].(map[string]interface{})
	require.Len(t, labels, 2)

	assert.Equal(t, "world", labels["one"])
	assert.Equal(t, "worlds", labels["three"])
}

func TestAllLabels(t *testing.T) {
	perm := newLabels()
	perm.store = map[string]string{"one": "1", "two": "2", "three": "3"}

	temp := newLabels()
	temp.store = map[string]string{"one": "ONE", "three": "THREE"}

	core := &core{zapcore.NewNopCore(), perm, temp}

	out := core.allLabels()
	require.Len(t, out.store, 3)

	out.mutex.RLock()
	assert.Equal(t, out.store["one"], "ONE")
	assert.Equal(t, out.store["two"], "2")
	assert.Equal(t, out.store["three"], "THREE")
	out.mutex.RUnlock()
}
<commit_msg>Add a wait group to wait for all concurrent calls to finish<commit_after>package zapdriver

import (
	"runtime"
	"sync"
	"sync/atomic"
	"testing"

	"github.com/stretchr/testify/require"

	"github.com/stretchr/testify/assert"
	"go.uber.org/zap"
	"go.uber.org/zap/zapcore"
	"go.uber.org/zap/zaptest/observer"
)

func TestWithLabels(t *testing.T) {
	fields := []zap.Field{
		zap.String("hello", "world"),
		Label("one", "value"),
		Label("two", "value"),
	}

	labels := newLabels()
	labels.store = map[string]string{"one": "value", "two": "value"}

	want := []zap.Field{
		zap.String("hello", "world"),
		zap.Object("labels", labels),
	}

	assert.Equal(t, want, (&core{}).withLabels(fields))
}

func TestExtractLabels(t *testing.T) {
	var lbls *labels
	c := &core{zapcore.NewNopCore(), newLabels(), newLabels()}

	fields := []zap.Field{
		zap.String("hello", "world"),
		Label("one", "world"),
		Label("two", "worlds"),
	}

	lbls, fields = c.extractLabels(fields)

	require.Len(t, lbls.store, 2)

	lbls.mutex.RLock()
	assert.Equal(t, "world", lbls.store["one"])
	assert.Equal(t, "worlds", lbls.store["two"])
	lbls.mutex.RUnlock()

	require.Len(t, fields, 1)
	assert.Equal(t, zap.String("hello", "world"), fields[0])
}

func TestWithSourceLocation(t *testing.T) {
	fields := []zap.Field{zap.String("hello", "world")}
	pc, file, line, ok := runtime.Caller(0)
	ent := zapcore.Entry{Caller: zapcore.NewEntryCaller(pc, file, line, ok)}

	want := []zap.Field{
		zap.String("hello", "world"),
		zap.Object(sourceKey, newSource(pc, file, line, ok)),
	}

	assert.Equal(t, want, (&core{}).withSourceLocation(ent, fields))
}

func TestWithSourceLocation_DoesNotOverwrite(t *testing.T) {
	fields := []zap.Field{zap.String(sourceKey, "world")}
	pc, file, line, ok := runtime.Caller(0)
	ent := zapcore.Entry{Caller: zapcore.NewEntryCaller(pc, file, line, ok)}

	want := []zap.Field{
		zap.String(sourceKey, "world"),
	}

	assert.Equal(t, want, (&core{}).withSourceLocation(ent, fields))
}

func TestWithSourceLocation_OnlyWhenDefined(t *testing.T) {
	fields := []zap.Field{zap.String("hello", "world")}
	pc, file, line, ok := runtime.Caller(0)
	ent := zapcore.Entry{Caller: zapcore.NewEntryCaller(pc, file, line, ok)}
	ent.Caller.Defined = false

	want := []zap.Field{
		zap.String("hello", "world"),
	}

	assert.Equal(t, want, (&core{}).withSourceLocation(ent, fields))
}

func TestWrite(t *testing.T) {
	temp := newLabels()
	temp.store = map[string]string{"one": "1", "two": "2"}

	debugcore, logs := observer.New(zapcore.DebugLevel)
	core := &core{debugcore, newLabels(), temp}

	fields := []zap.Field{
		zap.String("hello", "world"),
		Label("one", "value"),
		Label("two", "value"),
	}

	err := core.Write(zapcore.Entry{}, fields)
	require.NoError(t, err)

	assert.NotNil(t, logs.All()[0].ContextMap()["labels"])
}

func TestWriteConcurrent(t *testing.T) {
	temp := newLabels()
	temp.store = map[string]string{"one": "1", "two": "2"}
	goRoutines := 8
	counter := int32(10000)

	debugcore, logs := observer.New(zapcore.DebugLevel)
	core := &core{debugcore, newLabels(), temp}

	fields := []zap.Field{
		zap.String("hello", "world"),
		Label("one", "value"),
		Label("two", "value"),
	}

	var wg sync.WaitGroup
	wg.Add(goRoutines)
	for i := 0; i < goRoutines; i++ {
		go func() {
			defer wg.Done()
			for atomic.AddInt32(&counter, -1) > 0 {
				err := core.Write(zapcore.Entry{}, fields)
				require.NoError(t, err)
			}
		}()
	}
	wg.Wait()

	assert.NotNil(t, logs.All()[0].ContextMap()["labels"])
}

func TestWithAndWrite(t *testing.T) {
	debugcore, logs := observer.New(zapcore.DebugLevel)
	core := zapcore.Core(&core{debugcore, newLabels(), newLabels()})

	core = core.With([]zapcore.Field{Label("one", "world")})
	err := core.Write(zapcore.Entry{}, []zapcore.Field{Label("two", "worlds")})
	require.NoError(t, err)

	labels := logs.All()[0].ContextMap()["labels"].(map[string]interface{})

	assert.Equal(t, "world", labels["one"])
	assert.Equal(t, "worlds", labels["two"])
}

func TestWithAndWrite_MultipleEntries(t *testing.T) {
	debugcore, logs := observer.New(zapcore.DebugLevel)
	core := zapcore.Core(&core{debugcore, newLabels(), newLabels()})

	core = core.With([]zapcore.Field{Label("one", "world")})
	err := core.Write(zapcore.Entry{}, []zapcore.Field{Label("two", "worlds")})
	require.NoError(t, err)

	labels := logs.All()[0].ContextMap()["labels"].(map[string]interface{})
	require.Len(t, labels, 2)

	assert.Equal(t, "world", labels["one"])
	assert.Equal(t, "worlds", labels["two"])

	err = core.Write(zapcore.Entry{}, []zapcore.Field{Label("three", "worlds")})
	require.NoError(t, err)

	labels = logs.All()[1].ContextMap()["labels"].(map[string]interface{})
	require.Len(t, labels, 2)

	assert.Equal(t, "world", labels["one"])
	assert.Equal(t, "worlds", labels["three"])
}

func TestAllLabels(t *testing.T) {
	perm := newLabels()
	perm.store = map[string]string{"one": "1", "two": "2", "three": "3"}

	temp := newLabels()
	temp.store = map[string]string{"one": "ONE", "three": "THREE"}

	core := &core{zapcore.NewNopCore(), perm, temp}

	out := core.allLabels()
	require.Len(t, out.store, 3)

	out.mutex.RLock()
	assert.Equal(t, out.store["one"], "ONE")
	assert.Equal(t, out.store["two"], "2")
	assert.Equal(t, out.store["three"], "THREE")
	out.mutex.RUnlock()
}
<|endoftext|>


<commit_before>package editor

import (
	"github.com/gdamore/tcell"
	"github.com/rivo/tview"
	"log"
)

// MainView implements the main editor view.
type MainView struct {
	dataView map[string]*Dataview
	Lines    [][]Block
	*tview.Box
	*Edit
	offy, offx int
}

type Block struct {
	Rune  rune
	Style tcell.Style
}

// NewMainView returns a new main view primitive.
func NewMainView() *MainView {
	view := MainView{
		Box:   tview.NewBox().SetBorder(true),
		Lines: [][]Block{},
	}
	return &view
}

// Draw draws this primitive onto the screen.
func (m *MainView) Draw(screen tcell.Screen) {
	_, bg, _ := defaultStyle.Decompose()
	m.Box.SetBackgroundColor(bg).Draw(screen)
	dataview := m.dataView[m.curViewID]
	if dataview == nil {
		return
	}
	lines := dataview.Lines()
	m.Lines = [][]Block{}
	for y, line := range lines[m.offy:] {
		var blocks []Block
		m.Lines = append(m.Lines, blocks)
		for x, r := range line.Text {
			var style = defaultStyle
			if line.StyleIds[x] >= 2 {
				fg, _, _ := styles[line.StyleIds[x]].Decompose()
				style = style.Foreground(fg)
			}
			m.Lines[y] = append(m.Lines[y], Block{Rune: r, Style: style})
		}
	}

	for y, line := range m.Lines {
		for x, block := range line {
			m.draw(screen, x, y, block)
		}
	}

	// Draw cursors
	for y, line := range lines[m.offy:] {
		for _, cursor := range line.Cursors {
			content := m.getContent(screen, cursor, y)
			content.Style = content.Style.Reverse(true)
			m.draw(screen, cursor, y, content)
		}
	}
}

func (m *MainView) draw(screen tcell.Screen, x int, y int, b Block) {

	xMin, yMin, width, height := m.Box.GetInnerRect()
	x = xMin + x - m.offx
	y = yMin + y

	if x < xMin || y < yMin || x >= width+xMin || y >= height+yMin {
		return
	}
	screen.SetContent(x, y, b.Rune, nil, b.Style)
}

func (m *MainView) getContent(screen tcell.Screen, x int, y int) Block {

	xMin, yMin, width, height := m.Box.GetInnerRect()
	x = xMin + x - m.offx
	y = yMin + y

	if x < xMin || y < yMin || x >= width+xMin || y >= height+yMin {
		return Block{}
	}
	mainc, _, style, _ := screen.GetContent(x, y)
	return Block{Rune: mainc, Style: style}
}

func (m *MainView) MakeVisible(x, y int) {
	_, _, width, height := m.Box.GetInnerRect()
	log.Println(y, m.offy+height, y >= m.offy+height)
	if y >= m.offy+height {
		m.offy = y - (height - 1)
	}

	if y >= 0 && y < m.offy {
		m.offy = y
	}

	if x >= m.offx+width {
		m.offx = x - (width - 1)
	}
	if x >= 0 && x < m.offx {
		m.offx = x
	}
}

// InputHandler returns the handler for this primitive.
func (m *MainView) InputHandler() func(event *tcell.EventKey, setFocus func(p tview.Primitive)) {
	return m.WrapInputHandler(func(event *tcell.EventKey, setFocus func(p tview.Primitive)) {
		dataview := m.dataView[m.curViewID]
		ctrl := event.Modifiers()&tcell.ModCtrl != 0
		alt := event.Modifiers()&tcell.ModAlt != 0
		if !ctrl && !alt {
			switch event.Key() {
			case tcell.KeyUp:
				dataview.MoveUp()
			case tcell.KeyDown:
				dataview.MoveDown()
			case tcell.KeyLeft:
				dataview.MoveLeft()
			case tcell.KeyEnter:
				dataview.Newline()
			case tcell.KeyRight:
				dataview.MoveRight()
			case tcell.KeyRune:
				dataview.Insert(string(event.Rune()))
			case tcell.KeyTab:
				dataview.Tab()
			case tcell.KeyBS:
				dataview.DeleteForward()
			case tcell.KeyDEL:
				dataview.DeleteBackward()
			case tcell.KeyPgUp:
				dataview.ScrollPageUp()
			case tcell.KeyPgDn:
				dataview.ScrollPageDown()
			default:
				log.Println(event.Name())
			}
		}
		if ctrl && !alt {
			switch event.Key() {
			case tcell.KeyCtrlS:
				dataview.Save()
			case tcell.KeyCtrlQ:
				dataview.Save()
				dataview.Close()
				m.curViewID = ""
				m.focusFileselector()
			default:
				log.Println(event.Name())
			}
		}
		if !ctrl && alt {
			switch event.Name() {
			case "Alt+Rune[0]":
				m.focusFileselector()
			default:
				log.Println(event.Name())
			}
		}
		if ctrl && alt {
			switch event.Key() {

			default:
				log.Println(event.Name())
			}
		}
		//dataview.Save()
	})
}
<commit_msg>Paste and duplicate line<commit_after>package editor

import (
	"github.com/atotto/clipboard"
	"github.com/gdamore/tcell"
	"github.com/rivo/tview"
	"log"
)

// MainView implements the main editor view.
type MainView struct {
	dataView map[string]*Dataview
	Lines    [][]Block
	*tview.Box
	*Edit
	offy, offx int
}

type Block struct {
	Rune  rune
	Style tcell.Style
}

// NewMainView returns a new main view primitive.
func NewMainView() *MainView {
	view := MainView{
		Box:   tview.NewBox().SetBorder(true),
		Lines: [][]Block{},
	}
	return &view
}

// Draw draws this primitive onto the screen.
func (m *MainView) Draw(screen tcell.Screen) {
	_, bg, _ := defaultStyle.Decompose()
	m.Box.SetBackgroundColor(bg).Draw(screen)
	dataview := m.dataView[m.curViewID]
	if dataview == nil {
		return
	}
	lines := dataview.Lines()
	m.Lines = [][]Block{}
	for y, line := range lines[m.offy:] {
		var blocks []Block
		m.Lines = append(m.Lines, blocks)
		for x, r := range line.Text {
			var style = defaultStyle
			if line.StyleIds[x] >= 2 {
				fg, _, _ := styles[line.StyleIds[x]].Decompose()
				style = style.Foreground(fg)
			}
			m.Lines[y] = append(m.Lines[y], Block{Rune: r, Style: style})
		}
	}

	for y, line := range m.Lines {
		for x, block := range line {
			m.draw(screen, x, y, block)
		}
	}

	// Draw cursors
	for y, line := range lines[m.offy:] {
		for _, cursor := range line.Cursors {
			content := m.getContent(screen, cursor, y)
			content.Style = content.Style.Reverse(true)
			m.draw(screen, cursor, y, content)
		}
	}
}

func (m *MainView) draw(screen tcell.Screen, x int, y int, b Block) {

	xMin, yMin, width, height := m.Box.GetInnerRect()
	x = xMin + x - m.offx
	y = yMin + y

	if x < xMin || y < yMin || x >= width+xMin || y >= height+yMin {
		return
	}
	screen.SetContent(x, y, b.Rune, nil, b.Style)
}

func (m *MainView) getContent(screen tcell.Screen, x int, y int) Block {

	xMin, yMin, width, height := m.Box.GetInnerRect()
	x = xMin + x - m.offx
	y = yMin + y

	if x < xMin || y < yMin || x >= width+xMin || y >= height+yMin {
		return Block{}
	}
	mainc, _, style, _ := screen.GetContent(x, y)
	return Block{Rune: mainc, Style: style}
}

func (m *MainView) MakeVisible(x, y int) {
	_, _, width, height := m.Box.GetInnerRect()
	log.Println(y, m.offy+height, y >= m.offy+height)
	if y >= m.offy+height {
		m.offy = y - (height - 1)
	}

	if y >= 0 && y < m.offy {
		m.offy = y
	}

	if x >= m.offx+width {
		m.offx = x - (width - 1)
	}
	if x >= 0 && x < m.offx {
		m.offx = x
	}
}

// InputHandler returns the handler for this primitive.
func (m *MainView) InputHandler() func(event *tcell.EventKey, setFocus func(p tview.Primitive)) {
	return m.WrapInputHandler(func(event *tcell.EventKey, setFocus func(p tview.Primitive)) {
		dataview := m.dataView[m.curViewID]
		ctrl := event.Modifiers()&tcell.ModCtrl != 0
		alt := event.Modifiers()&tcell.ModAlt != 0
		if !ctrl && !alt {
			switch event.Key() {
			case tcell.KeyUp:
				dataview.MoveUp()
			case tcell.KeyDown:
				dataview.MoveDown()
			case tcell.KeyLeft:
				dataview.MoveLeft()
			case tcell.KeyEnter:
				dataview.Newline()
			case tcell.KeyRight:
				dataview.MoveRight()
			case tcell.KeyRune:
				dataview.Insert(string(event.Rune()))
			case tcell.KeyTab:
				dataview.Tab()
			case tcell.KeyBS:
				dataview.DeleteForward()
			case tcell.KeyDEL:
				dataview.DeleteBackward()
			case tcell.KeyPgUp:
				dataview.ScrollPageUp()
			case tcell.KeyPgDn:
				dataview.ScrollPageDown()
			default:
				log.Println(event.Name())
			}
		}
		if ctrl && !alt {
			switch event.Key() {
			case tcell.KeyCtrlS:
				dataview.Save()
			case tcell.KeyCtrlQ:
				dataview.Save()
				dataview.Close()
				m.curViewID = ""
				m.focusFileselector()
			case tcell.KeyCtrlD:
				dataview.DuplicateLine()
			case tcell.KeyCtrlV:
				s, e := clipboard.ReadAll()
				if e != nil {
					log.Println(e)
					return
				}
				dataview.Insert(s)
			default:
				log.Println(event.Name())
			}
		}
		if !ctrl && alt {
			switch event.Name() {
			case "Alt+Rune[0]":
				m.focusFileselector()
			default:
				log.Println(event.Name())
			}
		}
		if ctrl && alt {
			switch event.Key() {

			default:
				log.Println(event.Name())
			}
		}
		log.Println(event.Name())
		//dataview.Save()
	})
}
<|endoftext|>


<commit_before>package main

import (
	"bufio"
	"bytes"
	"encoding/json"
	"expvar"
	"flag"
	"fmt"
	"github.com/jmhodges/howsmyssl/tls"
	"html/template"
	"io/ioutil"
	"log"
	"net"
	"net/http"
	"net/http/httputil"
	_ "net/http/pprof"
	"net/url"
	"strconv"
	"strings"
	"time"
)

const (
	resp500Format = `HTTP/1.%d 500 Internal Server Error
Content-Length: 26
Connection: close
Content-Type: text/plain; charset="utf-8"
Date: %s

500 Internal Server Error
`
)

var (
	httpsAddr = flag.String("httpsAddr", "localhost:10443", "address to boot the HTTPS server on")
	httpAddr  = flag.String("httpAddr", "localhost:10080", "address to boot the HTTP server on")
	vhost     = flag.String("vhost", "localhost:10443", "public domain to use in redirects and templates")
	certPath  = flag.String("cert", "./config/development.crt", "file path to the TLS certificate to serve with")
	keyPath   = flag.String("key", "./config/development.key", "file path to the TLS key to serve with")
	staticDir = flag.String("staticDir", "./static", "file path to the directory of static files to serve")
	tmplDir   = flag.String("templateDir", "./templates", "file path to the directory of templates")

	apiVars        = expvar.NewMap("api")
	staticVars     = expvar.NewMap("static")
	webVars        = expvar.NewMap("web")
	apiRequests    = new(expvar.Int)
	staticRequests = new(expvar.Int)
	webRequests    = new(expvar.Int)
	apiStatuses    = NewStatusStats(apiVars)
	staticStatuses = NewStatusStats(staticVars)
	webStatuses    = NewStatusStats(webVars)

	index *template.Template
)

func main() {
	flag.Parse()

	host := *vhost
	if strings.Contains(*vhost, ":") {
		var err error
		shost, port, err := net.SplitHostPort(*vhost)
		if err != nil {
			log.Fatalf("unable to parse httpsAddr: %s", err)
		}
		host = shost
		if port != "443" {
			host = *vhost
		}
	}

	apiVars.Set("requests", apiRequests)
	staticVars.Set("requests", staticRequests)
	webVars.Set("requests", webRequests)

	index = loadIndex()
	tlsConf := makeTLSConfig(*certPath, *keyPath)

	tlsListener, err := tls.Listen("tcp", *httpsAddr, tlsConf)
	if err != nil {
		log.Fatalf("unable to listen for the HTTPS server on %s: %s", *httpsAddr, err)
	}
	plaintextListener, err := net.Listen("tcp", *httpAddr)
	if err != nil {
		log.Fatalf("unable to listen for the HTTP server on %s: %s", *httpAddr, err)
	}
	l := &listener{tlsListener}

	m := tlsMux(
		host,
		makeStaticHandler())

	go func() {
		err := http.ListenAndServe("localhost:4567", nil)
		if err != nil {
			log.Fatalf("unable to open admin server: %s", err)
		}
	}()

	log.Printf("Booting HTTPS on %s and HTTP on %s", *httpsAddr, *httpAddr)
	go func() {
		err := http.Serve(l, m)
		if err != nil {
			log.Fatalf("https server error: %s", err)
		}
	}()
	err = http.Serve(plaintextListener, plaintextMux(host))
	if err != nil {
		log.Fatalf("http server error: %s", err)
	}
}

func tlsMux(vhost string, staticHandler http.Handler) http.Handler {
	m := http.NewServeMux()
	m.Handle(vhost+"/s/", staticHandler)
	m.HandleFunc(vhost+"/a/check", handleAPI)
	m.HandleFunc(vhost+"/", handleWeb)
	m.HandleFunc(vhost+"/healthcheck", healthcheck)
	m.HandleFunc("/healthcheck", healthcheck)
	m.Handle("/", commonRedirect(vhost))
	return logHandler{inner: m, proto: "https"}
}

func plaintextMux(vhost string) http.Handler {
	m := http.NewServeMux()
	m.HandleFunc("/healthcheck", healthcheck)
	m.Handle("/", commonRedirect(vhost))
	return logHandler{inner: m, proto: "http"}
}

func renderHTML(data *clientInfo) ([]byte, error) {
	b := new(bytes.Buffer)
	err := index.Execute(b, data)
	if err != nil {
		return nil, err
	}
	return b.Bytes(), nil
}

func renderJSON(data *clientInfo) ([]byte, error) {
	return json.Marshal(data)
}

func handleWeb(w http.ResponseWriter, r *http.Request) {
	if r.URL.Path != "/" {
		http.Error(w, "404 Not Found", http.StatusNotFound)
		return
	}
	webRequests.Add(1)
	hijackHandle(w, r, "text/html;charset=utf-8", webStatuses, renderHTML)
}

func handleAPI(w http.ResponseWriter, r *http.Request) {
	apiRequests.Add(1)
	hijackHandle(w, r, "application/json", apiStatuses, renderJSON)
}

func hijackHandle(w http.ResponseWriter, r *http.Request, contentType string, statuses *statusStats, render func(*clientInfo) ([]byte, error)) {
	hj, ok := w.(http.Hijacker)
	if !ok {
		log.Printf("server not hijackable\n")
		http.Error(w, "500 Internal Server Error", http.StatusInternalServerError)
		return
	}

	c, brw, err := hj.Hijack()
	if err != nil {
		log.Printf("server errored during hijack: %s\n", err)
		return
	}
	defer c.Close()
	tc, ok := c.(*conn)
	if !ok {
		log.Printf("Unable to convert net.Conn to *conn: %s\n", err)
		hijacked500(brw, r.ProtoMinor, statuses)
	}
	data := ClientInfo(tc)
	bs, err := render(data)
	if err != nil {
		log.Printf("Unable to excute index template: %s\n", err)
		hijacked500(brw, r.ProtoMinor, statuses)
		return
	}
	contentLength := int64(len(bs))
	h := make(http.Header)
	h.Set("Date", time.Now().Format(http.TimeFormat))
	h.Set("Content-Type", contentType)
	if r.ProtoMinor == 1 { // Assumes HTTP/1.x
		h.Set("Connection", "close")
	}
	h.Set("Content-Length", strconv.FormatInt(contentLength, 10))
	resp := &http.Response{
		StatusCode:    200,
		ContentLength: contentLength,
		Header:        h,
		Body:          ioutil.NopCloser(bytes.NewBuffer(bs)),
		ProtoMajor:    1, // Assumes HTTP/1.x
		ProtoMinor:    r.ProtoMinor,
	}
	bs, err = httputil.DumpResponse(resp, true)
	if err != nil {
		log.Printf("unable to write response: %s\n", err)
		hijacked500(brw, r.ProtoMinor, statuses)
		return
	}
	statuses.status2xx.Add(1)
	brw.Write(bs)
	brw.Flush()
}

func hijacked500(brw *bufio.ReadWriter, protoMinor int, statuses *statusStats) {
	statuses.status5xx.Add(1)
	// Assumes HTTP/1.x
	s := fmt.Sprintf(resp500Format, protoMinor, time.Now().Format(http.TimeFormat))
	brw.WriteString(s)
	brw.Flush()
}

func healthcheck(w http.ResponseWriter, r *http.Request) {
	w.WriteHeader(200)
	w.Write([]byte("ok"))
}

func commonRedirect(vhost string) http.Handler {
	hf := func(w http.ResponseWriter, r *http.Request) {
		var u url.URL
		u = *r.URL
		u.Scheme = "https"
		u.Host = vhost
		http.Redirect(w, r, u.String(), http.StatusMovedPermanently)
	}
	return http.HandlerFunc(hf)
}

func loadIndex() *template.Template {
	return template.Must(template.New("index.html").
		Funcs(template.FuncMap{"sentence": sentence, "ratingSpan": ratingSpan}).
		ParseFiles(*tmplDir + "/index.html"))
}

func makeTLSConfig(certPath, keyPath string) *tls.Config {
	cert, err := tls.LoadX509KeyPair(certPath, keyPath)
	if err != nil {
		log.Fatalf("unable to load TLS key cert pair %s: %s", certPath, err)
	}

	tlsConf := &tls.Config{
		Certificates: []tls.Certificate{cert},
		NextProtos:   []string{"https"},
	}
	tlsConf.BuildNameToCertificate()
	return tlsConf
}

func makeStaticHandler() http.HandlerFunc {
	stats := NewStatusStats(staticVars)
	h := http.StripPrefix("/s/", http.FileServer(http.Dir(*staticDir)))
	return func(w http.ResponseWriter, r *http.Request) {
		staticRequests.Add(1)
		w = &statWriter{w: w, stats: stats}
		h.ServeHTTP(w, r)
	}
}

func ratingSpan(rating Rating) template.HTML {
	class := ""
	switch rating {
	case okay:
		class = "okay"
	case improvable:
		class = "improvable"
	case bad:
		class = "bad"
	}
	return template.HTML(fmt.Sprintf(`<span class="%s">%s</span>`, class, rating))
}

func sentence(parts []string) string {
	if len(parts) == 1 {
		return parts[0] + "."
	}
	commaed := parts[:len(parts)-1]
	return strings.Join(commaed, ", ") + ", and " + parts[len(parts)-1] + "."
}

type logHandler struct {
	inner http.Handler
	proto string
}

// Since we have a Hijack in our code, this simple writer will suffice for
// now.
func (h logHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
	host, _, err := net.SplitHostPort(r.RemoteAddr)
	if err != nil {
		host = "0.0.0.0"
	}
	fmt.Printf("%s %s %s\n", host, h.proto, r.URL)
	h.inner.ServeHTTP(w, r)
}
<commit_msg>add HSTS header<commit_after>package main

import (
	"bufio"
	"bytes"
	"encoding/json"
	"expvar"
	"flag"
	"fmt"
	"github.com/jmhodges/howsmyssl/tls"
	"html/template"
	"io/ioutil"
	"log"
	"net"
	"net/http"
	"net/http/httputil"
	_ "net/http/pprof"
	"strconv"
	"strings"
	"time"
)

const (
	resp500Format = `HTTP/1.%d 500 Internal Server Error
Content-Length: 26
Connection: close
Content-Type: text/plain; charset="utf-8"
Strict-Transport-Security: max-age=631138519; includeSubdomains
Date: %s

500 Internal Server Error
`
	hstsHeaderValue = "max-age=631138519; includeSubdomains"
	xForwardedProto = "X-Forwarded-Proto"
)

var (
	httpsAddr = flag.String("httpsAddr", "localhost:10443", "address to boot the HTTPS server on")
	httpAddr  = flag.String("httpAddr", "localhost:10080", "address to boot the HTTP server on")
	vhost     = flag.String("vhost", "localhost:10443", "public domain to use in redirects and templates")
	certPath  = flag.String("cert", "./config/development.crt", "file path to the TLS certificate to serve with")
	keyPath   = flag.String("key", "./config/development.key", "file path to the TLS key to serve with")
	staticDir = flag.String("staticDir", "./static", "file path to the directory of static files to serve")
	tmplDir   = flag.String("templateDir", "./templates", "file path to the directory of templates")

	apiVars        = expvar.NewMap("api")
	staticVars     = expvar.NewMap("static")
	webVars        = expvar.NewMap("web")
	apiRequests    = new(expvar.Int)
	staticRequests = new(expvar.Int)
	webRequests    = new(expvar.Int)
	apiStatuses    = NewStatusStats(apiVars)
	staticStatuses = NewStatusStats(staticVars)
	webStatuses    = NewStatusStats(webVars)

	index *template.Template
)

func main() {
	flag.Parse()

	host := *vhost
	if strings.Contains(*vhost, ":") {
		var err error
		shost, port, err := net.SplitHostPort(*vhost)
		if err != nil {
			log.Fatalf("unable to parse httpsAddr: %s", err)
		}
		host = shost
		if port != "443" {
			host = *vhost
		}
	}

	apiVars.Set("requests", apiRequests)
	staticVars.Set("requests", staticRequests)
	webVars.Set("requests", webRequests)

	index = loadIndex()
	tlsConf := makeTLSConfig(*certPath, *keyPath)

	tlsListener, err := tls.Listen("tcp", *httpsAddr, tlsConf)
	if err != nil {
		log.Fatalf("unable to listen for the HTTPS server on %s: %s", *httpsAddr, err)
	}
	plaintextListener, err := net.Listen("tcp", *httpAddr)
	if err != nil {
		log.Fatalf("unable to listen for the HTTP server on %s: %s", *httpAddr, err)
	}
	l := &listener{tlsListener}

	m := tlsMux(
		host,
		makeStaticHandler())

	go func() {
		err := http.ListenAndServe("localhost:4567", nil)
		if err != nil {
			log.Fatalf("unable to open admin server: %s", err)
		}
	}()

	log.Printf("Booting HTTPS on %s and HTTP on %s", *httpsAddr, *httpAddr)
	go func() {
		err := http.Serve(l, m)
		if err != nil {
			log.Fatalf("https server error: %s", err)
		}
	}()
	err = http.Serve(plaintextListener, plaintextMux(host))
	if err != nil {
		log.Fatalf("http server error: %s", err)
	}
}

func tlsMux(vhost string, staticHandler http.Handler) http.Handler {
	m := http.NewServeMux()
	m.Handle(vhost+"/s/", staticHandler)
	m.HandleFunc(vhost+"/a/check", handleAPI)
	m.HandleFunc(vhost+"/", handleWeb)
	m.HandleFunc(vhost+"/healthcheck", healthcheck)
	m.HandleFunc("/healthcheck", healthcheck)
	m.Handle("/", commonRedirect(vhost))
	return protoHandler{logHandler{m}, "https"}
}

func plaintextMux(vhost string) http.Handler {
	m := http.NewServeMux()
	m.HandleFunc("/healthcheck", healthcheck)
	m.Handle("/", commonRedirect(vhost))
	return protoHandler{logHandler{m}, "http"}
}

func renderHTML(data *clientInfo) ([]byte, error) {
	b := new(bytes.Buffer)
	err := index.Execute(b, data)
	if err != nil {
		return nil, err
	}
	return b.Bytes(), nil
}

func renderJSON(data *clientInfo) ([]byte, error) {
	return json.Marshal(data)
}

func handleWeb(w http.ResponseWriter, r *http.Request) {
	if r.URL.Path != "/" {
		http.Error(w, "404 Not Found", http.StatusNotFound)
		return
	}
	webRequests.Add(1)
	hijackHandle(w, r, "text/html;charset=utf-8", webStatuses, renderHTML)
}

func handleAPI(w http.ResponseWriter, r *http.Request) {
	apiRequests.Add(1)
	hijackHandle(w, r, "application/json", apiStatuses, renderJSON)
}

func hijackHandle(w http.ResponseWriter, r *http.Request, contentType string, statuses *statusStats, render func(*clientInfo) ([]byte, error)) {
	hj, ok := w.(http.Hijacker)
	if !ok {
		log.Printf("server not hijackable\n")
		http.Error(w, "500 Internal Server Error", http.StatusInternalServerError)
		return
	}

	c, brw, err := hj.Hijack()
	if err != nil {
		log.Printf("server errored during hijack: %s\n", err)
		return
	}
	defer c.Close()
	tc, ok := c.(*conn)
	if !ok {
		log.Printf("Unable to convert net.Conn to *conn: %s\n", err)
		hijacked500(brw, r.ProtoMinor, statuses)
	}
	data := ClientInfo(tc)
	bs, err := render(data)
	if err != nil {
		log.Printf("Unable to excute index template: %s\n", err)
		hijacked500(brw, r.ProtoMinor, statuses)
		return
	}
	contentLength := int64(len(bs))
	h := make(http.Header)
	h.Set("Date", time.Now().Format(http.TimeFormat))
	h.Set("Content-Type", contentType)
	if r.ProtoMinor == 1 { // Assumes HTTP/1.x
		h.Set("Connection", "close")
	}
	h.Set("Strict-Transport-Security", hstsHeaderValue)
	h.Set("Content-Length", strconv.FormatInt(contentLength, 10))
	resp := &http.Response{
		StatusCode:    200,
		ContentLength: contentLength,
		Header:        h,
		Body:          ioutil.NopCloser(bytes.NewBuffer(bs)),
		ProtoMajor:    1, // Assumes HTTP/1.x
		ProtoMinor:    r.ProtoMinor,
	}
	bs, err = httputil.DumpResponse(resp, true)
	if err != nil {
		log.Printf("unable to write response: %s\n", err)
		hijacked500(brw, r.ProtoMinor, statuses)
		return
	}
	statuses.status2xx.Add(1)
	brw.Write(bs)
	brw.Flush()
}

func hijacked500(brw *bufio.ReadWriter, protoMinor int, statuses *statusStats) {
	statuses.status5xx.Add(1)
	// Assumes HTTP/1.x
	s := fmt.Sprintf(resp500Format, protoMinor, time.Now().Format(http.TimeFormat))
	brw.WriteString(s)
	brw.Flush()
}

func healthcheck(w http.ResponseWriter, r *http.Request) {
	w.WriteHeader(200)
	w.Write([]byte("ok"))
}

func commonRedirect(vhost string) http.Handler {
	hf := func(w http.ResponseWriter, r *http.Request) {
		if r.Header.Get(xForwardedProto) == "https" {
			w.Header().Set("Strict-Transport-Security", hstsHeaderValue)

		}
		u := r.URL
		// Never set by the Go HTTP library.
		u.Scheme = "https"
		u.Host = vhost
		http.Redirect(w, r, u.String(), http.StatusMovedPermanently)
	}
	return http.HandlerFunc(hf)
}

func loadIndex() *template.Template {
	return template.Must(template.New("index.html").
		Funcs(template.FuncMap{"sentence": sentence, "ratingSpan": ratingSpan}).
		ParseFiles(*tmplDir + "/index.html"))
}

func makeTLSConfig(certPath, keyPath string) *tls.Config {
	cert, err := tls.LoadX509KeyPair(certPath, keyPath)
	if err != nil {
		log.Fatalf("unable to load TLS key cert pair %s: %s", certPath, err)
	}

	tlsConf := &tls.Config{
		Certificates: []tls.Certificate{cert},
		NextProtos:   []string{"https"},
	}
	tlsConf.BuildNameToCertificate()
	return tlsConf
}

func makeStaticHandler() http.HandlerFunc {
	stats := NewStatusStats(staticVars)
	h := http.StripPrefix("/s/", http.FileServer(http.Dir(*staticDir)))
	return func(w http.ResponseWriter, r *http.Request) {
		staticRequests.Add(1)
		w = &statWriter{w: w, stats: stats}
		h.ServeHTTP(w, r)
	}
}

func ratingSpan(rating Rating) template.HTML {
	class := ""
	switch rating {
	case okay:
		class = "okay"
	case improvable:
		class = "improvable"
	case bad:
		class = "bad"
	}
	return template.HTML(fmt.Sprintf(`<span class="%s">%s</span>`, class, rating))
}

func sentence(parts []string) string {
	if len(parts) == 1 {
		return parts[0] + "."
	}
	commaed := parts[:len(parts)-1]
	return strings.Join(commaed, ", ") + ", and " + parts[len(parts)-1] + "."
}

type logHandler struct {
	inner http.Handler
}

// Since we have a Hijack in our code, this simple writer will suffice for
// now.
func (h logHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
	host, _, err := net.SplitHostPort(r.RemoteAddr)
	if err != nil {
		host = "0.0.0.0"
	}
	proto := r.Header.Get(xForwardedProto)
	if proto == "" {
		proto = "unknown"
	}
	fmt.Printf("%s %s %s\n", host, proto, r.URL)
	h.inner.ServeHTTP(w, r)
}

type protoHandler struct {
	inner http.Handler
	proto string
}

func (h protoHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
	r.Header.Set(xForwardedProto, h.proto)
	h.inner.ServeHTTP(w, r)
}
<|endoftext|>


<commit_before>package md

import (
	"flag"
	"log"

	"github.com/mrwill84/goctp"
)

var (
	broker_id    = flag.String("BrokerID", "9999", "经纪公司编号,SimNow BrokerID统一为：9999")
	investor_id  = flag.String("InvestorID", "<InvestorID>", "交易用户代码")
	pass_word    = flag.String("Password", "<Password>", "交易用户密码")
	market_front = flag.String("MarketFront", "tcp://180.168.146.187:10031", "行情前置,SimNow的测试环境: tcp://180.168.146.187:10031")
	trade_front  = flag.String("TradeFront", "tcp://180.168.146.187:10030", "交易前置,SimNow的测试环境: tcp://180.168.146.187:10030")
)

var CTP GoCTPClient

type GoCTPClient struct {
	BrokerID   string
	InvestorID string
	Password   string

	MdFront string
	MdApi   goctp.CThostFtdcMdApi

	TraderFront string
	TraderApi   goctp.CThostFtdcTraderApi

	MdRequestID     int
	TraderRequestID int
	FrontendConnent chan bool
}

func (g *GoCTPClient) GetMdRequestID() int {
	g.MdRequestID += 1
	return g.MdRequestID
}

func NewDirectorCThostFtdcMdSpi(v interface{}) goctp.CThostFtdcMdSpi {

	mdspi := goctp.NewDirectorCThostFtdcMdSpi(v)
	mdspi.FrontendConnent = make(chan bool, 1)
	return
}

type GoCThostFtdcMdSpi struct {
	Client GoCTPClient
}

func (p *GoCThostFtdcMdSpi) OnRspError(pRspInfo goctp.CThostFtdcRspInfoField, nRequestID int, bIsLast bool) {
	log.Println("GoCThostFtdcMdSpi.OnRspError.")
	p.IsErrorRspInfo(pRspInfo)
}

func (p *GoCThostFtdcMdSpi) OnFrontDisconnected(nReason int) {
	log.Printf("GoCThostFtdcMdSpi.OnFrontDisconnected: %#v\n", nReason)
}

func (p *GoCThostFtdcMdSpi) OnHeartBeatWarning(nTimeLapse int) {
	log.Printf("GoCThostFtdcMdSpi.OnHeartBeatWarning: %v", nTimeLapse)

}

func (p *GoCThostFtdcMdSpi) OnFrontConnected() {
	log.Println("GoCThostFtdcMdSpi.OnFrontConnected.")
	mdspi.FrontendConnent <- true
	//p.ReqUserLogin()
}

func (p *GoCThostFtdcMdSpi) IsErrorRspInfo(pRspInfo goctp.CThostFtdcRspInfoField) bool {
	// 如果ErrorID != 0, 说明收到了错误的响应
	bResult := (pRspInfo.GetErrorID() != 0)
	if bResult {
		log.Printf("ErrorID=%v ErrorMsg=%v\n", pRspInfo.GetErrorID(), pRspInfo.GetErrorMsg())
	}
	return bResult
}
<commit_msg>md fix<commit_after>package md

import (
	"flag"
	"log"

	"github.com/mrwill84/goctp"
)

var (
	broker_id    = flag.String("BrokerID", "9999", "经纪公司编号,SimNow BrokerID统一为：9999")
	investor_id  = flag.String("InvestorID", "<InvestorID>", "交易用户代码")
	pass_word    = flag.String("Password", "<Password>", "交易用户密码")
	market_front = flag.String("MarketFront", "tcp://180.168.146.187:10031", "行情前置,SimNow的测试环境: tcp://180.168.146.187:10031")
	trade_front  = flag.String("TradeFront", "tcp://180.168.146.187:10030", "交易前置,SimNow的测试环境: tcp://180.168.146.187:10030")
)

var CTP GoCTPClient

type GoCTPClient struct {
	BrokerID   string
	InvestorID string
	Password   string

	MdFront string
	MdApi   goctp.CThostFtdcMdApi

	TraderFront string
	TraderApi   goctp.CThostFtdcTraderApi

	MdRequestID     int
	TraderRequestID int
	FrontendConnent chan bool
}

func init() {
	CTP.FrontendConnent = make(chan bool, 1)
}
func (g *GoCTPClient) GetMdRequestID() int {
	g.MdRequestID += 1
	return g.MdRequestID
}

func NewDirectorCThostFtdcMdSpi(v interface{}) goctp.CThostFtdcMdSpi {

	mdspi := goctp.NewDirectorCThostFtdcMdSpi(v)

	return
}

type GoCThostFtdcMdSpi struct {
	Client GoCTPClient
}

func (p *GoCThostFtdcMdSpi) OnRspError(pRspInfo goctp.CThostFtdcRspInfoField, nRequestID int, bIsLast bool) {
	log.Println("GoCThostFtdcMdSpi.OnRspError.")
	p.IsErrorRspInfo(pRspInfo)
}

func (p *GoCThostFtdcMdSpi) OnFrontDisconnected(nReason int) {
	log.Printf("GoCThostFtdcMdSpi.OnFrontDisconnected: %#v\n", nReason)
}

func (p *GoCThostFtdcMdSpi) OnHeartBeatWarning(nTimeLapse int) {
	log.Printf("GoCThostFtdcMdSpi.OnHeartBeatWarning: %v", nTimeLapse)

}

func (p *GoCThostFtdcMdSpi) OnFrontConnected() {
	log.Println("GoCThostFtdcMdSpi.OnFrontConnected.")
	CTP.FrontendConnent <- true
	//p.ReqUserLogin()
}

func (p *GoCThostFtdcMdSpi) IsErrorRspInfo(pRspInfo goctp.CThostFtdcRspInfoField) bool {
	// 如果ErrorID != 0, 说明收到了错误的响应
	bResult := (pRspInfo.GetErrorID() != 0)
	if bResult {
		log.Printf("ErrorID=%v ErrorMsg=%v\n", pRspInfo.GetErrorID(), pRspInfo.GetErrorMsg())
	}
	return bResult
}
<|endoftext|>


<commit_before>package player

import "github.com/lean-poker/poker-player-go/leanpoker"
import s "github.com/lean-poker/poker-player-go/strategies"

const VERSION = "Pasha Team Player 0.0.2"

func BetRequest(state *leanpoker.Game) int {
	return s.Default(state)
}

func Showdown(state *leanpoker.Game) {

}

func Version() string {
	return VERSION
}
<commit_msg>bump version.<commit_after>package player

import "github.com/lean-poker/poker-player-go/leanpoker"
import s "github.com/lean-poker/poker-player-go/strategies"

const VERSION = "Pasha Team Player 0.0.3"

func BetRequest(state *leanpoker.Game) int {
	return s.Default(state)
}

func Showdown(state *leanpoker.Game) {

}

func Version() string {
	return VERSION
}
<|endoftext|>


<commit_before>package gatekeeper

import (
	"bytes"
	"crypto/tls"
	"crypto/x509"
	"encoding/json"
	"errors"
	"fmt"
	"net/http"
	"net/url"
	"os"
	"strconv"
)

type Client struct {
	VaultAddress      string
	GatekeeperAddress string
	HttpClient        *http.Client
}

var DefaultClient *Client

var ErrNoTaskId = errors.New("No task id provided.")

func init() {
	DefaultClient = new(Client)
	DefaultClient.VaultAddress = os.Getenv("VAULT_ADDR")
	DefaultClient.GatekeeperAddress = os.Getenv("GATEKEEPER_ADDR")
	tr := &http.Transport{
		TLSClientConfig: &tls.Config{},
	}
	capath := os.Getenv("VAULT_CAPATH")
	cacert := os.Getenv("VAULT_CACERT")

	if b, err := strconv.ParseBool(os.Getenv("VAULT_SKIP_VERIFY")); err == nil && b {
		tr.TLSClientConfig.InsecureSkipVerify = true
	}

	if capath != "" || cacert != "" {
		LoadCA := func() (*x509.CertPool, error) {
			if capath != "" {
				return LoadCAPath(capath)
			} else if cacert != "" {
				return LoadCACert(cacert)
			}
			panic("invariant violation")
		}
		if certs, err := LoadCA(); err == nil {
			tr.TLSClientConfig.RootCAs = certs
		} else {
			fmt.Fprintf(os.Stderr, "Gatekeeper: Failed to read client certs. Error: %v\n", err)
		}
	}
	DefaultClient.HttpClient = &http.Client{Transport: tr}
}

func RequestVaultToken(taskId string) (string, error) {
	return DefaultClient.RequestVaultToken(taskId)
}

func EnvRequestVaultToken() (string, error) {
	return DefaultClient.RequestVaultToken(os.Getenv("MESOS_TASK_ID"))
}

func (c *Client) RequestVaultToken(taskId string) (string, error) {
	if c.HttpClient == nil {
		c.HttpClient = http.DefaultClient
	}
	tempToken, err := c.requestTempToken(taskId)
	if err != nil {
		return "", err
	}

	permToken, err := c.requestPermToken(tempToken)
	if err != nil {
		return "", err
	}

	return permToken, err
}

func (c *Client) requestTempToken(taskID string) (string, error) {
	if taskID == "" {
		return "", ErrNoTaskId
	}

	gkAddr, err := url.Parse(c.GatekeeperAddress)
	if err != nil {
		return "", err
	}
	gkAddr.Path = "/token"

	gkTaskID := gkTokenReq{TaskId: taskID}
	gkReq, err := json.Marshal(gkTaskID)
	if err != nil {
		return "", err
	}

	gkResp, err := c.HttpClient.Post(gkAddr.String(), "application/json", bytes.NewReader(gkReq))
	if err != nil {
		return "", err
	}
	defer gkResp.Body.Close()

	gkTokResp := &gkTokenResp{}
	if err := json.NewDecoder(gkResp.Body).Decode(gkTokResp); err != nil {
		return "", err
	}

	if !gkTokResp.OK {
		return "", errors.New(gkTokResp.Error)
	}

	return gkTokResp.Token, nil
}

func (c *Client) requestPermToken(tempToken string) (string, error) {
	vaultAddr, err := url.Parse(c.VaultAddress)
	if err != nil {
		return "", err
	}
	vaultAddr.Path = "/v1/cubbyhole/response"

	req, err := http.NewRequest("GET", vaultAddr.String(), nil)
	if err != nil {
		return "", err
	}
	req.Header.Add("X-Vault-Token", tempToken)

	vaultResp, err := c.HttpClient.Do(req)
	if err != nil {
		return "", err
	}
	defer vaultResp.Body.Close()

	if err := buildVaultError(vaultResp); err != nil {
		return "", err
	}

	cubbyholeSecret := &cubbyholeSecret{}
	if err := json.NewDecoder(vaultResp.Body).Decode(cubbyholeSecret); err != nil {
		return "", err
	}

	return cubbyholeSecret.Data.WrappedSecret.Token, nil
}
<commit_msg>Client: Add NewClient helper function<commit_after>package gatekeeper

import (
	"bytes"
	"crypto/tls"
	"crypto/x509"
	"encoding/json"
	"errors"
	"fmt"
	"net/http"
	"net/url"
	"os"
	"strconv"
)

type Client struct {
	VaultAddress      string
	GatekeeperAddress string
	HttpClient        *http.Client
}

var DefaultClient *Client

var ErrNoTaskId = errors.New("No task id provided.")

func init() {
	capath := os.Getenv("VAULT_CAPATH")
	cacert := os.Getenv("VAULT_CACERT")
	var rootCas *x509.CertPool

	if capath != "" || cacert != "" {
		LoadCA := func() (*x509.CertPool, error) {
			if capath != "" {
				return LoadCAPath(capath)
			} else if cacert != "" {
				return LoadCACert(cacert)
			}
			panic("invariant violation")
		}
		if certs, err := LoadCA(); err == nil {
			rootCas = certs
		} else {
			fmt.Fprintf(os.Stderr, "Gatekeeper: Failed to read client certs. Error: %v\n", err)
		}
	}

	var err error
	DefaultClient, err = NewClient(os.Getenv("VAULT_ADDR"), os.Getenv("GATEKEEPER_ADDR"), rootCas)
	if err == nil {
		if b, err := strconv.ParseBool(os.Getenv("VAULT_SKIP_VERIFY")); err == nil && b {
			DefaultClient.InsecureSkipVerify(true)
		}
	}
}

func RequestVaultToken(taskId string) (string, error) {
	return DefaultClient.RequestVaultToken(taskId)
}

func EnvRequestVaultToken() (string, error) {
	return DefaultClient.RequestVaultToken(os.Getenv("MESOS_TASK_ID"))
}

func NewClient(vaultAddress, gatekeeperAddress string, certPool *x509.CertPool) (*Client, error) {
	client := new(Client)
	client.VaultAddress = vaultAddress
	client.GatekeeperAddress = gatekeeperAddress
	tr := &http.Transport{
		TLSClientConfig: &tls.Config{},
	}
	if certPool != nil {
		tr.TLSClientConfig.RootCAs = certPool
	}
	client.HttpClient = &http.Client{Transport: tr}
	if _, err := url.Parse(client.GatekeeperAddress); err != nil {
		return nil, err
	}
	if _, err := url.Parse(client.VaultAddress); err != nil {
		return nil, err
	}
	return client, nil
}

func (c *Client) InsecureSkipVerify(skipVerify bool) {
	if _, ok := c.HttpClient.Transport.(*http.Transport); ok {
		c.HttpClient.Transport.(*http.Transport).TLSClientConfig.InsecureSkipVerify = skipVerify
	}
}

func (c *Client) RequestVaultToken(taskId string) (string, error) {
	if c.HttpClient == nil {
		c.HttpClient = http.DefaultClient
	}
	tempToken, err := c.requestTempToken(taskId)
	if err != nil {
		return "", err
	}

	permToken, err := c.requestPermToken(tempToken)
	if err != nil {
		return "", err
	}

	return permToken, err
}

func (c *Client) requestTempToken(taskID string) (string, error) {
	if taskID == "" {
		return "", ErrNoTaskId
	}

	gkAddr, err := url.Parse(c.GatekeeperAddress)
	if err != nil {
		return "", err
	}
	gkAddr.Path = "/token"

	gkTaskID := gkTokenReq{TaskId: taskID}
	gkReq, err := json.Marshal(gkTaskID)
	if err != nil {
		return "", err
	}

	gkResp, err := c.HttpClient.Post(gkAddr.String(), "application/json", bytes.NewReader(gkReq))
	if err != nil {
		return "", err
	}
	defer gkResp.Body.Close()

	gkTokResp := &gkTokenResp{}
	if err := json.NewDecoder(gkResp.Body).Decode(gkTokResp); err != nil {
		return "", err
	}

	if !gkTokResp.OK {
		return "", errors.New(gkTokResp.Error)
	}

	return gkTokResp.Token, nil
}

func (c *Client) requestPermToken(tempToken string) (string, error) {
	vaultAddr, err := url.Parse(c.VaultAddress)
	if err != nil {
		return "", err
	}
	vaultAddr.Path = "/v1/cubbyhole/response"

	req, err := http.NewRequest("GET", vaultAddr.String(), nil)
	if err != nil {
		return "", err
	}
	req.Header.Add("X-Vault-Token", tempToken)

	vaultResp, err := c.HttpClient.Do(req)
	if err != nil {
		return "", err
	}
	defer vaultResp.Body.Close()

	if err := buildVaultError(vaultResp); err != nil {
		return "", err
	}

	cubbyholeSecret := &cubbyholeSecret{}
	if err := json.NewDecoder(vaultResp.Body).Decode(cubbyholeSecret); err != nil {
		return "", err
	}

	return cubbyholeSecret.Data.WrappedSecret.Token, nil
}
<|endoftext|>


<commit_before>package controllers

import (
	"bytes"
	"encoding/json"
	"fmt"
	"io/ioutil"
	"net/http"
	"path"
	"runtime"

	"github.com/jelmersnoeck/noscito/pdf"
)

func MainIndex(w http.ResponseWriter, r *http.Request) {
	template, _ := pdf.NewJsonTemplate(loadTemplate("print-batch-collection"))
	template.LoadBlocks(userInput())

	f := pdf.NewGoFpdf(template.Layout())
	f.ParseBlocks(template.Blocks())

	buffer := bytes.NewBufferString("")
	w.Write(f.Bytes(buffer))
}

func userInput() (data map[string]interface{}) {
	byt := []byte(`{
		"first_image": { "url": "https://upload.wikimedia.org/wikipedia/commons/thumb/5/5d/UPC-A-036000291452.png/220px-UPC-A-036000291452.png", "visible": false },
		"second_image": { "url": "http://petapixel.com/assets/uploads/2013/11/bloomf1.jpeg" }
	}`)

	json.Unmarshal(byt, &data)
	return data
}

func loadTemplate(name string) []byte {
	_, filename, _, ok := runtime.Caller(1)

	if !ok {
		return nil
	}

	filepath := path.Join(path.Dir(filename), "../templates/"+name+".json")
	file, err := ioutil.ReadFile(filepath)

	if err != nil {
		fmt.Printf(err.Error())
		return nil
	}

	return file
}
<commit_msg>Main: add actual API implementation example.<commit_after>package controllers

import (
	"bytes"
	"encoding/json"
	"fmt"
	"io/ioutil"
	"net/http"
	"path"
	"runtime"

	"github.com/jelmersnoeck/noscito/pdf"
)

func MainIndex(w http.ResponseWriter, r *http.Request) {
	//var data map[string]interface{}
	//body, _ := ioutil.ReadAll(r.Body)
	//json.Unmarshal(body, &data)

	template, _ := pdf.NewJsonTemplate(loadTemplate("pb-collection"))
	template.LoadBlocks(userInput())
	//template.LoadBlocks(data["data"].(map[string]interface{}))

	f := pdf.NewGoFpdf(template.Layout())
	f.ParseBlocks(template.Blocks())

	buffer := bytes.NewBufferString("")
	w.Write(f.Bytes(buffer))
}

func userInput() (data map[string]interface{}) {
	byt := []byte(`{
		"set_1_image_1": { "url": "https://upload.wikimedia.org/wikipedia/commons/thumb/5/5d/UPC-A-036000291452.png/220px-UPC-A-036000291452.png", "visible": false },
		"set_1_image_2": { "url": "http://petapixel.com/assets/uploads/2013/11/bloomf1.jpeg" }
	}`)

	json.Unmarshal(byt, &data)
	return data
}

func loadTemplate(name string) []byte {
	_, filename, _, ok := runtime.Caller(1)

	if !ok {
		return nil
	}

	filepath := path.Join(path.Dir(filename), "../templates/"+name+".json")
	file, err := ioutil.ReadFile(filepath)

	if err != nil {
		fmt.Printf(err.Error())
		return nil
	}

	return file
}
<|endoftext|>


<commit_before>package main

import (
	"fmt"
	"io/ioutil"
	"os"

	"github.com/gonuts/commander"
	"github.com/zellyn/go6502/asm"
)

var cmdDisasm = &commander.Command{
	Run:       runDisasm,
	UsageLine: "disasm [-a address] filename",
	Short:     "disassemble binary files",
	Long: `
Disasm is a very simple disassembler for 6502 binary files.
`,
}

var disasmAddress uint // disasm -a flag

func init() {
	cmdDisasm.Flag.UintVar(&disasmAddress, "a", 0, "The starting memory address.")
}

func runDisasm(cmd *commander.Command, args []string) error {
	if len(args) != 1 {
		cmd.Usage()
		return nil
	}

	bytes, err := ioutil.ReadFile(args[0])
	if err != nil {
		return nil
	}
	if len(bytes) > 0x10000 {
		return fmt.Errorf("File %s is %04X bytes long, which is more than $10000.", args[0], len(bytes))
	}
	if int(disasmAddress)+len(bytes) > 0x10000 {
		return fmt.Errorf("Starting address ($%04X) + file length ($%04X) = $%X, which is > $10000",
			disasmAddress, len(bytes), int(disasmAddress)+len(bytes))
	}

	asm.DisasmBlock(bytes, uint16(disasmAddress), os.Stdout)
	return nil
}
<commit_msg>working on disasm<commit_after>package main

import (
	"fmt"
	"io/ioutil"
	"os"

	"github.com/gonuts/commander"
	"github.com/zellyn/go6502/asm"
)

var cmdDisasm = &commander.Command{
	Run:       runDisasm,
	UsageLine: "disasm [-a address] filename",
	Short:     "disassemble binary files",
	Long: `
Disasm is a very simple disassembler for 6502 binary files.
`,
}

var disasmAddress uint // disasm -a flag
var symbolFile string  // disasm -s flag
var printLabels bool   // disasm -p flag

func init() {
	cmdDisasm.Flag.UintVar(&disasmAddress, "a", 0, "The starting memory address.")
	cmdDisasm.Flag.StringVar(&symbolFile, "s", "", "File of symbol definitions.")
	cmdDisasm.Flag.BoolVar(&printLabels, "p", false, "Print labels for symbols.")
}

func runDisasm(cmd *commander.Command, args []string) error {
	if len(args) != 1 {
		cmd.Usage()
		return nil
	}

	bytes, err := ioutil.ReadFile(args[0])
	if err != nil {
		return err
	}
	if len(bytes) > 0x10000 {
		return fmt.Errorf("File %s is %04X bytes long, which is more than $10000.", args[0], len(bytes))
	}
	if int(disasmAddress)+len(bytes) > 0x10000 {
		return fmt.Errorf("Starting address ($%04X) + file length ($%04X) = $%X, which is > $10000",
			disasmAddress, len(bytes), int(disasmAddress)+len(bytes))
	}

	var s asm.Symbols
	if symbolFile != "" {
		s, err = asm.ReadSymbols(symbolFile)
		if err != nil {
			return err
		}
	} else {
		if printLabels {
			return fmt.Errorf("-p (print labels) specified without -s (symbol table file")
		}
	}

	asm.DisasmBlock(bytes, uint16(disasmAddress), os.Stdout, s, 2, printLabels)
	return nil
}
<|endoftext|>


<commit_before>package controllers

import (
  "github.com/astaxie/beego"
)

type PingController struct {
  beego.Controller
}

type PingResult struct {
  Result bool
}

func (this *PingController) Get() {
  this.Ctx.Output.Context.ResponseWriter.Header().Set("X-Docker-Registry-Version", "0.6.0")
  pingResult := PingResult{Result: true}
  this.Data["json"] = &pingResult
  this.ServeJson()
}
<commit_msg>Add comments in codes.<commit_after>package controllers

import (
  "github.com/astaxie/beego"
)

type PingController struct {
  beego.Controller
}

type PingResult struct {
  Result bool
}

// GET /_ping or /v1/_ping
// API Spec GET /_ping http://docs.docker.io/en/latest/reference/api/registry_api
// Section 2.4 Status
func (this *PingController) Get() {
  this.Ctx.Output.Context.ResponseWriter.Header().Set("X-Docker-Registry-Version", "0.6.0")
  pingResult := PingResult{Result: true}
  this.Data["json"] = &pingResult
  this.ServeJson()
}
<|endoftext|>


<commit_before>package http

import (
	"context"
	"crypto/md5"
	"crypto/sha1"
	"crypto/sha256"
	"crypto/sha512"
	"encoding/hex"
	"fmt"
	"net/http"
	"time"

	"golang.org/x/time/rate"

	"github.com/aptly-dev/aptly/utils"
	"github.com/cavaliercoder/grab"
	"github.com/pkg/errors"

	"github.com/aptly-dev/aptly/aptly"
)

type GrabDownloader struct {
	client    *grab.Client
	progress  aptly.Progress
	maxTries int
	downLimit int64
}

// Check interface
var (
	_ aptly.Downloader = (*GrabDownloader)(nil)
)

// NewGrabDownloader creates new expected downloader
func NewGrabDownloader(downLimit int64, maxTries int, progress aptly.Progress) *GrabDownloader {
func NewGrabDownloader(downLimit int64, progress aptly.Progress) *GrabDownloader {
	client := grab.NewClient()
	return &GrabDownloader{
		client:    client,
		progress:  progress,
		maxTries: maxTries,
		downLimit: downLimit,
	}
}

func (d *GrabDownloader) Download(ctx context.Context, url string, destination string) error {
	return d.DownloadWithChecksum(ctx, url, destination, nil, false)
}

func (d *GrabDownloader) DownloadWithChecksum(ctx context.Context, url string, destination string, expected *utils.ChecksumInfo, ignoreMismatch bool) error {
	maxTries := d.maxTries
	const delayMax = time.Duration(5 * time.Minute)
	delay := time.Duration(1 * time.Second)
	const delayMultiplier = 2
	err := fmt.Errorf("No tries available")
	for maxTries > 0 {
		err = d.download(ctx, url, destination, expected, ignoreMismatch)
		if err == nil {
			// Success
			break
		}
		d.log("Error downloading %s: %v\n", url, err)
		if retryableError(err) {
			maxTries--
			d.log("Retrying download %s: %d\n", url, maxTries)
			time.Sleep(delay)
		} else {
			// Can't retry
			d.log("Cannot retry download %s\n", url)
			break
		}
	}
	return err
}

func (d *GrabDownloader) log(msg string, a ...interface{}) {
	fmt.Printf(msg, a...)
	if d.progress != nil {
		d.progress.Printf(msg, a...)
	}
}

func (d *GrabDownloader) maybeSetupChecksum(req *grab.Request, expected *utils.ChecksumInfo) error {
	if expected == nil {
		// Nothing to setup
		return nil
	}
	if expected.MD5 != "" {
		expected_hash, err := hex.DecodeString(expected.MD5)
		if err != nil {
			return err
		}
		req.SetChecksum(md5.New(), expected_hash, true)
	} else if expected.SHA1 != "" {
		expected_hash, err := hex.DecodeString(expected.SHA1)
		if err != nil {
			return err
		}
		req.SetChecksum(sha1.New(), expected_hash, true)
	} else if expected.SHA256 != "" {
		expected_hash, err := hex.DecodeString(expected.SHA256)
		if err != nil {
			return err
		}
		req.SetChecksum(sha256.New(), expected_hash, true)
	} else if expected.SHA512 != "" {
		expected_hash, err := hex.DecodeString(expected.SHA512)
		if err != nil {
			return err
		}
		req.SetChecksum(sha512.New(), expected_hash, true)
	}
	return nil
}

func (d *GrabDownloader) download(ctx context.Context, url string, destination string, expected *utils.ChecksumInfo, ignoreMismatch bool) error {
	// TODO clean up dest dir on permanent failure
	d.log("Download %s -> %s\n", url, destination)

	req, err := grab.NewRequest(destination, url)
	if err != nil {
		d.log("Error creating new request: %v\n", err)
		return errors.Wrap(err, url)
	}
	req.RateLimiter = rate.NewLimiter(rate.Limit(d.downLimit), int(d.downLimit))

	d.maybeSetupChecksum(req, expected)
	if err != nil {
		d.log("Error setting up checksum: %v\n", err)
		return errors.Wrap(err, url)
	}

	resp := d.client.Do(req)

Loop:
	for {
		select {
		case <-resp.Done:
			// download is complete
			break Loop
		}
	}
	err = resp.Err()
	if err != nil && errors.Is(err, grab.ErrBadChecksum) && ignoreMismatch {
		fmt.Printf("Ignoring checksum mismatch for %s\n", url)
		return nil
	}
	return err
}

func (d *GrabDownloader) GetProgress() aptly.Progress {
	return d.progress
}

func (f *GrabDownloader) GetLength(ctx context.Context, url string) (int64, error) {
	resp, err := http.Head(url)
	if err != nil {
		return -1, err
	}

	if resp.StatusCode < 200 || resp.StatusCode > 299 {
		return -1, &Error{Code: resp.StatusCode, URL: url}
	}

	if resp.ContentLength < 0 {
		return -1, fmt.Errorf("could not determine length of %s", url)
	}

	return resp.ContentLength, nil
}
<commit_msg>Fix error checking<commit_after>package http

import (
	"context"
	"crypto/md5"
	"crypto/sha1"
	"crypto/sha256"
	"crypto/sha512"
	"encoding/hex"
	"fmt"
	"net/http"
	"time"

	"golang.org/x/time/rate"

	"github.com/aptly-dev/aptly/utils"
	"github.com/cavaliercoder/grab"
	"github.com/pkg/errors"

	"github.com/aptly-dev/aptly/aptly"
)

type GrabDownloader struct {
	client    *grab.Client
	progress  aptly.Progress
	maxTries int
	downLimit int64
}

// Check interface
var (
	_ aptly.Downloader = (*GrabDownloader)(nil)
)

// NewGrabDownloader creates new expected downloader
func NewGrabDownloader(downLimit int64, maxTries int, progress aptly.Progress) *GrabDownloader {
func NewGrabDownloader(downLimit int64, progress aptly.Progress) *GrabDownloader {
	client := grab.NewClient()
	return &GrabDownloader{
		client:    client,
		progress:  progress,
		maxTries: maxTries,
		downLimit: downLimit,
	}
}

func (d *GrabDownloader) Download(ctx context.Context, url string, destination string) error {
	return d.DownloadWithChecksum(ctx, url, destination, nil, false)
}

func (d *GrabDownloader) DownloadWithChecksum(ctx context.Context, url string, destination string, expected *utils.ChecksumInfo, ignoreMismatch bool) error {
	maxTries := d.maxTries
	const delayMax = time.Duration(5 * time.Minute)
	delay := time.Duration(1 * time.Second)
	const delayMultiplier = 2
	err := fmt.Errorf("No tries available")
	for maxTries > 0 {
		err = d.download(ctx, url, destination, expected, ignoreMismatch)
		if err == nil {
			// Success
			break
		}
		d.log("Error downloading %s: %v\n", url, err)
		if retryableError(err) {
			maxTries--
			d.log("Retrying download %s: %d\n", url, maxTries)
			time.Sleep(delay)
		} else {
			// Can't retry
			d.log("Cannot retry download %s\n", url)
			break
		}
	}
	return err
}

func (d *GrabDownloader) log(msg string, a ...interface{}) {
	fmt.Printf(msg, a...)
	if d.progress != nil {
		d.progress.Printf(msg, a...)
	}
}

func (d *GrabDownloader) maybeSetupChecksum(req *grab.Request, expected *utils.ChecksumInfo) error {
	if expected == nil {
		// Nothing to setup
		return nil
	}
	if expected.MD5 != "" {
		expected_hash, err := hex.DecodeString(expected.MD5)
		if err != nil {
			return err
		}
		req.SetChecksum(md5.New(), expected_hash, true)
	} else if expected.SHA1 != "" {
		expected_hash, err := hex.DecodeString(expected.SHA1)
		if err != nil {
			return err
		}
		req.SetChecksum(sha1.New(), expected_hash, true)
	} else if expected.SHA256 != "" {
		expected_hash, err := hex.DecodeString(expected.SHA256)
		if err != nil {
			return err
		}
		req.SetChecksum(sha256.New(), expected_hash, true)
	} else if expected.SHA512 != "" {
		expected_hash, err := hex.DecodeString(expected.SHA512)
		if err != nil {
			return err
		}
		req.SetChecksum(sha512.New(), expected_hash, true)
	}
	return nil
}

func (d *GrabDownloader) download(ctx context.Context, url string, destination string, expected *utils.ChecksumInfo, ignoreMismatch bool) error {
	// TODO clean up dest dir on permanent failure
	d.log("Download %s -> %s\n", url, destination)

	req, err := grab.NewRequest(destination, url)
	if err != nil {
		d.log("Error creating new request: %v\n", err)
		return errors.Wrap(err, url)
	}
	req.RateLimiter = rate.NewLimiter(rate.Limit(d.downLimit), int(d.downLimit))

	d.maybeSetupChecksum(req, expected)
	if err != nil {
		d.log("Error setting up checksum: %v\n", err)
		return errors.Wrap(err, url)
	}

	resp := d.client.Do(req)

Loop:
	for {
		select {
		case <-resp.Done:
			// download is complete
			break Loop
		}
	}
	err = resp.Err()
	if err != nil && err == grab.ErrBadChecksum && ignoreMismatch {
		fmt.Printf("Ignoring checksum mismatch for %s\n", url)
		return nil
	}
	return err
}

func (d *GrabDownloader) GetProgress() aptly.Progress {
	return d.progress
}

func (f *GrabDownloader) GetLength(ctx context.Context, url string) (int64, error) {
	resp, err := http.Head(url)
	if err != nil {
		return -1, err
	}

	if resp.StatusCode < 200 || resp.StatusCode > 299 {
		return -1, &Error{Code: resp.StatusCode, URL: url}
	}

	if resp.ContentLength < 0 {
		return -1, fmt.Errorf("could not determine length of %s", url)
	}

	return resp.ContentLength, nil
}
<|endoftext|>


<commit_before>package httpcheck

import (
	"encoding/json"
	"encoding/xml"
	"github.com/braintree/manners"
	"github.com/ivpusic/golog"
	"github.com/stretchr/testify/assert"
	"io/ioutil"
	"net/http"
	"strings"
	"testing"
	"time"
)

type (
	Checker struct {
		t        *testing.T
		handler  http.Handler
		addr     string
		server   *manners.GracefulServer
		request  *http.Request
		response *http.Response
		prefix   string
	}

	Callback func(*http.Response)
)

var (
	logger = golog.GetLogger("github.com/ivpusic/httpcheck")
)

func New(t *testing.T, handler http.Handler, addr string) *Checker {
	logger.Level = golog.INFO
	prefix := ""

	addrParts := strings.Split(addr, ":")
	if addrParts[0] == "" {
		prefix = "http://localhost" + addr
	} else {
		prefix = "http://" + addr
	}

	instance := &Checker{
		t:       t,
		handler: handler,
		addr:    addr,
		prefix:  prefix,
	}
	instance.server = manners.NewServer()

	return instance
}

// Will run HTTP server
func (c *Checker) run() {
	logger.Debug("running server")
	c.server.ListenAndServe(c.addr, c.handler)
}

// Will stop HTTP server
func (c *Checker) stop() {
	logger.Debug("stopping server")
	c.server.Shutdown <- true
	// todo: solve race condition
	time.Sleep(1 * time.Millisecond)
}

// make request /////////////////////////////////////////////////

// If you want to provide you custom http.Request instance, you can do it using this method
// In this case internal http.Request instance won't be created, and passed instane will be used
// for making request
func (c *Checker) TestRequest(request *http.Request) *Checker {
	assert.NotNil(c.t, request, "Request nil")

	c.request = request
	return c
}

// Prepare for testing some part of code which lives on provided path and method.
func (c *Checker) Test(method, path string) *Checker {
	method = strings.ToUpper(method)
	request, err := http.NewRequest(method, c.prefix+path, nil)

	assert.Nil(c.t, err, "Failed to make new request")

	c.request = request
	return c
}

// Final URL for request will be prefix+path.
// Prefix can be something like "http://localhost:3000", and path can be "/some/path" for example.
// Path is provided by user using "Test" method.
// Library will try to figure out URL prefix automatically for you.
// But in case that for your case is not the best, you can set prefix manually
func (c *Checker) SetPrefix(prefix string) *Checker {
	c.prefix = prefix
	return c
}

// headers ///////////////////////////////////////////////////////

// Will put header on request
func (c *Checker) WithHeader(key, value string) *Checker {
	c.request.Header.Set(key, value)
	return c
}

// Will check if response contains header on provided key with provided value
func (c *Checker) HasHeader(key, expectedValue string) *Checker {
	value := c.response.Header.Get(key)
	assert.Exactly(c.t, expectedValue, value)

	return c
}

// cookies ///////////////////////////////////////////////////////

// Will put cookie on request
func (c *Checker) HasCookie(key, expectedValue string) *Checker {
	found := false
	for _, cookie := range c.response.Cookies() {
		if cookie.Name == key && cookie.Value == expectedValue {
			found = true
			break
		}
	}
	assert.True(c.t, found)

	return c
}

// Will ckeck if response contains cookie with provided key and value
func (c *Checker) WithCookie(key, value string) *Checker {
	c.request.AddCookie(&http.Cookie{
		Name:  key,
		Value: value,
	})

	return c
}

// status ////////////////////////////////////////////////////////

// Will ckeck if response status is equal to provided
func (c *Checker) HasStatus(status int) *Checker {
	assert.Exactly(c.t, status, c.response.StatusCode)
	return c
}

// json body /////////////////////////////////////////////////////

// Will ckeck if body contains json with provided value
func (c *Checker) HasJson(value interface{}) *Checker {
	body, err := ioutil.ReadAll(c.response.Body)
	assert.Nil(c.t, err)

	valueBytes, err := json.Marshal(value)
	assert.Nil(c.t, err)
	assert.Equal(c.t, string(valueBytes), string(body))

	return c
}

// Will ckeck if body contains xml with provided value
func (c *Checker) HasXml(value interface{}) *Checker {
	body, err := ioutil.ReadAll(c.response.Body)
	assert.Nil(c.t, err)

	valueBytes, err := xml.Marshal(value)
	assert.Nil(c.t, err)
	assert.Equal(c.t, string(valueBytes), string(body))

	return c
}

// body //////////////////////////////////////////////////////////

// Will check if body contains provided []byte data
func (c *Checker) HasBody(body []byte) *Checker {
	responseBody, err := ioutil.ReadAll(c.response.Body)

	assert.Nil(c.t, err)
	assert.Equal(c.t, body, responseBody)

	return c
}

// Will make reqeust to built request object.
// After request is made, it will save response object for future assertions
// Responsibility of this method is also to start and stop HTTP server
func (c *Checker) Check() *Checker {
	// start server in new goroutine
	go c.run()

	timeout := time.Duration(5 * time.Second)
	client := http.Client{
		Timeout: timeout,
	}

	response, err := client.Do(c.request)
	assert.Nil(c.t, err, "Failed while making new request.", err)

	// save response for assertion checks
	c.response = response

	// stop server
	c.stop()

	return c
}

// Will call provided callback function with current response
func (c *Checker) Cb(cb Callback) {
	cb(c.response)
}
<commit_msg>Reuse one http.Client object for multipli requests to preserve cookies<commit_after>package httpcheck

import (
	"encoding/json"
	"encoding/xml"
	"github.com/braintree/manners"
	"github.com/ivpusic/golog"
	"github.com/stretchr/testify/assert"
	"io/ioutil"
	"net/http"
	"net/http/cookiejar"
	"strings"
	"testing"
	"time"
)

type (
	Checker struct {
		t        *testing.T
		handler  http.Handler
		addr     string
		server   *manners.GracefulServer
		client   *http.Client
		request  *http.Request
		response *http.Response
		prefix   string
		// whether cookies should be saved during multipli calls
		persist bool
	}

	Callback func(*http.Response)
)

var (
	logger = golog.GetLogger("github.com/ivpusic/httpcheck")
)

func New(t *testing.T, handler http.Handler, addr string) *Checker {
	logger.Level = golog.INFO
	prefix := ""

	addrParts := strings.Split(addr, ":")
	if addrParts[0] == "" {
		prefix = "http://localhost" + addr
	} else {
		prefix = "http://" + addr
	}

	instance := &Checker{
		t:       t,
		handler: handler,
		addr:    addr,
		prefix:  prefix,
		client: &http.Client{
			Timeout: time.Duration(5 * time.Second),
		},
		persist: false,
	}
	instance.server = manners.NewServer()

	return instance
}

// Sets whether server-issued http cookies are saved between calls
// Default: False
func (c *Checker) SetPersistCookies(persist bool) {
	c.persist = persist
}

// Will run HTTP server
func (c *Checker) run() {
	logger.Debug("running server")
	c.server.ListenAndServe(c.addr, c.handler)
}

// Will stop HTTP server
func (c *Checker) stop() {
	logger.Debug("stopping server")
	c.server.Shutdown <- true
	// todo: solve race condition
	time.Sleep(1 * time.Millisecond)
}

// make request /////////////////////////////////////////////////

// If you want to provide you custom http.Request instance, you can do it using this method
// In this case internal http.Request instance won't be created, and passed instane will be used
// for making request
func (c *Checker) TestRequest(request *http.Request) *Checker {
	assert.NotNil(c.t, request, "Request nil")

	c.request = request
	return c
}

// Prepare for testing some part of code which lives on provided path and method.
func (c *Checker) Test(method, path string) *Checker {
	method = strings.ToUpper(method)
	request, err := http.NewRequest(method, c.prefix+path, nil)

	assert.Nil(c.t, err, "Failed to make new request")

	c.request = request
	return c
}

// Final URL for request will be prefix+path.
// Prefix can be something like "http://localhost:3000", and path can be "/some/path" for example.
// Path is provided by user using "Test" method.
// Library will try to figure out URL prefix automatically for you.
// But in case that for your case is not the best, you can set prefix manually
func (c *Checker) SetPrefix(prefix string) *Checker {
	c.prefix = prefix
	return c
}

// headers ///////////////////////////////////////////////////////

// Will put header on request
func (c *Checker) WithHeader(key, value string) *Checker {
	c.request.Header.Set(key, value)
	return c
}

// Will check if response contains header on provided key with provided value
func (c *Checker) HasHeader(key, expectedValue string) *Checker {
	value := c.response.Header.Get(key)
	assert.Exactly(c.t, expectedValue, value)

	return c
}

// cookies ///////////////////////////////////////////////////////

// Will put cookie on request
func (c *Checker) HasCookie(key, expectedValue string) *Checker {
	found := false
	for _, cookie := range c.response.Cookies() {
		if cookie.Name == key && cookie.Value == expectedValue {
			found = true
			break
		}
	}
	assert.True(c.t, found)

	return c
}

// Will ckeck if response contains cookie with provided key and value
func (c *Checker) WithCookie(key, value string) *Checker {
	c.request.AddCookie(&http.Cookie{
		Name:  key,
		Value: value,
	})

	return c
}

// status ////////////////////////////////////////////////////////

// Will ckeck if response status is equal to provided
func (c *Checker) HasStatus(status int) *Checker {
	assert.Exactly(c.t, status, c.response.StatusCode)
	return c
}

// json body /////////////////////////////////////////////////////

// Will ckeck if body contains json with provided value
func (c *Checker) HasJson(value interface{}) *Checker {
	body, err := ioutil.ReadAll(c.response.Body)
	assert.Nil(c.t, err)

	valueBytes, err := json.Marshal(value)
	assert.Nil(c.t, err)
	assert.Equal(c.t, string(valueBytes), string(body))

	return c
}

// Will ckeck if body contains xml with provided value
func (c *Checker) HasXml(value interface{}) *Checker {
	body, err := ioutil.ReadAll(c.response.Body)
	assert.Nil(c.t, err)

	valueBytes, err := xml.Marshal(value)
	assert.Nil(c.t, err)
	assert.Equal(c.t, string(valueBytes), string(body))

	return c
}

// body //////////////////////////////////////////////////////////

// Will check if body contains provided []byte data
func (c *Checker) HasBody(body []byte) *Checker {
	responseBody, err := ioutil.ReadAll(c.response.Body)

	assert.Nil(c.t, err)
	assert.Equal(c.t, body, responseBody)

	return c
}

// Will make reqeust to built request object.
// After request is made, it will save response object for future assertions
// Responsibility of this method is also to start and stop HTTP server
func (c *Checker) Check() *Checker {
	// start server in new goroutine
	go c.run()

	if !c.persist {
		jar, _ := cookiejar.New(nil)
		c.client.Jar = jar
	}

	response, err := c.client.Do(c.request)
	assert.Nil(c.t, err, "Failed while making new request.", err)

	// save response for assertion checks
	c.response = response

	// stop server
	c.stop()

	return c
}

// Will call provided callback function with current response
func (c *Checker) Cb(cb Callback) {
	cb(c.response)
}
<|endoftext|>


<commit_before>package httpd

import (
	"io"
	"net/http"

	"github.com/Symantec/Dominator/lib/log"
	"github.com/Symantec/Dominator/lib/net/reverseconnection"
	"github.com/Symantec/tricorder/go/tricorder"
)

type HtmlWriter interface {
	WriteHtml(writer io.Writer)
}

type RequestHtmlWriter interface {
	HtmlWriter
	RequestWriteHtml(writer io.Writer, req *http.Request)
}

var htmlWriters []HtmlWriter

func StartServer(portNum uint, logger log.DebugLogger) error {
	listener, err := reverseconnection.Listen("tcp", portNum, logger)
	if err != nil {
		return err
	}
	err = listener.RequestConnections(tricorder.CollectorServiceName)
	if err != nil {
		return err
	}
	http.HandleFunc("/", statusHandler)
	http.HandleFunc("/favicon.ico", func(http.ResponseWriter, *http.Request) {})
	go http.Serve(listener, nil)
	return nil
}

func AddHtmlWriter(htmlWriter HtmlWriter) {
	htmlWriters = append(htmlWriters, htmlWriter)
}
<commit_msg>Add "security headers" (compliance checkbox) to HTTP responses.<commit_after>package httpd

import (
	"io"
	"net/http"

	"github.com/Symantec/Dominator/lib/html"
	"github.com/Symantec/Dominator/lib/log"
	"github.com/Symantec/Dominator/lib/net/reverseconnection"
	"github.com/Symantec/tricorder/go/tricorder"
)

type HtmlWriter interface {
	WriteHtml(writer io.Writer)
}

type RequestHtmlWriter interface {
	HtmlWriter
	RequestWriteHtml(writer io.Writer, req *http.Request)
}

var htmlWriters []HtmlWriter

func StartServer(portNum uint, logger log.DebugLogger) error {
	listener, err := reverseconnection.Listen("tcp", portNum, logger)
	if err != nil {
		return err
	}
	err = listener.RequestConnections(tricorder.CollectorServiceName)
	if err != nil {
		return err
	}
	html.HandleFunc("/", statusHandler)
	html.HandleFunc("/favicon.ico", func(http.ResponseWriter, *http.Request) {})
	go http.Serve(listener, nil)
	return nil
}

func AddHtmlWriter(htmlWriter HtmlWriter) {
	htmlWriters = append(htmlWriters, htmlWriter)
}
<|endoftext|>


<commit_before>package main

import (
	"io"

	"github.com/itchio/wharf/pwr"

	"gopkg.in/kothar/brotli-go.v0/dec"
	"gopkg.in/kothar/brotli-go.v0/enc"
)

type brotliCompressor struct{}

func (bc *brotliCompressor) Apply(writer io.Writer, quality int32) (io.Writer, error) {
	params := enc.NewBrotliParams()
	params.SetQuality(int(quality))
	bw := enc.NewBrotliWriter(params, writer)
	return bw, nil
}

type brotliDecompressor struct{}

func (bc *brotliDecompressor) Apply(reader io.Reader) (io.Reader, error) {
	br := dec.NewBrotliReader(reader)
	return br, nil
}

func init() {
	pwr.RegisterCompressor(pwr.CompressionAlgorithm_BROTLI, &brotliCompressor{})
	pwr.RegisterDecompressor(pwr.CompressionAlgorithm_BROTLI, &brotliDecompressor{})
}
<commit_msg>Use wharf's (de)compressors<commit_after>package main

import (
	_ "github.com/itchio/wharf/compressors/cbrotli"
	_ "github.com/itchio/wharf/decompressors/cbrotli"
)
<|endoftext|>


<commit_before>package postcard

import (
	"fmt"
	"io/ioutil"
	"strings"

	"github.com/davidnix/lob-cli/lob"
	"github.com/davidnix/lob-cli/parse"
	cli "gopkg.in/urfave/cli.v1"
)

// Send sends postcards from csv of addresses
func Send(c *cli.Context) error {
	var err error
	a, err := parse.Addresses(c)
	if err != nil {
		return err
	}

	fmt.Println("Parsed", len(a), "addresses")
	if len(a) == 0 {
		return nil
	}
	front, back, err := openTemplates(c)
	if err != nil {
		return err
	}

	client := lob.NewClient(c.GlobalString("api-key"))

	fromAddress := parse.FromAddress(c)
	var errors []string
	for _, v := range a {
		var localErr error
		verified, localErr := client.VerifyAddress(v)
		if localErr != nil {
			fmt.Println(localErr)
			continue
		}
		fmt.Println("Sending postcard for", verified)
		localErr = client.SendPostcard(fromAddress, verified, front, back)
		if localErr != nil {
			fmt.Println("Error:", verified, localErr)
		}
	}

	if len(errors) > 0 {
		return fmt.Errorf(strings.Join(errors, "\n"))
	}

	fmt.Println("Sending postcards complete!")
	return nil
}

func openTemplates(c *cli.Context) (string, string, error) {
	var err error
	frontURI := c.String("front")
	front, err := ioutil.ReadFile(frontURI)
	if err != nil {
		return "", "", fmt.Errorf("Invalid front file %v: error %v", frontURI, err)
	}

	backURI := c.String("back")
	back, err := ioutil.ReadFile(backURI)
	if err != nil {
		return "", "", fmt.Errorf("Invalid back file %v: error %v", backURI, err)
	}

	return string(front), string(back), nil
}
<commit_msg>color some output<commit_after>package postcard

import (
	"fmt"
	"io/ioutil"

	"github.com/davidnix/lob-cli/lob"
	"github.com/davidnix/lob-cli/parse"
	"github.com/fatih/color"
	cli "gopkg.in/urfave/cli.v1"
)

// Send sends postcards from csv of addresses
func Send(c *cli.Context) error {
	var err error
	a, err := parse.Addresses(c)
	if err != nil {
		return err
	}

	fmt.Println("Parsed", len(a), "addresses")
	if len(a) == 0 {
		return nil
	}
	front, back, err := openTemplates(c)
	if err != nil {
		return err
	}

	client := lob.NewClient(c.GlobalString("api-key"))

	fromAddress := parse.FromAddress(c)
	for _, v := range a {
		var localErr error
		verified, localErr := client.VerifyAddress(v)
		if localErr != nil {
			color.Red(localErr.Error())
			continue
		}
		fmt.Println("Sending postcard for", verified)
		localErr = client.SendPostcard(fromAddress, verified, front, back)
		if localErr != nil {
			color.Red(fmt.Sprint("Error:", verified, localErr.Error(), "\n"))
		}
	}

	color.Green("Sending postcards complete!")
	return nil
}

func openTemplates(c *cli.Context) (string, string, error) {
	var err error
	frontURI := c.String("front")
	front, err := ioutil.ReadFile(frontURI)
	if err != nil {
		return "", "", fmt.Errorf("Invalid front file %v: error %v", frontURI, err)
	}

	backURI := c.String("back")
	back, err := ioutil.ReadFile(backURI)
	if err != nil {
		return "", "", fmt.Errorf("Invalid back file %v: error %v", backURI, err)
	}

	return string(front), string(back), nil
}
<|endoftext|>