<commit_before>package main

import (
	"net"
	"bufio"
	"image/color"
	"fmt"
	"math"
	"math/rand"
)

type SideType int

const (
	SIDE_OUR     SideType = -1 + iota
	SIDE_NEUTRAL
	SIDE_ENEMY
)

type AreaType int

const (
	AREA_UNKNOWN AreaType = 0 + iota
	AREA_FOREST
	AREA_SWAMP
	AREA_RAIN
	AREA_CLOUD
)

type UnitType int

const (
	UNIT_UNKNOWN    UnitType = 0 + iota
	UNIT_TANK
	UNIT_IFV
	UNIT_ARRV
	UNIT_HELICOPTER
	UNIT_FIGHTER
)

type RewindClient struct {
	conn   net.Conn
	reader *bufio.Reader
	writer *bufio.Writer
}

func Client() *RewindClient {
	var host, port string

	host, port = "127.0.0.1", "9111"

	cli := new(RewindClient);
	if err := cli.Dial(host, port); err == nil {
		return cli;
	} else {
		panic(err)
	}
}

func (c *RewindClient) Close() {
	c.conn.Close();
}

func (c *RewindClient) Dial(host, port string) (err error) {
	if c.conn, err = net.Dial("tcp", host+":"+port); err == nil {
		c.reader = bufio.NewReader(c.conn)
		c.writer = bufio.NewWriter(c.conn)
	}

	return
}

func getIntFromColor(color color.Color) uint32 {
	var red, green, blue, alpha = color.RGBA();
	var colorInt = (red << 24) + (green << 16) + (blue << 8) + (alpha);
	return colorInt
}

func (c *RewindClient) circle(x float64, y float64, r float64, color color.Color, layer int) {
	c.writeString(fmt.Sprintf("{\"type\": \"circle\", \"x\": %f, \"y\": %f, \"r\": %f, \"color\": %d, \"layer\": %d}", x, y, r, getIntFromColor(color), layer));
}

func (c *RewindClient) popup(x float64, y float64, r float64, text string) {
	c.writeString(fmt.Sprintf("{\"type\": \"popup\", \"x\": %f, \"y\": %f, \"r\": %f, \"text\": \"%s \"}", x, y, r, text));
}

func (c *RewindClient) rect(x1 float64, y1 float64, x2 float64, y2 float64, color color.Color, layer int) {
	c.writeString(fmt.Sprintf("{\"type\": \"rectangle\", \"x1\": %f, \"y1\": %f, \"x2\": %f, \"y2\": %f, \"color\": %d, \"layer\": %d}", x1, y1, x2, y2, getIntFromColor(color), layer));
}

func (c *RewindClient) line(x1 float64, y1 float64, x2 float64, y2 float64, color color.Color, layer int) {
	c.writeString(fmt.Sprintf("{\"type\": \"line\", \"x1\": %f, \"y1\": %f, \"x2\": %f, \"y2\": %f, \"color\": %d, \"layer\": %d}", x1, y1, x2, y2, getIntFromColor(color), layer));
}

func (c *RewindClient) livingUnit(x float64, y float64, r float64, hp int, maxHp int, side SideType, course float64, unit UnitType, remCooldown int, maxCooldown int, selected bool) {
	var isSelected int = 0
	if selected {
		isSelected = 1
	}
	c.writeString(fmt.Sprintf("{\"type\": \"unit\", \"x\": %f, \"y\": %f, \"r\": %f, \"hp\": %d, \"max_hp\": %d, \"enemy\": %d, \"unit_type\":%d, \"course\": %.3f,"+
		"\"rem_cooldown\":%d, \"cooldown\":%d, \"selected\":%d }",
		x, y, r, hp, maxHp, side, unit, course, remCooldown, maxCooldown, isSelected));
}

func (c *RewindClient) livingUnitSmaller(x float64, y float64, r float64, hp int, maxHp int, side SideType) {
	c.livingUnit(x, y, r, hp, maxHp, side, 0, UNIT_UNKNOWN, 0, 0, false)
}

func (c *RewindClient) areaDescription(cellX int, cellY int, areaType AreaType) {
	fmt.Println(fmt.Sprintf("{\"type\": \"area\", \"x\": %d, \"y\": %d, \"area_type\": %d}", cellX, cellY, areaType));
	c.writeString(fmt.Sprintf("{\"type\": \"area\", \"x\": %d, \"y\": %d, \"area_type\": %d}", cellX, cellY, areaType));
}

func (c *RewindClient) message(str string) {
	c.writeString(fmt.Sprintf("{\"type\": \"message\", \"message\" : \"%s\"}", str));
}

func (c *RewindClient) endFrame() {
	c.writeString("{\"type\":\"end\"}");
}

func (c *RewindClient) writeString(v string) {
	if _, err := c.writer.WriteString(v); err != nil {
		panic(err)
	}
	c.flush();
}

func (c *RewindClient) flush() {
	if err := c.writer.Flush(); err != nil {
		panic(err)
	}
}

func main() {
	rc := Client()
	worldSize := 1024;
	random := rand.New(rand.NewSource(123));
	for x := 0; x < worldSize/32; x++ {
		for y := 0; y < worldSize/32; y++ {
			rc.areaDescription(x, y, AreaType(random.Intn(5)));
		}
	}
	rc.message("Hello World");
	rc.endFrame();
	for i := 0; i < 2000; i++ {
		rc.message(fmt.Sprintf("Step %d", i));
		for j := 0; j < 100; j++ {
			color := color.RGBA{uint8(random.Intn(256)), uint8(random.Intn(256)), uint8(random.Intn(256)), uint8(random.Intn(256))};
			unitX := random.Float64() * float64(worldSize);
			unitY := random.Float64()*32 + float64(i);
			rc.livingUnit(
				unitX,
				unitY,
				2+random.Float64()*10,
				10,
				100,
				SideType(random.Intn(3)-1),
				math.Pi*random.Float64(),
				UnitType(random.Intn(6)),
				int(60*random.Float32()),
				60,
				false);
			rc.line(unitX, unitY, random.Float64()*float64(worldSize), random.Float64()*float64(worldSize), color, 3);
			circleX := unitX + random.Float64()*40 - 20;
			circleY := unitY + random.Float64()*40 - 20;
			rc.circle(circleX, circleY, 10+random.Float64()*10, color, 2);
			rectX1 := circleX + random.Float64()*100;
			rectY1 := circleY + random.Float64()*100;
			rc.rect(rectX1, rectY1, rectX1+random.Float64()*40, rectY1+random.Float64()*40, color, 1);
		}
		rc.endFrame();
	}

	rc.message("Bye!");
	rc.endFrame();
	rc.Close();
}
<commit_msg>Update rewind_client.go<commit_after>package main

import (
	"net"
	"bufio"
	"image/color"
	"fmt"
	"math"
	"math/rand"
)

type SideType int

const (
	SIDE_OUR     SideType = -1 + iota
	SIDE_NEUTRAL
	SIDE_ENEMY
)

type AreaType int

const (
	AREA_UNKNOWN AreaType = 0 + iota
	AREA_FOREST
	AREA_SWAMP
	AREA_RAIN
	AREA_CLOUD
)

type UnitType int

const (
	UNIT_UNKNOWN    UnitType = 0 + iota
	UNIT_TANK
	UNIT_IFV
	UNIT_ARRV
	UNIT_HELICOPTER
	UNIT_FIGHTER
)

type RewindClient struct {
	conn   net.Conn
	reader *bufio.Reader
	writer *bufio.Writer
}

func Client() *RewindClient {
	var host, port string

	host, port = "127.0.0.1", "9111"

	cli := new(RewindClient);
	if err := cli.Dial(host, port); err == nil {
		return cli;
	} else {
		panic(err)
	}
}

func (c *RewindClient) Close() {
	c.conn.Close();
}

func (c *RewindClient) Dial(host, port string) (err error) {
	if c.conn, err = net.Dial("tcp", host+":"+port); err == nil {
		c.reader = bufio.NewReader(c.conn)
		c.writer = bufio.NewWriter(c.conn)
	}

	return
}

func getIntFromColor(color color.Color) uint32 {
	var red, green, blue, alpha = color.RGBA();
	var colorInt = (red << 24) + (green << 16) + (blue << 8) + (alpha);
	return colorInt
}

func (c *RewindClient) circle(x float64, y float64, r float64, color color.Color, layer int) {
	c.writeString(fmt.Sprintf("{\"type\": \"circle\", \"x\": %f, \"y\": %f, \"r\": %f, \"color\": %d, \"layer\": %d}", x, y, r, getIntFromColor(color), layer));
}

func (c *RewindClient) popup(x float64, y float64, r float64, text string) {
	c.writeString(fmt.Sprintf("{\"type\": \"popup\", \"x\": %f, \"y\": %f, \"r\": %f, \"text\": \"%s \"}", x, y, r, text));
}

func (c *RewindClient) rect(x1 float64, y1 float64, x2 float64, y2 float64, color color.Color, layer int) {
	c.writeString(fmt.Sprintf("{\"type\": \"rectangle\", \"x1\": %f, \"y1\": %f, \"x2\": %f, \"y2\": %f, \"color\": %d, \"layer\": %d}", x1, y1, x2, y2, getIntFromColor(color), layer));
}

func (c *RewindClient) line(x1 float64, y1 float64, x2 float64, y2 float64, color color.Color, layer int) {
	c.writeString(fmt.Sprintf("{\"type\": \"line\", \"x1\": %f, \"y1\": %f, \"x2\": %f, \"y2\": %f, \"color\": %d, \"layer\": %d}", x1, y1, x2, y2, getIntFromColor(color), layer));
}

func (c *RewindClient) livingUnit(x float64, y float64, r float64, hp int, maxHp int, side SideType, course float64, unit UnitType, remCooldown int, maxCooldown int, selected bool) {
	var isSelected int = 0
	if selected {
		isSelected = 1
	}
	c.writeString(fmt.Sprintf("{\"type\": \"unit\", \"x\": %f, \"y\": %f, \"r\": %f, \"hp\": %d, \"max_hp\": %d, \"enemy\": %d, \"unit_type\":%d, \"course\": %.3f,"+
		"\"rem_cooldown\":%d, \"cooldown\":%d, \"selected\":%d }",
		x, y, r, hp, maxHp, side, unit, course, remCooldown, maxCooldown, isSelected));
}

func (c *RewindClient) livingUnitSmaller(x float64, y float64, r float64, hp int, maxHp int, side SideType) {
	c.livingUnit(x, y, r, hp, maxHp, side, 0, UNIT_UNKNOWN, 0, 0, false)
}

func (c *RewindClient) areaDescription(cellX int, cellY int, areaType AreaType) {
	c.writeString(fmt.Sprintf("{\"type\": \"area\", \"x\": %d, \"y\": %d, \"area_type\": %d}", cellX, cellY, areaType));
}

func (c *RewindClient) message(str string) {
	c.writeString(fmt.Sprintf("{\"type\": \"message\", \"message\" : \"%s\"}", str));
}

func (c *RewindClient) endFrame() {
	c.writeString("{\"type\":\"end\"}");
}

func (c *RewindClient) writeString(v string) {
	if _, err := c.writer.WriteString(v); err != nil {
		panic(err)
	}
	c.flush();
}

func (c *RewindClient) flush() {
	if err := c.writer.Flush(); err != nil {
		panic(err)
	}
}

func main() {
	rc := Client()
	worldSize := 1024;
	random := rand.New(rand.NewSource(123));
	for x := 0; x < worldSize/32; x++ {
		for y := 0; y < worldSize/32; y++ {
			rc.areaDescription(x, y, AreaType(random.Intn(5)));
		}
	}
	rc.message("Hello World");
	rc.endFrame();
	for i := 0; i < 2000; i++ {
		rc.message(fmt.Sprintf("Step %d", i));
		for j := 0; j < 100; j++ {
			color := color.RGBA{uint8(random.Intn(256)), uint8(random.Intn(256)), uint8(random.Intn(256)), uint8(random.Intn(256))};
			unitX := random.Float64() * float64(worldSize);
			unitY := random.Float64()*32 + float64(i);
			rc.livingUnit(
				unitX,
				unitY,
				2+random.Float64()*10,
				10,
				100,
				SideType(random.Intn(3)-1),
				math.Pi*random.Float64(),
				UnitType(random.Intn(6)),
				int(60*random.Float32()),
				60,
				false);
			rc.line(unitX, unitY, random.Float64()*float64(worldSize), random.Float64()*float64(worldSize), color, 3);
			circleX := unitX + random.Float64()*40 - 20;
			circleY := unitY + random.Float64()*40 - 20;
			rc.circle(circleX, circleY, 10+random.Float64()*10, color, 2);
			rectX1 := circleX + random.Float64()*100;
			rectY1 := circleY + random.Float64()*100;
			rc.rect(rectX1, rectY1, rectX1+random.Float64()*40, rectY1+random.Float64()*40, color, 1);
		}
		rc.endFrame();
	}

	rc.message("Bye!");
	rc.endFrame();
	rc.Close();
}
<|endoftext|>


<commit_before>package s3api

import (
	"context"
	"encoding/xml"
	"fmt"
	"math"
	"net/http"
	"time"

	xhttp "github.com/chrislusf/seaweedfs/weed/s3api/http"
	"github.com/chrislusf/seaweedfs/weed/s3api/s3err"

	"github.com/aws/aws-sdk-go/aws"
	"github.com/aws/aws-sdk-go/service/s3"

	"github.com/chrislusf/seaweedfs/weed/glog"
	"github.com/chrislusf/seaweedfs/weed/pb/filer_pb"
)

type ListAllMyBucketsResult struct {
	XMLName xml.Name `xml:"http://s3.amazonaws.com/doc/2006-03-01/ ListAllMyBucketsResult"`
	Owner   *s3.Owner
	Buckets []*s3.Bucket `xml:"Buckets>Bucket"`
}

func (s3a *S3ApiServer) ListBucketsHandler(w http.ResponseWriter, r *http.Request) {

	var response ListAllMyBucketsResult

	entries, _, err := s3a.list(s3a.option.BucketsPath, "", "", false, math.MaxInt32)

	if err != nil {
		writeErrorResponse(w, s3err.ErrInternalError, r.URL)
		return
	}

	identityId := r.Header.Get(xhttp.AmzIdentityId)

	var buckets []*s3.Bucket
	for _, entry := range entries {
		if entry.IsDirectory {
			if !s3a.hasAccess(r, entry) {
				continue
			}
			buckets = append(buckets, &s3.Bucket{
				Name:         aws.String(entry.Name),
				CreationDate: aws.Time(time.Unix(entry.Attributes.Crtime, 0).UTC()),
			})
		}
	}

	response = ListAllMyBucketsResult{
		Owner: &s3.Owner{
			ID:          aws.String(identityId),
			DisplayName: aws.String(identityId),
		},
		Buckets: buckets,
	}

	writeSuccessResponseXML(w, encodeResponse(response))
}

func (s3a *S3ApiServer) PutBucketHandler(w http.ResponseWriter, r *http.Request) {

	bucket, _ := getBucketAndObject(r)

	// avoid duplicated buckets
	errCode := s3err.ErrNone
	if err := s3a.WithFilerClient(func(client filer_pb.SeaweedFilerClient) error {
		if resp, err := client.CollectionList(context.Background(), &filer_pb.CollectionListRequest{
			IncludeEcVolumes:     true,
			IncludeNormalVolumes: true,
		}); err != nil {
			glog.Errorf("list collection: %v", err)
			return fmt.Errorf("list collections: %v", err)
		} else {
			for _, c := range resp.Collections {
				if bucket == c.Name {
					errCode = s3err.ErrBucketAlreadyExists
					break
				}
			}
		}
		return nil
	}); err != nil {
		writeErrorResponse(w, s3err.ErrInternalError, r.URL)
		return
	}
	if exist, err := s3a.exists(s3a.option.BucketsPath, bucket, true); err == nil && exist {
		errCode = s3err.ErrBucketAlreadyExists
	}
	if errCode != s3err.ErrNone {
		writeErrorResponse(w, errCode, r.URL)
		return
	}

	fn := func(entry *filer_pb.Entry) {
		if identityId := r.Header.Get(xhttp.AmzIdentityId); identityId != "" {
			if entry.Extended == nil {
				entry.Extended = make(map[string][]byte)
			}
			entry.Extended[xhttp.AmzIdentityId] = []byte(identityId)
		}
	}

	// create the folder for bucket, but lazily create actual collection
	if err := s3a.mkdir(s3a.option.BucketsPath, bucket, fn); err != nil {
		glog.Errorf("PutBucketHandler mkdir: %v", err)
		writeErrorResponse(w, s3err.ErrInternalError, r.URL)
		return
	}

	writeSuccessResponseEmpty(w)
}

func (s3a *S3ApiServer) DeleteBucketHandler(w http.ResponseWriter, r *http.Request) {

	bucket, _ := getBucketAndObject(r)

	entry, err := s3a.getEntry(s3a.option.BucketsPath, bucket)
	if entry == nil || err == filer_pb.ErrNotFound {
		writeErrorResponse(w, s3err.ErrNoSuchBucket, r.URL)
		return
	}

	if !s3a.hasAccess(r, entry) {
		writeErrorResponse(w, s3err.ErrAccessDenied, r.URL)
		return
	}

	err = s3a.WithFilerClient(func(client filer_pb.SeaweedFilerClient) error {

		// delete collection
		deleteCollectionRequest := &filer_pb.DeleteCollectionRequest{
			Collection: bucket,
		}

		glog.V(1).Infof("delete collection: %v", deleteCollectionRequest)
		if _, err := client.DeleteCollection(context.Background(), deleteCollectionRequest); err != nil {
			return fmt.Errorf("delete collection %s: %v", bucket, err)
		}

		return nil
	})

	err = s3a.rm(s3a.option.BucketsPath, bucket, false, true)

	if err != nil {
		writeErrorResponse(w, s3err.ErrInternalError, r.URL)
		return
	}

	writeResponse(w, http.StatusNoContent, nil, mimeNone)
}

func (s3a *S3ApiServer) HeadBucketHandler(w http.ResponseWriter, r *http.Request) {

	bucket, _ := getBucketAndObject(r)

	entry, err := s3a.getEntry(s3a.option.BucketsPath, bucket)
	if entry == nil || err == filer_pb.ErrNotFound {
		writeErrorResponse(w, s3err.ErrNoSuchBucket, r.URL)
		return
	}

	if !s3a.hasAccess(r, entry) {
		writeErrorResponse(w, s3err.ErrAccessDenied, r.URL)
		return
	}

	writeSuccessResponseEmpty(w)
}

func (s3a *S3ApiServer) hasAccess(r *http.Request, entry *filer_pb.Entry) bool {
	isAdmin := r.Header.Get(xhttp.AmzIsAdmin) != ""
	if isAdmin {
		return true
	}
	if entry.Extended == nil {
		return true
	}

	identityId := r.Header.Get(xhttp.AmzIdentityId)
	if id, ok := entry.Extended[xhttp.AmzIdentityId]; ok {
		if identityId != string(id) {
			return false
		}
	}
	return true
}<commit_msg>adjust check bucket if exist or has access.<commit_after>package s3api

import (
	"context"
	"encoding/xml"
	"fmt"
	"math"
	"net/http"
	"time"

	xhttp "github.com/chrislusf/seaweedfs/weed/s3api/http"
	"github.com/chrislusf/seaweedfs/weed/s3api/s3err"

	"github.com/aws/aws-sdk-go/aws"
	"github.com/aws/aws-sdk-go/service/s3"

	"github.com/chrislusf/seaweedfs/weed/glog"
	"github.com/chrislusf/seaweedfs/weed/pb/filer_pb"
)

type ListAllMyBucketsResult struct {
	XMLName xml.Name `xml:"http://s3.amazonaws.com/doc/2006-03-01/ ListAllMyBucketsResult"`
	Owner   *s3.Owner
	Buckets []*s3.Bucket `xml:"Buckets>Bucket"`
}

func (s3a *S3ApiServer) ListBucketsHandler(w http.ResponseWriter, r *http.Request) {

	var response ListAllMyBucketsResult

	entries, _, err := s3a.list(s3a.option.BucketsPath, "", "", false, math.MaxInt32)

	if err != nil {
		writeErrorResponse(w, s3err.ErrInternalError, r.URL)
		return
	}

	identityId := r.Header.Get(xhttp.AmzIdentityId)

	var buckets []*s3.Bucket
	for _, entry := range entries {
		if entry.IsDirectory {
			if !s3a.hasAccess(r, entry) {
				continue
			}
			buckets = append(buckets, &s3.Bucket{
				Name:         aws.String(entry.Name),
				CreationDate: aws.Time(time.Unix(entry.Attributes.Crtime, 0).UTC()),
			})
		}
	}

	response = ListAllMyBucketsResult{
		Owner: &s3.Owner{
			ID:          aws.String(identityId),
			DisplayName: aws.String(identityId),
		},
		Buckets: buckets,
	}

	writeSuccessResponseXML(w, encodeResponse(response))
}

func (s3a *S3ApiServer) PutBucketHandler(w http.ResponseWriter, r *http.Request) {

	bucket, _ := getBucketAndObject(r)

	// avoid duplicated buckets
	errCode := s3err.ErrNone
	if err := s3a.WithFilerClient(func(client filer_pb.SeaweedFilerClient) error {
		if resp, err := client.CollectionList(context.Background(), &filer_pb.CollectionListRequest{
			IncludeEcVolumes:     true,
			IncludeNormalVolumes: true,
		}); err != nil {
			glog.Errorf("list collection: %v", err)
			return fmt.Errorf("list collections: %v", err)
		} else {
			for _, c := range resp.Collections {
				if bucket == c.Name {
					errCode = s3err.ErrBucketAlreadyExists
					break
				}
			}
		}
		return nil
	}); err != nil {
		writeErrorResponse(w, s3err.ErrInternalError, r.URL)
		return
	}
	if exist, err := s3a.exists(s3a.option.BucketsPath, bucket, true); err == nil && exist {
		errCode = s3err.ErrBucketAlreadyExists
	}
	if errCode != s3err.ErrNone {
		writeErrorResponse(w, errCode, r.URL)
		return
	}

	fn := func(entry *filer_pb.Entry) {
		if identityId := r.Header.Get(xhttp.AmzIdentityId); identityId != "" {
			if entry.Extended == nil {
				entry.Extended = make(map[string][]byte)
			}
			entry.Extended[xhttp.AmzIdentityId] = []byte(identityId)
		}
	}

	// create the folder for bucket, but lazily create actual collection
	if err := s3a.mkdir(s3a.option.BucketsPath, bucket, fn); err != nil {
		glog.Errorf("PutBucketHandler mkdir: %v", err)
		writeErrorResponse(w, s3err.ErrInternalError, r.URL)
		return
	}

	writeSuccessResponseEmpty(w)
}

func (s3a *S3ApiServer) DeleteBucketHandler(w http.ResponseWriter, r *http.Request) {

	bucket, _ := getBucketAndObject(r)

	if err := s3a.checkBucket(r, bucket); err != s3err.ErrNone {
		writeErrorResponse(w, err, r.URL)
		return
	}

	err := s3a.WithFilerClient(func(client filer_pb.SeaweedFilerClient) error {

		// delete collection
		deleteCollectionRequest := &filer_pb.DeleteCollectionRequest{
			Collection: bucket,
		}

		glog.V(1).Infof("delete collection: %v", deleteCollectionRequest)
		if _, err := client.DeleteCollection(context.Background(), deleteCollectionRequest); err != nil {
			return fmt.Errorf("delete collection %s: %v", bucket, err)
		}

		return nil
	})

	err = s3a.rm(s3a.option.BucketsPath, bucket, false, true)

	if err != nil {
		writeErrorResponse(w, s3err.ErrInternalError, r.URL)
		return
	}

	writeResponse(w, http.StatusNoContent, nil, mimeNone)
}

func (s3a *S3ApiServer) HeadBucketHandler(w http.ResponseWriter, r *http.Request) {

	bucket, _ := getBucketAndObject(r)

	if err := s3a.checkBucket(r, bucket); err != s3err.ErrNone {
		writeErrorResponse(w, err, r.URL)
		return
	}

	writeSuccessResponseEmpty(w)
}

func (s3a *S3ApiServer) checkBucket(r *http.Request, bucket string) s3err.ErrorCode {
	entry, err := s3a.getEntry(s3a.option.BucketsPath, bucket)
	if entry == nil || err == filer_pb.ErrNotFound {
		return s3err.ErrNoSuchBucket
	}

	if !s3a.hasAccess(r, entry) {
		return s3err.ErrAccessDenied
	}
	return s3err.ErrNone
}

func (s3a *S3ApiServer) hasAccess(r *http.Request, entry *filer_pb.Entry) bool {
	isAdmin := r.Header.Get(xhttp.AmzIsAdmin) != ""
	if isAdmin {
		return true
	}
	if entry.Extended == nil {
		return true
	}

	identityId := r.Header.Get(xhttp.AmzIdentityId)
	if id, ok := entry.Extended[xhttp.AmzIdentityId]; ok {
		if identityId != string(id) {
			return false
		}
	}
	return true
}
<|endoftext|>


<commit_before>package main

import (
	"flag"
	"fmt"
	"koding/newkite/kite"
	"koding/newkite/protocol"
)

var port = flag.String("port", "", "port to bind itself")

func main() {
	flag.Parse()

	options := &protocol.Options{
		Kitename:    "mathworker",
		Version:     "1",
		Port:        *port,
		Region:      "localhost",
		Environment: "development",
		PublicIP:    "127.0.0.1",
	}

	k := kite.New(options)

	k.HandleFunc("square", Square)

	k.Run()
}

func Square(r *kite.Request) (interface{}, error) {
	a, err := r.Args.Float64()
	if err != nil {
		return nil, err
	}

	result := a * a

	fmt.Printf("Kite call, sending result '%s' back\n", result)

	// Print a log on remote Kite.
	r.RemoteKite.Go("log", fmt.Sprintf("You have requested square of: %f", a))

	return result, nil
}
<commit_msg>kite: fix log in example<commit_after>package main

import (
	"flag"
	"fmt"
	"koding/newkite/kite"
	"koding/newkite/protocol"
)

var port = flag.String("port", "", "port to bind itself")

func main() {
	flag.Parse()

	options := &protocol.Options{
		Kitename:    "mathworker",
		Version:     "1",
		Port:        *port,
		Region:      "localhost",
		Environment: "development",
		PublicIP:    "127.0.0.1",
	}

	k := kite.New(options)

	k.HandleFunc("square", Square)

	k.Run()
}

func Square(r *kite.Request) (interface{}, error) {
	a, err := r.Args.Float64()
	if err != nil {
		return nil, err
	}

	result := a * a

	fmt.Printf("Kite call, sending result %.0f back\n", result)

	// Print a log on remote Kite.
	r.RemoteKite.Go("log", fmt.Sprintf("You have requested square of: %f", a))

	return result, nil
}
<|endoftext|>


<commit_before>// Copyright 2014 Hajime Hoshi
//
// 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.

// +build example

package main

import (
	"fmt"
	"image"
	"image/color"
	"log"
	"math"

	"github.com/hajimehoshi/ebiten"
	"github.com/hajimehoshi/ebiten/ebitenutil"
)

const (
	screenWidth  = 320
	screenHeight = 240
)

var (
	count       int
	brushImage  *ebiten.Image
	canvasImage *ebiten.Image
)

func paint(screen *ebiten.Image, x, y int) {
	op := &ebiten.DrawImageOptions{}
	op.GeoM.Translate(float64(x), float64(y))
	op.ColorM.Scale(1.0, 0.50, 0.125, 1.0)
	theta := 2.0 * math.Pi * float64(count%ebiten.FPS) / ebiten.FPS
	op.ColorM.RotateHue(theta)
	canvasImage.DrawImage(brushImage, op)
}

func update(screen *ebiten.Image) error {
	drawn := false
	mx, my := ebiten.CursorPosition()
	if ebiten.IsMouseButtonPressed(ebiten.MouseButtonLeft) {
		paint(screen, mx, my)
		drawn = true
	}
	for _, t := range ebiten.Touches() {
		x, y := t.Position()
		paint(screen, x, y)
		drawn = true
	}
	if drawn {
		count++
	}
	if ebiten.IsRunningSlowly() {
		return nil
	}
	screen.DrawImage(canvasImage, nil)

	msg := fmt.Sprintf("(%d, %d)", mx, my)
	for _, t := range ebiten.Touches() {
		x, y := t.Position()
		msg += fmt.Sprintf("\n(%d, %d) touch %d", x, y, t.ID())
	}
	ebitenutil.DebugPrint(screen, msg)
	return nil
}

func main() {
	const a0, a1, a2 = 0x40, 0xc0, 0xff
	pixels := []uint8{
		a0, a1, a1, a0,
		a1, a2, a2, a1,
		a1, a2, a2, a1,
		a0, a1, a1, a0,
	}
	brushImage, _ = ebiten.NewImageFromImage(&image.Alpha{
		Pix:    pixels,
		Stride: 4,
		Rect:   image.Rect(0, 0, 4, 4),
	}, ebiten.FilterNearest)

	canvasImage, _ = ebiten.NewImage(screenWidth, screenHeight, ebiten.FilterNearest)
	canvasImage.Fill(color.White)

	if err := ebiten.Run(update, screenWidth, screenHeight, 2, "Paint (Ebiten Demo)"); err != nil {
		log.Fatal(err)
	}
}
<commit_msg>examples/paint: Bug fix: paint function ignored the given image<commit_after>// Copyright 2014 Hajime Hoshi
//
// 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.

// +build example

package main

import (
	"fmt"
	"image"
	"image/color"
	"log"
	"math"

	"github.com/hajimehoshi/ebiten"
	"github.com/hajimehoshi/ebiten/ebitenutil"
)

const (
	screenWidth  = 320
	screenHeight = 240
)

var (
	count       int
	brushImage  *ebiten.Image
	canvasImage *ebiten.Image
)

func init() {
	const (
		a0 = 0x40
		a1 = 0xc0
		a2 = 0xff
	)
	pixels := []uint8{
		a0, a1, a1, a0,
		a1, a2, a2, a1,
		a1, a2, a2, a1,
		a0, a1, a1, a0,
	}
	brushImage, _ = ebiten.NewImageFromImage(&image.Alpha{
		Pix:    pixels,
		Stride: 4,
		Rect:   image.Rect(0, 0, 4, 4),
	}, ebiten.FilterNearest)

	canvasImage, _ = ebiten.NewImage(screenWidth, screenHeight, ebiten.FilterNearest)
	canvasImage.Fill(color.White)
}

// paint draws the brush on the given canvas image at the position (x, y).
func paint(canvas *ebiten.Image, x, y int) {
	op := &ebiten.DrawImageOptions{}
	op.GeoM.Translate(float64(x), float64(y))
	// Scale the color and rotate the hue so that colors vary on each frame.
	op.ColorM.Scale(1.0, 0.50, 0.125, 1.0)
	theta := 2.0 * math.Pi * float64(count%ebiten.FPS) / ebiten.FPS
	op.ColorM.RotateHue(theta)
	canvas.DrawImage(brushImage, op)
}

func update(screen *ebiten.Image) error {
	drawn := false

	// Paint the brush by mouse dragging
	mx, my := ebiten.CursorPosition()
	if ebiten.IsMouseButtonPressed(ebiten.MouseButtonLeft) {
		paint(canvasImage, mx, my)
		drawn = true
	}

	// Paint the brush by touches
	for _, t := range ebiten.Touches() {
		x, y := t.Position()
		paint(canvasImage, x, y)
		drawn = true
	}
	if drawn {
		count++
	}

	if ebiten.IsRunningSlowly() {
		return nil
	}

	screen.DrawImage(canvasImage, nil)

	msg := fmt.Sprintf("(%d, %d)", mx, my)
	for _, t := range ebiten.Touches() {
		x, y := t.Position()
		msg += fmt.Sprintf("\n(%d, %d) touch %d", x, y, t.ID())
	}
	ebitenutil.DebugPrint(screen, msg)
	return nil
}

func main() {
	if err := ebiten.Run(update, screenWidth, screenHeight, 2, "Paint (Ebiten Demo)"); err != nil {
		log.Fatal(err)
	}
}
<|endoftext|>


<commit_before>package main

import (
	"fmt"
	"testing"
	"time"
)

const (
	LED      = 5  // Pin 29
	RELAY    = 13 // Pin 33
	CAP4700  = 19 // Pin 35: Also PCM capable
	CAP10000 = 6  // Pin 31
	SWITCH   = 26 // Pin 37
)

func GpioStr(g PiPin) string {
	switch g.Pin() {
	case LED:
		return "LED"
	case RELAY:
		return "RELAY"
	case CAP4700:
		return "CAP4700"
	case CAP10000:
		return "CAP10000"
	case SWITCH:
		return "SWITCH"
	default:
		return "UNKNOWN"
	}
	return ""
}

var Led PiPin        // Setup: GPIO -> <1k Resistor -> LED -> GND
var TestRelay *Relay // Setup GPIO -> 4.7k Resistor -> Relay Board
var Cap4700 PiPin    // Setup: +3.3v -> 4.7k Resistor -> GPIO -> 10uF capacitor -> GND
var Cap10000 PiPin   // Setup: +3.3v -> 10k Resistor -> GPIO -> 10uF capacitor -> GND
var Switch PiPin     // Setup: GPIO -> Button Switch -> GND

func ExpectedState(t *testing.T, gpio PiPin, exp GpioState) {
	if val := gpio.Read(); val != exp {
		t.Errorf("%s: Expected %s but found %s", GpioStr(gpio), exp, val)
	}
}

func TestInitilization(t *testing.T) {
	EnableDebug()
	err := GpioInit()
	t.Run("Init Host", func(t *testing.T) {
		if err != nil {
			t.Errorf("Problem initializing gpio: %s", err.Error())
		}
	})

	// Initialized GPIOs
	Led = NewGpio(LED)
	ExpectedState(t, Led, Low)
}

func TestBlinkLed(t *testing.T) {
	Info("Running %s", t.Name())
	for i := 0; i < 6; i++ {
		time.Sleep(time.Second / 5)
		Led.Output(High)
		ExpectedState(t, Led, High)
		time.Sleep(time.Second / 5)
		Led.Output(Low)
		ExpectedState(t, Led, Low)
	}
}

func doStop(button *Button, b *bool, t time.Time) {
	*b = false
	button.Stop()
	*b = true
	Info("doStop - Stopped after %d ms", time.Now().Sub(t)/time.Millisecond)
}

func runRelayTestOn(t *testing.T, relay *Relay) {
	relay.TurnOn()
	Info("Testing Relay On: %s is %s", relay.Name(), relay.Status())
	if !relay.isOn() {
		t.Errorf("Relay(%s) is %s", relay.Name(), relay.Status())
	}
}

func runRelayTestOff(t *testing.T, relay *Relay) {
	relay.TurnOff()
	Info("Testing Relay Off: %s is %s", relay.Name(), relay.Status())
	if relay.isOn() {
		t.Errorf("Relay(%s) is %s", relay.Name(), relay.Status())
	}
}

func runRelayTest(t *testing.T, r *Relay, sleep time.Duration) {
	t.Run(fmt.Sprintf("%s.Test", r.Name()), func(t *testing.T) {
		Info("Running %s", t.Name())
		runRelayTestOn(t, r)
		time.Sleep(sleep)
		runRelayTestOff(t, r)
	})
}

func TestRelays(t *testing.T) {
	Info("Running %s", t.Name())
	TestRelay = NewRelay(RELAY, "Relay", "Testing")
	runRelayTest(t, TestRelay, time.Second)
}

func TestThermometer(t *testing.T) {
	Info("Running %s", t.Name())
	therm := NewGpioThermometer("Fixed 4.7kOhm ResistorTest", "TestManufacturer", CAP4700, 10.0)

	t.Run("Calibrate Cap4700", func(t *testing.T) {
		Info("Running %s", t.Name())
		c, err := therm.Calibrate(4700)
		if err != nil {
			t.Errorf("Failure to Calibrate successfully: %s", err.Error())
		}
		Debug("Setting calibration for %0.3f", c)
		therm.SetAdjustment(c)
	})
	t.Run("Temperature Cap4700", func(t *testing.T) {
		Info("Running %s", t.Name())
		err := therm.Update()
		if err != nil {
			t.Errorf("Thermometer update failed: %s", err.Error())
		}
		if therm.Temperature() > 44.1 || therm.Temperature() < 43.1 {
			t.Errorf("Thermometer value off: %0.1f, expected 43.6",
				therm.Temperature())
		}
	})

	therm = NewGpioThermometer("Fixed 10kOhm ResistorTest", "TestManufacturer", CAP10000, 10.0)
	t.Run("Calibrate Cap10000", func(t *testing.T) {
		Info("Running %s", t.Name())
		c, err := therm.Calibrate(10000)
		if err != nil {
			t.Errorf("Failure to Calibrate successfully: %s", err.Error())
		}
		Debug("Setting calibration for %0.3f", c)
		therm.SetAdjustment(c)
	})
	t.Run("Temperature Cap4700", func(t *testing.T) {
		Info("Running %s", t.Name())
		err := therm.Update()
		if err != nil {
			t.Errorf("Thermometer update failed: %s", err.Error())
		}
		if therm.Temperature() > 25.4 || therm.Temperature() < 24.4 {
			t.Errorf("Thermometer value off: %0.1f, expected 24.9",
				therm.Temperature())
		}
	})
}

func TestPushButton(t *testing.T) {
	Info("Running %s", t.Name())
	if testing.Short() {
		t.Skip("skipping test in short mode.")
	}
	wasRun := 0
	button := NewGpioButton(SWITCH, func() {
		wasRun++
		Info("Button Pushed %d!!!", wasRun)
		Led.Output(High)
		time.Sleep(time.Second / 2)
		Led.Output(Low)
	})

	Info("Starting button test, push it 3 times!")
	button.Start()
	for i := 0; i < 3; i++ {
		TestRelay.TurnOn()
		time.Sleep(time.Second / 10)
		TestRelay.TurnOff()
		time.Sleep(time.Second / 2)
	}
	if wasRun < 3 {
		t.Errorf("Expected 3 button pushes")
	}
	Info("Stopping button job")
	exited := false
	go doStop(button, &exited, time.Now())
	time.Sleep(time.Second)
	if !exited {
		t.Errorf("Button loop should have stopped within time allotted")
	}
	Info("Button job stopped")
}
<commit_msg>test sync<commit_after>package main

import (
	"fmt"
	"testing"
	"time"
)

const (
	LED      = 5  // Pin 29
	RELAY    = 13 // Pin 33
	CAP4700  = 19 // Pin 35: Also PCM capable
	CAP10000 = 6  // Pin 31
	SWITCH   = 26 // Pin 37
)

func GpioStr(g PiPin) string {
	switch g.Pin() {
	case LED:
		return "LED"
	case RELAY:
		return "RELAY"
	case CAP4700:
		return "CAP4700"
	case CAP10000:
		return "CAP10000"
	case SWITCH:
		return "SWITCH"
	default:
		return "UNKNOWN"
	}
	return ""
}

var Led PiPin        // Setup: GPIO -> <1k Resistor -> LED -> GND
var TestRelay *Relay // Setup GPIO -> 4.7k Resistor -> Relay Board
var Cap4700 PiPin    // Setup: +3.3v -> 4.7k Resistor -> GPIO -> 10uF capacitor -> GND
var Cap10000 PiPin   // Setup: +3.3v -> 10k Resistor -> GPIO -> 10uF capacitor -> GND
var Switch PiPin     // Setup: GPIO -> Button Switch -> GND

func ExpectedState(t *testing.T, gpio PiPin, exp GpioState) {
	if val := gpio.Read(); val != exp {
		t.Errorf("%s: Expected %s but found %s", GpioStr(gpio), exp, val)
	}
}

func TestInitilization(t *testing.T) {
	err := GpioInit()
	t.Run("Init Host", func(t *testing.T) {
		if err != nil {
			t.Errorf("Problem initializing gpio: %s", err.Error())
		}
	})

	// Initialized GPIOs
	Led = NewGpio(LED)
	ExpectedState(t, Led, Low)
}

func TestBlinkLed(t *testing.T) {
	Info("Running %s", t.Name())
	for i := 0; i < 6; i++ {
		time.Sleep(time.Second / 5)
		Led.Output(High)
		ExpectedState(t, Led, High)
		time.Sleep(time.Second / 5)
		Led.Output(Low)
		ExpectedState(t, Led, Low)
	}
}

func doStop(button *Button, b *bool, t time.Time) {
	*b = false
	button.Stop()
	*b = true
	Info("doStop - Stopped after %d ms", time.Now().Sub(t)/time.Millisecond)
}

func runRelayTestOn(t *testing.T, relay *Relay) {
	relay.TurnOn()
	Info("Testing Relay On: %s is %s", relay.Name(), relay.Status())
	if !relay.isOn() {
		t.Errorf("Relay(%s) is %s", relay.Name(), relay.Status())
	}
}

func runRelayTestOff(t *testing.T, relay *Relay) {
	relay.TurnOff()
	Info("Testing Relay Off: %s is %s", relay.Name(), relay.Status())
	if relay.isOn() {
		t.Errorf("Relay(%s) is %s", relay.Name(), relay.Status())
	}
}

func runRelayTest(t *testing.T, r *Relay, sleep time.Duration) {
	t.Run(fmt.Sprintf("%s.Test", r.Name()), func(t *testing.T) {
		Info("Running %s", t.Name())
		runRelayTestOn(t, r)
		time.Sleep(sleep)
		runRelayTestOff(t, r)
	})
}

func TestRelays(t *testing.T) {
	Info("Running %s", t.Name())
	TestRelay = NewRelay(RELAY, "Relay", "Testing")
	runRelayTest(t, TestRelay, time.Second)
}

func TestThermometer(t *testing.T) {
	Info("Running %s", t.Name())
	therm := NewGpioThermometer("Fixed 4.7kOhm ResistorTest", "TestManufacturer", CAP4700, 10.0)

	t.Run("Calibrate Cap4700", func(t *testing.T) {
		Info("Running %s", t.Name())
		c, err := therm.Calibrate(4700)
		if err != nil {
			t.Errorf("Failure to Calibrate successfully: %s", err.Error())
		}
		Debug("Setting calibration for %0.3f", c)
		therm.SetAdjustment(c)
	})
	t.Run("Temperature Cap4700", func(t *testing.T) {
		Info("Running %s", t.Name())
		err := therm.Update()
		if err != nil {
			t.Errorf("Thermometer update failed: %s", err.Error())
		}
		if therm.Temperature() > 44.1 || therm.Temperature() < 43.1 {
			t.Errorf("Thermometer value off: %0.1f, expected 43.6",
				therm.Temperature())
		}
	})

	therm = NewGpioThermometer("Fixed 10kOhm ResistorTest", "TestManufacturer", CAP10000, 10.0)
	t.Run("Calibrate Cap10000", func(t *testing.T) {
		Info("Running %s", t.Name())
		c, err := therm.Calibrate(10000)
		if err != nil {
			t.Errorf("Failure to Calibrate successfully: %s", err.Error())
		}
		Debug("Setting calibration for %0.3f", c)
		therm.SetAdjustment(c)
	})
	t.Run("Temperature Cap4700", func(t *testing.T) {
		Info("Running %s", t.Name())
		err := therm.Update()
		if err != nil {
			t.Errorf("Thermometer update failed: %s", err.Error())
		}
		if therm.Temperature() > 25.4 || therm.Temperature() < 24.4 {
			t.Errorf("Thermometer value off: %0.1f, expected 24.9",
				therm.Temperature())
		}
	})
}

func TestPushButton(t *testing.T) {
	Info("Running %s", t.Name())
	if testing.Short() {
		t.Skip("skipping test in short mode.")
	}
	wasRun := 0
	button := NewGpioButton(SWITCH, func() {
		wasRun++
		Info("Button Pushed %d!!!", wasRun)
		Led.Output(High)
		time.Sleep(time.Second / 2)
		Led.Output(Low)
	})

	Info("Starting button test, push it 3 times!")
	button.Start()
	for i := 0; i < 3; i++ {
		TestRelay.TurnOn()
		time.Sleep(time.Second / 10)
		TestRelay.TurnOff()
		time.Sleep(time.Second / 2)
	}
	if wasRun < 3 {
		t.Errorf("Expected 3 button pushes")
	}
	Info("Stopping button job")
	exited := false
	go doStop(button, &exited, time.Now())
	time.Sleep(time.Second)
	if !exited {
		t.Errorf("Button loop should have stopped within time allotted")
	}
	Info("Button job stopped")
}
<|endoftext|>


<commit_before>// Copyright 2021 Google LLC
//
// 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 fuzzing

import (
	"bytes"
	"context"
	"gvisor.dev/gvisor/pkg/buffer"
	"gvisor.dev/gvisor/pkg/state"
)

func FuzzStateLoad(data []byte) int {
	ctx := context.Background()
	var toLoad *buffer.View
	_, _ = state.Load(ctx, bytes.NewReader(data), toLoad)
	return 1
}
<commit_msg>gvisor: fix broken build (#8173)<commit_after>// Copyright 2021 Google LLC
//
// 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 fuzzing

import (
	"bytes"
	"context"
	"gvisor.dev/gvisor/pkg/bufferv2"
	"gvisor.dev/gvisor/pkg/state"
)

func FuzzStateLoad(data []byte) int {
	ctx := context.Background()
	var toLoad *bufferv2.View
	_, _ = state.Load(ctx, bytes.NewReader(data), toLoad)
	return 1
}
<|endoftext|>


<commit_before>package hackyslack

import (
	"encoding/json"
	"golang.org/x/oauth2"
	"google.golang.org/appengine"
	"google.golang.org/appengine/datastore"
	"google.golang.org/appengine/log"
	"html/template"
	"net/http"
	"time"
)

var (
	templates = template.Must(template.ParseGlob("*.html"))
	conf      = oauth2.Config{
		ClientID:     clientId,
		ClientSecret: clientSecret,
		Scopes:       []string{},
		Endpoint: oauth2.Endpoint{
			AuthURL:  "https://slack.com/oauth/authorize",
			TokenURL: "https://slack.com/api/oauth.access",
		},
	}
)

func init() {
	http.HandleFunc("/", index)
	http.HandleFunc("/oauth", oauth)
	http.HandleFunc("/privacy", privacy)
	http.HandleFunc("/contact", contact)
}

type D map[string]interface{}
type Args struct {
	TeamId      string
	TeamDomain  string
	ChannelId   string
	ChannelName string
	UserId      string
	UserName    string
	Command     string
	Text        string
	ResponseUrl string
}
type Command func(Args) D

// Manually inline oauth2.Token for datastore.
type TeamToken struct {
	AccessToken  string    `json:"access_token"`
	TokenType    string    `json:"token_type,omitempty"`
	RefreshToken string    `json:"refresh_token,omitempty"`
	Expiry       time.Time `json:"expiry,omitempty"`
	TeamId       string    `json:"team_id,omitempty"`
	TeamName     string    `json:"team_name,omitempty"`
	Scope        string    `json:"scope,omitempty"`
	Created      time.Time `json:"created,omitempty"`
}

func Register(name string, cmd Command) {
	http.HandleFunc("/"+name, func(w http.ResponseWriter, r *http.Request) {
		args := Args{
			TeamId:      r.FormValue("team_id"),
			TeamDomain:  r.FormValue("team_domain"),
			ChannelId:   r.FormValue("channel_id"),
			ChannelName: r.FormValue("channel_name"),
			UserId:      r.FormValue("user_id"),
			UserName:    r.FormValue("user_name"),
			Command:     r.FormValue("command"),
			Text:        r.FormValue("text"),
			ResponseUrl: r.FormValue("response_url"),
		}
		c := appengine.NewContext(r)
		log.Infof(c, "Got command %v", args)
		writeJson(w, r, cmd(args))
	})
}

func writeJson(w http.ResponseWriter, r *http.Request, data D) {
	bytes, err := json.Marshal(data)
	if err != nil {
		c := appengine.NewContext(r)
		log.Errorf(c, "Failed to mashal %v: %v", data, err)
	}
	w.Header().Set("Content-Type", "application/json")
	w.Write(bytes)
}

func index(w http.ResponseWriter, r *http.Request) {
	c, _ := r.Cookie("s")
	http.SetCookie(w, &http.Cookie{
		Name:   "s",
		MaxAge: -1,
	})
	templates.ExecuteTemplate(w, "index.html", c != nil)
}

func oauth(w http.ResponseWriter, r *http.Request) {
	code := r.URL.Query()["code"]
	if len(code) == 0 {
		http.Redirect(w, r, "/", 303)
		return
	}
	c := appengine.NewContext(r)
	tok, err := conf.Exchange(c, code[0])
	if err != nil {
		log.Errorf(c, "Failed to exchange token %v: %v", tok, err)
	}
	team := TeamToken{
		AccessToken:  tok.AccessToken,
		TokenType:    tok.TokenType,
		RefreshToken: tok.RefreshToken,
		Expiry:       tok.Expiry,
		TeamId:       tok.Extra("team_id").(string),
		TeamName:     tok.Extra("team_name").(string),
		Scope:        tok.Extra("scope").(string),
		Created:      time.Now(),
	}
	key := datastore.NewKey(c, "token", team.TeamId, 0, nil)
	datastore.Put(c, key, &team)
	http.SetCookie(w, &http.Cookie{
		Name:  "s",
		Value: "1",
	})
	http.Redirect(w, r, "/", 303)
}

func privacy(w http.ResponseWriter, r *http.Request) {
	templates.ExecuteTemplate(w, "privacy.html", true)
}

func contact(w http.ResponseWriter, r *http.Request) {
	templates.ExecuteTemplate(w, "contact.html", true)
}
<commit_msg>Migration path for /command<commit_after>package hackyslack

import (
	"encoding/json"
	"golang.org/x/oauth2"
	"google.golang.org/appengine"
	"google.golang.org/appengine/datastore"
	"google.golang.org/appengine/log"
	"html/template"
	"net/http"
	"time"
)

var (
	templates = template.Must(template.ParseGlob("*.html"))
	commands  = map[string]Command{}
	conf      = oauth2.Config{
		ClientID:     clientId,
		ClientSecret: clientSecret,
		Scopes:       []string{},
		Endpoint: oauth2.Endpoint{
			AuthURL:  "https://slack.com/oauth/authorize",
			TokenURL: "https://slack.com/api/oauth.access",
		},
	}
)

func init() {
	http.HandleFunc("/", index)
	http.HandleFunc("/command", command)
	http.HandleFunc("/contact", contact)
	http.HandleFunc("/oauth", oauth)
	http.HandleFunc("/privacy", privacy)
}

type D map[string]interface{}
type Args struct {
	TeamId      string
	TeamDomain  string
	ChannelId   string
	ChannelName string
	UserId      string
	UserName    string
	Command     string
	Text        string
	ResponseUrl string
}
type Command func(Args) D

// Manually inline oauth2.Token for datastore.
type TeamToken struct {
	AccessToken  string    `json:"access_token"`
	TokenType    string    `json:"token_type,omitempty"`
	RefreshToken string    `json:"refresh_token,omitempty"`
	Expiry       time.Time `json:"expiry,omitempty"`
	TeamId       string    `json:"team_id,omitempty"`
	TeamName     string    `json:"team_name,omitempty"`
	Scope        string    `json:"scope,omitempty"`
	Created      time.Time `json:"created,omitempty"`
}

func Register(name string, cmd Command) {
	commands["/"+name] = cmd
	http.HandleFunc("/"+name, func(w http.ResponseWriter, r *http.Request) {
		args := Args{
			TeamId:      r.FormValue("team_id"),
			TeamDomain:  r.FormValue("team_domain"),
			ChannelId:   r.FormValue("channel_id"),
			ChannelName: r.FormValue("channel_name"),
			UserId:      r.FormValue("user_id"),
			UserName:    r.FormValue("user_name"),
			Command:     r.FormValue("command"),
			Text:        r.FormValue("text"),
			ResponseUrl: r.FormValue("response_url"),
		}
		c := appengine.NewContext(r)
		log.Infof(c, "Got command %v", args)
		writeJson(w, r, cmd(args))
	})
}

func writeJson(w http.ResponseWriter, r *http.Request, data D) {
	bytes, err := json.Marshal(data)
	if err != nil {
		c := appengine.NewContext(r)
		log.Errorf(c, "Failed to mashal %v: %v", data, err)
	}
	w.Header().Set("Content-Type", "application/json")
	w.Write(bytes)
}

func command(w http.ResponseWriter, r *http.Request) {
	args := Args{
		TeamId:      r.FormValue("team_id"),
		TeamDomain:  r.FormValue("team_domain"),
		ChannelId:   r.FormValue("channel_id"),
		ChannelName: r.FormValue("channel_name"),
		UserId:      r.FormValue("user_id"),
		UserName:    r.FormValue("user_name"),
		Command:     r.FormValue("command"),
		Text:        r.FormValue("text"),
		ResponseUrl: r.FormValue("response_url"),
	}
	c := appengine.NewContext(r)
	log.Infof(c, "Got command %v", args)
	cmd, ok := commands[args.Command]
	if ok {
		writeJson(w, r, cmd(args))
	} else {
		w.Write([]byte("Command not found."))
	}
}

func index(w http.ResponseWriter, r *http.Request) {
	c, _ := r.Cookie("s")
	http.SetCookie(w, &http.Cookie{
		Name:   "s",
		MaxAge: -1,
	})
	templates.ExecuteTemplate(w, "index.html", c != nil)
}

func oauth(w http.ResponseWriter, r *http.Request) {
	code := r.URL.Query()["code"]
	if len(code) == 0 {
		http.Redirect(w, r, "/", 303)
		return
	}
	c := appengine.NewContext(r)
	tok, err := conf.Exchange(c, code[0])
	if err != nil {
		log.Errorf(c, "Failed to exchange token %v: %v", tok, err)
	}
	team := TeamToken{
		AccessToken:  tok.AccessToken,
		TokenType:    tok.TokenType,
		RefreshToken: tok.RefreshToken,
		Expiry:       tok.Expiry,
		TeamId:       tok.Extra("team_id").(string),
		TeamName:     tok.Extra("team_name").(string),
		Scope:        tok.Extra("scope").(string),
		Created:      time.Now(),
	}
	key := datastore.NewKey(c, "token", team.TeamId, 0, nil)
	datastore.Put(c, key, &team)
	http.SetCookie(w, &http.Cookie{
		Name:  "s",
		Value: "1",
	})
	http.Redirect(w, r, "/", 303)
}

func contact(w http.ResponseWriter, r *http.Request) {
	templates.ExecuteTemplate(w, "contact.html", true)
}

func privacy(w http.ResponseWriter, r *http.Request) {
	templates.ExecuteTemplate(w, "privacy.html", true)
}
<|endoftext|>


<commit_before>// +build ignore

package mp

import (
	"bufio"
	"fmt"
	"io"
	"math"
	"os/exec"
	"strconv"
	"strings"
	"time"
)

type MPlayer struct {
	outputChan  chan string
	commandChan chan func(time.Duration)
	stdin       io.WriteCloser
	stdout      *bufio.Reader
	process     *exec.Cmd
}

func (mpl *MPlayer) initialize() chan State {
	mpl.process = exec.Command("mplayer", "--prefer-ipv4", "--cache=8192", "--slave", "--quiet", "--softvol", "--volume="+strconv.Itoa(INITIAL_VOLUME), "--idle", "--input=nodefault-bindings:conf=/dev/null")

	stdin, err := mpl.process.StdinPipe()
	if err != nil {
		panic(err)
	}
	mpl.stdin = stdin

	stdout, err := mpl.process.StdoutPipe()
	if err != nil {
		panic(err)
	}
	mpl.stdout = bufio.NewReader(stdout)

	log.Println("Starting MPlayer...")
	err = mpl.process.Start()
	if err != nil {
		panic(err)
	}

	mpl.outputChan = make(chan string)
	mpl.commandChan = make(chan func(time.Duration))

	eventChan := make(chan State)

	go mpl.outputHandler()
	go mpl.run(eventChan)

	return eventChan
}

func (mpl *MPlayer) sendCommand(command string) {
	for _, part := range strings.Split(strings.TrimSpace(command), "\n") {
		log.Println("mplayer command:", part)
	}
	_, err := mpl.stdin.Write([]byte(command))
	if err != nil {
		panic(err)
	}
}

func (mpl *MPlayer) quit() {
	mpl.sendCommand("quit\n")
	time.Sleep(1) // let it close gracefully
	mpl.process.Process.Kill()
	mpl.process = nil
}

func (mpl *MPlayer) play(stream string, position time.Duration) {
	if strings.HasPrefix(stream, "https://") {
		// MPlayer2 doesn't support HTTPS, so using our built-in proxy.
		stream = "http://localhost:8008/proxy/" + stream[len("https://"):]
	}

	if position == 0 {
		mpl.sendCommand(fmt.Sprintf("stop\nloadfile \"%s\"\nget_time_length\nget_time_position\n", stream))
	} else {
		mpl.sendCommand(fmt.Sprintf("stop\nloadfile \"%s\"\nget_time_length\nseek %.3f 2\nget_time_position\n", stream, position.Seconds()))
	}
}

func (mpl *MPlayer) pause() {
	mpl.sendCommand("pause\nget_time_pos\nget_property pause\n")
}

func (mpl *MPlayer) resume() {
	mpl.sendCommand("pause\nget_property pause\n")
}

func (mpl *MPlayer) getPosition() time.Duration {
	ch := make(chan time.Duration)
	mpl.commandChan <- func(position time.Duration) {
		ch <- position
	}
	return <-ch
}

func (mpl *MPlayer) setPosition(position time.Duration) {
	mpl.sendCommand(fmt.Sprintf("seek %.3f 2\nget_time_pos\n", position.Seconds()))
}

func (mpl *MPlayer) setVolume(volume int) {
	mpl.sendCommand(fmt.Sprintf("volume %d 1\nget_time_length\n", volume))
}

func (mpl *MPlayer) stop() {
	mpl.sendCommand("stop\n")
	// TODO this doesn't send back that the video has actually stopped...
}

func (mpl *MPlayer) outputHandler() {
	for {
		line, err := mpl.stdout.ReadString('\n')
		if err != nil {
			if err == io.EOF {
				// process exited gracefully
				close(mpl.outputChan)
				return
			}
			panic(err)
		}
		line = strings.TrimSpace(line[:len(line)-1])

		mpl.outputChan <- line
	}
}

func (mpl *MPlayer) run(eventChan chan State) {
	var startTime *time.Time
	var position time.Duration
	var length time.Duration

	for {
		select {
		case c := <-mpl.commandChan:
			if startTime != nil {
				position = time.Now().Sub(*startTime)
			}
			c(position)

		case line, ok := <-mpl.outputChan:
			if !ok {
				// channel has closed, thus process has exited, thus this
				// goroutine can/must exit.
				return
			}

			log.Println("mplayer:", line)

			if line == "Starting playback..." {
				t := time.Now().Add(-position)
				startTime = &t
				eventChan <- STATE_PLAYING

			} else if strings.HasPrefix(line, "ANS_TIME_POSITION=") {
				p, err := time.ParseDuration(line[len("ANS_TIME_POSITION="):] + "s")
				if err != nil {
					panic(err)
				}
				position = p

				if startTime != nil {
					t := time.Now().Add(-position)
					startTime = &t
				}

			} else if strings.HasPrefix(line, "ANS_LENGTH=") {
				l, err := time.ParseDuration(line[len("ANS_LENGTH="):] + "s")
				if err != nil {
					panic(err)
				}
				length = l

			} else if strings.HasPrefix(line, "ANS_pause=") {
				paused := line[len("ANS_pause="):]
				switch paused {
				case "yes":
					if startTime != nil {
						// the player just got the 'paused' signal
						position = time.Now().Sub(*startTime)
						startTime = nil
					}
					eventChan <- STATE_PAUSED
				case "no":
					if startTime == nil {
						t := time.Now().Add(-position)
						startTime = &t
					}
					eventChan <- STATE_PLAYING
				default:
					panic("unknown response: " + line)
				}

			} else if line == "" {
				// The player may have stopped...
				// This is a very dirty hack. At the end of the stream,
				// mplayer2 writes a newline to the console. But we don't know
				// for sure this newline is due to mplayer2 stopping or not,
				// so we use a few heuristics here that aren't exactly perfect.

				if startTime == nil {
					continue
				}

				// using 5s+5% as cut-off: I hope that number works.
				// That's 8s for a 60s movie and 11 seconds for 120s movie.
				// If this doesn't work always, this MPlayer wrapper is one big hack anyway...
				endOffset := startTime.Add(length).Sub(time.Now())
				if math.Abs(endOffset.Seconds()) > (5.0 + length.Seconds()*0.05) {
					continue
				}

				// assume the stream has finished playing

				startTime = nil
				position = 0
				eventChan <- STATE_STOPPED
			}
		}
	}
}
<commit_msg>Remove mplayer support<commit_after><|endoftext|>


<commit_before>/*
Copyright 2014 Workiva, LLC

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 bitarray

func andSparseWithSparseBitArray(sba, other *sparseBitArray) BitArray {
	max := maxInt64(int64(len(sba.indices)), int64(len(other.indices)))
	indices := make(uintSlice, 0, max)
	blocks := make(blocks, 0, max)

	selfIndex := 0
	otherIndex := 0
	var resultBlock block

	// move through the array and compare the blocks if they happen to
	// intersect
	for {
		if selfIndex == len(sba.indices) || otherIndex == len(other.indices) {
			// One of the arrays has been exhausted. We don't need
			// to compare anything else for a bitwise and; the
			// operation is complete.
			break
		}

		selfValue := sba.indices[selfIndex]
		otherValue := other.indices[otherIndex]

		switch {
		case otherValue < selfValue:
			// The `sba` bitarray has a block with a index position
			// greater than us. We want to compare with that block
			// if possible, so move our `other` index closer to that
			// block's index.
			otherIndex++

		case otherValue > selfValue:
			// This is the exact logical inverse of the above case.
			selfIndex++

		default:
			// Here, our indices match for both `sba` and `other`.
			// Time to do the bitwise AND operation and add a block
			// to our result list if the block has values in it.
			resultBlock = sba.blocks[selfIndex].and(other.blocks[otherIndex])
			if resultBlock > 0 {
				indices = append(indices, selfValue)
				blocks = append(blocks, resultBlock)
			}
			selfIndex++
			otherIndex++
		}
	}

	return &sparseBitArray{
		indices: indices,
		blocks:  blocks,
	}
}

func andSparseWithDenseBitArray(sba *sparseBitArray, other *bitArray) BitArray {
	// Use a duplicate of the sparse array to store the results of the
	// bitwise and. More memory-efficient than allocating a new dense bit
	// array.
	//
	// NOTE: this could be faster if we didn't copy the values as well
	// (since they are overwritten), but I don't want this method to know
	// too much about the internals of sparseBitArray. The performance hit
	// should be minor anyway.
	ba := sba.copy()

	// Run through the sparse array and attempt comparisons wherever
	// possible against the dense bit array.
	for selfIndex, selfValue := range sba.indices {

		if selfValue >= uint64(len(other.blocks)) {
			// The dense bit array has been exhausted. This is the
			// annoying case because we have to trim the sparse
			// array to the size of the dense array.
			ba.blocks = ba.blocks[:selfIndex]
			ba.indices = ba.indices[:selfIndex]

			// once this is done, there are no more comparisons.
			// We're ready to return
			break
		}
		ba.blocks[selfIndex] = ba.blocks[selfIndex].and(
			other.blocks[selfValue])

		if ba.blocks[selfIndex] == 0 {
			ba.blocks.deleteAtIndex(int64(selfIndex))
			ba.indices.deleteAtIndex(int64(selfIndex))
		}
	}

	return ba
}

func andDenseWithDenseBitArray(dba, other *bitArray) BitArray {
	min := minUint64(uint64(len(dba.blocks)), uint64(len(other.blocks)))

	ba := newBitArray(min * s)

	for i := uint64(0); i < min; i++ {
		ba.blocks[i] = dba.blocks[i].and(other.blocks[i])
	}

	ba.setLowest()
	ba.setHighest()

	return ba
}
<commit_msg>fix andSparseWithDenseBitArray resulting array trimming<commit_after>/*
Copyright 2014 Workiva, LLC

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 bitarray

func andSparseWithSparseBitArray(sba, other *sparseBitArray) BitArray {
	max := maxInt64(int64(len(sba.indices)), int64(len(other.indices)))
	indices := make(uintSlice, 0, max)
	blocks := make(blocks, 0, max)

	selfIndex := 0
	otherIndex := 0
	var resultBlock block

	// move through the array and compare the blocks if they happen to
	// intersect
	for {
		if selfIndex == len(sba.indices) || otherIndex == len(other.indices) {
			// One of the arrays has been exhausted. We don't need
			// to compare anything else for a bitwise and; the
			// operation is complete.
			break
		}

		selfValue := sba.indices[selfIndex]
		otherValue := other.indices[otherIndex]

		switch {
		case otherValue < selfValue:
			// The `sba` bitarray has a block with a index position
			// greater than us. We want to compare with that block
			// if possible, so move our `other` index closer to that
			// block's index.
			otherIndex++

		case otherValue > selfValue:
			// This is the exact logical inverse of the above case.
			selfIndex++

		default:
			// Here, our indices match for both `sba` and `other`.
			// Time to do the bitwise AND operation and add a block
			// to our result list if the block has values in it.
			resultBlock = sba.blocks[selfIndex].and(other.blocks[otherIndex])
			if resultBlock > 0 {
				indices = append(indices, selfValue)
				blocks = append(blocks, resultBlock)
			}
			selfIndex++
			otherIndex++
		}
	}

	return &sparseBitArray{
		indices: indices,
		blocks:  blocks,
	}
}

func andSparseWithDenseBitArray(sba *sparseBitArray, other *bitArray) BitArray {
	if other.IsEmpty() {
		return newSparseBitArray()
	}

	// Use a duplicate of the sparse array to store the results of the
	// bitwise and. More memory-efficient than allocating a new dense bit
	// array.
	//
	// NOTE: this could be faster if we didn't copy the values as well
	// (since they are overwritten), but I don't want this method to know
	// too much about the internals of sparseBitArray. The performance hit
	// should be minor anyway.
	ba := sba.copy()

	// Run through the sparse array and attempt comparisons wherever
	// possible against the dense bit array.
	for selfIndex, selfValue := range ba.indices {

		if selfValue >= uint64(len(other.blocks)) {
			// The dense bit array has been exhausted. This is the
			// annoying case because we have to trim the sparse
			// array to the size of the dense array.
			ba.blocks = ba.blocks[:selfIndex-1]
			ba.indices = ba.indices[:selfIndex-1]

			// once this is done, there are no more comparisons.
			// We're ready to return
			break
		}
		ba.blocks[selfIndex] = ba.blocks[selfIndex].and(
			other.blocks[selfValue])

	}

	// Ensure any zero'd blocks in the resulting sparse
	// array are deleted
	for i := 0; i < len(ba.blocks); i++ {
		if ba.blocks[i] == 0 {
			ba.blocks.deleteAtIndex(int64(i))
			ba.indices.deleteAtIndex(int64(i))
			i--
		}
	}

	return ba
}

func andDenseWithDenseBitArray(dba, other *bitArray) BitArray {
	min := minUint64(uint64(len(dba.blocks)), uint64(len(other.blocks)))

	ba := newBitArray(min * s)

	for i := uint64(0); i < min; i++ {
		ba.blocks[i] = dba.blocks[i].and(other.blocks[i])
	}

	ba.setLowest()
	ba.setHighest()

	return ba
}
<|endoftext|>


<commit_before>/*
 * Copyright (c) 2014 Santiago Arias | Remy Jourde
 *
 * Permission to use, copy, modify, and distribute this software for any
 * purpose with or without fee is hereby granted, provided that the above
 * copyright notice and this permission notice appear in all copies.
 *
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 */

package teams

import (
	"errors"
	"net/http"

	"appengine"

	"github.com/santiaago/gonawin/extract"
	"github.com/santiaago/gonawin/helpers"
	"github.com/santiaago/gonawin/helpers/log"
	templateshlp "github.com/santiaago/gonawin/helpers/templates"

	mdl "github.com/santiaago/gonawin/models"
)

// Ranking handler, use it to retrieve the team ranking.
// Use this handler to get the ranking of a team.
// The ranking is an array of users (members of the team),
//	GET	/j/teams/[0-9]+/ranking/
//
func Ranking(w http.ResponseWriter, r *http.Request, u *mdl.User) error {
	if r.Method != "GET" {
		return &helpers.BadRequest{Err: errors.New(helpers.ErrorCodeNotSupported)}
	}

	c := appengine.NewContext(r)
	desc := "Team Ranking Handler:"
	extract := extract.NewContext(c, desc, r)

	var t *mdl.Team
	var err error
	t, err = extract.Team()
	if err != nil {
		return err
	}

	log.Infof(c, "%s ready to build a user array", desc)
	users := t.RankingByUser(c, 50)

	fieldsToKeep := []string{"Id", "Username", "Alias", "Score"}
	usersJson := make([]mdl.UserJson, len(users))
	helpers.TransformFromArrayOfPointers(&users, &usersJson, fieldsToKeep)

	data := struct {
		Users []mdl.UserJson
	}{
		usersJson,
	}

	return templateshlp.RenderJson(w, c, data)

}
<commit_msg>refactor team Ranking controller<commit_after>/*
 * Copyright (c) 2014 Santiago Arias | Remy Jourde
 *
 * Permission to use, copy, modify, and distribute this software for any
 * purpose with or without fee is hereby granted, provided that the above
 * copyright notice and this permission notice appear in all copies.
 *
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 */

package teams

import (
	"errors"
	"net/http"

	"appengine"

	"github.com/santiaago/gonawin/extract"
	"github.com/santiaago/gonawin/helpers"
	"github.com/santiaago/gonawin/helpers/log"
	templateshlp "github.com/santiaago/gonawin/helpers/templates"

	mdl "github.com/santiaago/gonawin/models"
)

// Ranking handler, use it to retrieve the team ranking.
// Use this handler to get the ranking of a team.
// The ranking is an array of users (members of the team),
//	GET	/j/teams/[0-9]+/ranking/
//
func Ranking(w http.ResponseWriter, r *http.Request, u *mdl.User) error {
	if r.Method != "GET" {
		return &helpers.BadRequest{Err: errors.New(helpers.ErrorCodeNotSupported)}
	}

	c := appengine.NewContext(r)
	desc := "Team Ranking Handler:"
	extract := extract.NewContext(c, desc, r)

	var t *mdl.Team
	var err error
	if t, err = extract.Team(); err != nil {
		return &helpers.InternalServerError{Err: err}
	}

	log.Infof(c, "%s ready to build a user array", desc)
	users := t.RankingByUser(c, 50)

	vm := buildTeamRankingViewModel(users)

	return templateshlp.RenderJson(w, c, vm)
}

type teamRankingViewModel struct {
	Users []mdl.UserJson
}

func buildTeamRankingViewModel(users []*mdl.User) teamRankingViewModel {
	fieldsToKeep := []string{"Id", "Username", "Alias", "Score"}
	u := make([]mdl.UserJson, len(users))
	helpers.TransformFromArrayOfPointers(&users, &u, fieldsToKeep)

	return teamRankingViewModel{u}

}
<|endoftext|>


<commit_before>package compressor

import (
	"archive/zip"
	"fmt"
	"io"
	"io/ioutil"
	"os"
)

type ZipCompressor struct{}

func NewZipCompressor() *ZipCompressor {
	return &ZipCompressor{}
}

func (c *ZipCompressor) Compress(compressedFile io.Writer, targetDir string, files []string) error {
	w := zip.NewWriter(compressedFile)

	for _, filename := range files {
		filepath := fmt.Sprintf("%s/%s", targetDir, filename)
		info, err := os.Stat(filepath)
		if err != nil {
			return err
		}

		if info.IsDir() {
			continue
		}

		file, err := os.Open(filepath)
		if err != nil {
			return err
		}
		defer file.Close()

		hdr, err := zip.FileInfoHeader(info)
		if err != nil {
			return err
		}

		hdr.Name = filename

		f, err := w.CreateHeader(hdr)
		if err != nil {
			return err
		}

		contents, _ := ioutil.ReadFile(filepath)
		_, err = f.Write(contents)
		if err != nil {
			return err
		}
	}

	if err := w.Close(); err != nil {
		return err
	}

	return nil
}
<commit_msg>local分の差分時刻を反映<commit_after>package compressor

import (
	"archive/zip"
	"fmt"
	"io"
	"io/ioutil"
	"os"
	"time"
)

type ZipCompressor struct{}

func NewZipCompressor() *ZipCompressor {
	return &ZipCompressor{}
}

func (c *ZipCompressor) Compress(compressedFile io.Writer, targetDir string, files []string) error {
	w := zip.NewWriter(compressedFile)

	for _, filename := range files {
		filepath := fmt.Sprintf("%s/%s", targetDir, filename)
		info, err := os.Stat(filepath)
		if err != nil {
			return err
		}

		if info.IsDir() {
			continue
		}

		file, err := os.Open(filepath)
		if err != nil {
			return err
		}
		defer file.Close()

		hdr, err := zip.FileInfoHeader(info)
		if err != nil {
			return err
		}

		hdr.Name = filename

		local := time.Now().Local()

		//現時刻のオフセットを取得
		_, offset := local.Zone()

		//差分を追加
		hdr.SetModTime(hdr.ModTime().Add(time.Duration(offset) * time.Second))

		f, err := w.CreateHeader(hdr)
		if err != nil {
			return err
		}

		contents, _ := ioutil.ReadFile(filepath)
		_, err = f.Write(contents)
		if err != nil {
			return err
		}
	}

	if err := w.Close(); err != nil {
		return err
	}

	return nil
}
<|endoftext|>


<commit_before>package cfnextract

import (
	"errors"
	"fmt"
	"os"
	"reflect"
	"strconv"
	"strings"

	"github.com/NeowayLabs/clinit-cfn-tool/utils"
	"github.com/jteeuwen/go-pkg-optarg"
)

func getAwsResources(awsMap map[string]interface{}) (map[string]interface{}, error) {
	for k, v := range awsMap {
		if k == "Resources" {
			return v.(map[string]interface{}), nil
		}
	}

	return awsMap, errors.New("Resources not found...")
}

func getAwsUserData(awsMap map[string]interface{}) []map[string]interface{} {
	var tmp map[string]interface{}
	userDataArr := make([]map[string]interface{}, 0, 0)
	userDataArr2 := make([]map[string]interface{}, 0, 0)

	resources := awsMap["Resources"].(map[string]interface{})

	if resources == nil {
		fmt.Println("AWS CloudFormation Resources not found...")
		return userDataArr
	}

	for kk, vv := range resources {
		tmp = vv.(map[string]interface{})
		if tmp["Properties"] != nil {
			tmp := tmp["Properties"].(map[string]interface{})
			if tmp == nil {
				fmt.Printf("Resource '%s' doesn't have UserData\n", kk)
				continue
			}

			if tmp["UserData"] != nil {
				tmp = tmp["UserData"].(map[string]interface{})
				userDataArr2 = make([]map[string]interface{}, len(userDataArr)+1, len(userDataArr)+1)
				for i := range userDataArr {
					userDataArr2[i] = userDataArr[i]
				}

				userDataArr2[len(userDataArr)] = tmp
				userDataArr = userDataArr2
			}
		} else {
			fmt.Printf("Resource '%s' doesn't have Properties\n", kk)
		}
	}

	return userDataArr
}

func JoinCfnUserData(userData map[string]interface{}) (string, error) {
	var tmp map[string]interface{}

	if userData["Fn::Base64"] == nil {
		return "", errors.New("UserData doesn't have Fn::Base64 field")
	}

	tmp = userData["Fn::Base64"].(map[string]interface{})

	if tmp["Fn::Join"] == nil {
		return "", errors.New("UserData doesn-t have Fn::Join field")
	}

	tmpArr := tmp["Fn::Join"].([]interface{})

	// TODO: Review this assertion
	if len(tmpArr) <= 0 {
		return "", errors.New("Empty UserData string")
	}

	tmpArr2 := tmpArr[1].([]interface{})

	cloudInitData := make([]string, len(tmpArr2))

	for i, elem := range tmpArr2 {
		if elemStr, ok := elem.(string); ok {
			cloudInitData[i] = elemStr
		} else {
			specialAwsFunc, ok := elem.(map[string]interface{})

			if !ok {
				return "", fmt.Errorf("Unsupported value: ", specialAwsFunc)
			}

			if len(specialAwsFunc) != 1 {
				return "", fmt.Errorf("Unsupported special variable: %s", specialAwsFunc)
			}

			for f, awsValue := range specialAwsFunc {
				v := reflect.TypeOf(awsValue)

				switch v.Kind() {
				case reflect.Slice:
					funcArr := awsValue.([]interface{})
					funcArrStr := make([]string, len(funcArr))
					for ii := range funcArr {
						funcArrStr[ii] = funcArr[ii].(string)
					}

					cloudInitData[i] = "{{ ." + f + "." + strings.Join(funcArrStr, ".") + " }}"
				case reflect.String:
					cloudInitData[i] = "{{ ." + f + "." + awsValue.(string) + " }}"
				default:
					return "", fmt.Errorf("Unsupported special variable of type '%': %s: %s", v, f, awsValue)
				}
			}
		}
	}

	return strings.Join(cloudInitData, ""), nil
}

func handleUserData(userData map[string]interface{}) string {
	userDataStr, err := JoinCfnUserData(userData)

	if err != nil {
		utils.Check(err)
	}

	return userDataStr
}

func ExtractCloudinit(baseCloudinitPath string, awsFormationPath string) bool {
	awsFormationContentStr := utils.ReadFile(awsFormationPath)
	awsMapInt, err := utils.DecodeJson([]byte(awsFormationContentStr))

	if err != nil {
		fmt.Println("Failed to decode JSON: %s", err.Error())
		panic(err)
	}
	awsMap := awsMapInt.(map[string]interface{})

	if err != nil {
		fmt.Errorf("Failed to decode Json")
		return false
	}

	userData := getAwsUserData(awsMap)
	cloudInitDataArr := make([]string, len(userData), len(userData))

	for i := range userData {
		cloudInitDataArr[i] = handleUserData(userData[i])
	}

	for i := range cloudInitDataArr {
		outPath := baseCloudinitPath + strconv.Itoa(i+1) + ".yaml"
		fmt.Printf("Generating file '%s'\n", outPath)
		err := utils.SaveOutput(outPath, cloudInitDataArr[i])

		utils.Check(err)
	}

	return true
}

func Extract() {
	var baseCloudinitPath, awsFormationPath string
	var helpOpt, missingOpts bool

	optarg.Add("h", "help", "Displays this help", false)
	optarg.Add("o", "output-base-path", "Output base path name.", "")
	optarg.Add("i", "cloud-formation", "CloudFormation input file", "")

	for opt := range optarg.Parse() {
		switch opt.ShortName {
		case "o":
			baseCloudinitPath = opt.String()
		case "i":
			awsFormationPath = opt.String()
		case "h":
			helpOpt = opt.Bool()

		default:
			fmt.Println("Invalid flag: ", opt)
			optarg.Usage()
			os.Exit(1)
		}
	}

	if helpOpt {
		optarg.Usage()
		os.Exit(0)
	}

	if baseCloudinitPath == "" {
		fmt.Println("-o is required...")
		missingOpts = true
	}

	if awsFormationPath == "" {
		fmt.Println("-i is required...")
		missingOpts = true
	}

	if missingOpts {
		optarg.Usage()
		os.Exit(1)
	}

	if os.Getenv("DEBUG_OPTS") != "" {
		fmt.Println(baseCloudinitPath)
		fmt.Println(awsFormationPath)
	}

	ExtractCloudinit(baseCloudinitPath, awsFormationPath)
}
<commit_msg>[BUGFIX] missing string formating<commit_after>package cfnextract

import (
	"errors"
	"fmt"
	"os"
	"reflect"
	"strconv"
	"strings"

	"github.com/NeowayLabs/clinit-cfn-tool/utils"
	"github.com/jteeuwen/go-pkg-optarg"
)

func getAwsResources(awsMap map[string]interface{}) (map[string]interface{}, error) {
	for k, v := range awsMap {
		if k == "Resources" {
			return v.(map[string]interface{}), nil
		}
	}

	return awsMap, errors.New("Resources not found...")
}

func getAwsUserData(awsMap map[string]interface{}) []map[string]interface{} {
	var tmp map[string]interface{}
	userDataArr := make([]map[string]interface{}, 0, 0)
	userDataArr2 := make([]map[string]interface{}, 0, 0)

	resources := awsMap["Resources"].(map[string]interface{})

	if resources == nil {
		fmt.Println("AWS CloudFormation Resources not found...")
		return userDataArr
	}

	for kk, vv := range resources {
		tmp = vv.(map[string]interface{})
		if tmp["Properties"] != nil {
			tmp := tmp["Properties"].(map[string]interface{})
			if tmp == nil {
				fmt.Printf("Resource '%s' doesn't have UserData\n", kk)
				continue
			}

			if tmp["UserData"] != nil {
				tmp = tmp["UserData"].(map[string]interface{})
				userDataArr2 = make([]map[string]interface{}, len(userDataArr)+1, len(userDataArr)+1)
				for i := range userDataArr {
					userDataArr2[i] = userDataArr[i]
				}

				userDataArr2[len(userDataArr)] = tmp
				userDataArr = userDataArr2
			}
		} else {
			fmt.Printf("Resource '%s' doesn't have Properties\n", kk)
		}
	}

	return userDataArr
}

func JoinCfnUserData(userData map[string]interface{}) (string, error) {
	var tmp map[string]interface{}

	if userData["Fn::Base64"] == nil {
		return "", errors.New("UserData doesn't have Fn::Base64 field")
	}

	tmp = userData["Fn::Base64"].(map[string]interface{})

	if tmp["Fn::Join"] == nil {
		return "", errors.New("UserData doesn-t have Fn::Join field")
	}

	tmpArr := tmp["Fn::Join"].([]interface{})

	// TODO: Review this assertion
	if len(tmpArr) <= 0 {
		return "", errors.New("Empty UserData string")
	}

	tmpArr2 := tmpArr[1].([]interface{})

	cloudInitData := make([]string, len(tmpArr2))

	for i, elem := range tmpArr2 {
		if elemStr, ok := elem.(string); ok {
			cloudInitData[i] = elemStr
		} else {
			specialAwsFunc, ok := elem.(map[string]interface{})

			if !ok {
				return "", fmt.Errorf("Unsupported value: ", specialAwsFunc)
			}

			if len(specialAwsFunc) != 1 {
				return "", fmt.Errorf("Unsupported special variable: %s", specialAwsFunc)
			}

			for f, awsValue := range specialAwsFunc {
				v := reflect.TypeOf(awsValue)

				switch v.Kind() {
				case reflect.Slice:
					funcArr := awsValue.([]interface{})
					funcArrStr := make([]string, len(funcArr))
					for ii := range funcArr {
						funcArrStr[ii] = funcArr[ii].(string)
					}

					cloudInitData[i] = "{{ ." + f + "." + strings.Join(funcArrStr, ".") + " }}"
				case reflect.String:
					cloudInitData[i] = "{{ ." + f + "." + awsValue.(string) + " }}"
				default:
					return "", fmt.Errorf("Unsupported special variable of type '%s': %s: %s", v, f, awsValue)
				}
			}
		}
	}

	return strings.Join(cloudInitData, ""), nil
}

func handleUserData(userData map[string]interface{}) string {
	userDataStr, err := JoinCfnUserData(userData)

	if err != nil {
		utils.Check(err)
	}

	return userDataStr
}

func ExtractCloudinit(baseCloudinitPath string, awsFormationPath string) bool {
	awsFormationContentStr := utils.ReadFile(awsFormationPath)
	awsMapInt, err := utils.DecodeJson([]byte(awsFormationContentStr))

	if err != nil {
		fmt.Println("Failed to decode JSON: %s", err.Error())
		panic(err)
	}
	awsMap := awsMapInt.(map[string]interface{})

	if err != nil {
		fmt.Errorf("Failed to decode Json")
		return false
	}

	userData := getAwsUserData(awsMap)
	cloudInitDataArr := make([]string, len(userData), len(userData))

	for i := range userData {
		cloudInitDataArr[i] = handleUserData(userData[i])
	}

	for i := range cloudInitDataArr {
		outPath := baseCloudinitPath + strconv.Itoa(i+1) + ".yaml"
		fmt.Printf("Generating file '%s'\n", outPath)
		err := utils.SaveOutput(outPath, cloudInitDataArr[i])

		utils.Check(err)
	}

	return true
}

func Extract() {
	var baseCloudinitPath, awsFormationPath string
	var helpOpt, missingOpts bool

	optarg.Add("h", "help", "Displays this help", false)
	optarg.Add("o", "output-base-path", "Output base path name.", "")
	optarg.Add("i", "cloud-formation", "CloudFormation input file", "")

	for opt := range optarg.Parse() {
		switch opt.ShortName {
		case "o":
			baseCloudinitPath = opt.String()
		case "i":
			awsFormationPath = opt.String()
		case "h":
			helpOpt = opt.Bool()

		default:
			fmt.Println("Invalid flag: ", opt)
			optarg.Usage()
			os.Exit(1)
		}
	}

	if helpOpt {
		optarg.Usage()
		os.Exit(0)
	}

	if baseCloudinitPath == "" {
		fmt.Println("-o is required...")
		missingOpts = true
	}

	if awsFormationPath == "" {
		fmt.Println("-i is required...")
		missingOpts = true
	}

	if missingOpts {
		optarg.Usage()
		os.Exit(1)
	}

	if os.Getenv("DEBUG_OPTS") != "" {
		fmt.Println(baseCloudinitPath)
		fmt.Println(awsFormationPath)
	}

	ExtractCloudinit(baseCloudinitPath, awsFormationPath)
}
<|endoftext|>


<commit_before>package spec

import (
	"encoding/json"
	"fmt"
	"net/http"
	"net/http/httptest"
	"net/url"
	"reflect"
	"testing"

	"github.com/mackerelio/mackerel-agent/config"
)

func TestCloudKey(t *testing.T) {
	g := &CloudGenerator{}

	if g.Key() != "cloud" {
		t.Error("key should be cloud")
	}
}

func TestCloudGenerate(t *testing.T) {
	handler := func(res http.ResponseWriter, req *http.Request) {
		fmt.Fprint(res, "i-4f90d537")
	}
	ts := httptest.NewServer(http.HandlerFunc(func(res http.ResponseWriter, req *http.Request) {
		handler(res, req)
	}))
	defer ts.Close()

	u, err := url.Parse(ts.URL)
	if err != nil {
		t.Errorf("should not raise error: %s", err)
	}
	g := &CloudGenerator{&EC2Generator{u}}

	value, err := g.Generate()
	if err != nil {
		t.Errorf("should not raise error: %s", err)
	}

	cloud, typeOk := value.(map[string]interface{})
	if !typeOk {
		t.Errorf("value should be map. %+v", value)
	}

	value, ok := cloud["metadata"]
	if !ok {
		t.Error("results should have metadata.")
	}

	metadata, typeOk := value.(map[string]string)
	if !typeOk {
		t.Errorf("v should be map. %+v", value)
	}

	if len(metadata["instance-id"]) == 0 {
		t.Error("instance-id should be filled")
	}

	customIdentifier, err := g.SuggestCustomIdentifier()
	if err != nil {
		t.Errorf("should not raise error: %s", err)
	}

	if len(customIdentifier) == 0 {
		t.Error("customIdentifier should be retrieved")
	}
}

func TestGCEGenerate(t *testing.T) {
	// curl "http://metadata.google.internal/computeMetadata/v1/?recursive=true" -H "Metadata-Flavor: Google"
	sampleJSON := []byte(`{
	  "instance": {
		"attributes": {},
		"cpuPlatform": "Intel Ivy Bridge",
		"description": "",
		"disks": [
		  {
			"deviceName": "gce-1",
			"index": 0,
			"mode": "READ_WRITE",
			"type": "PERSISTENT"
		  }
		],
		"hostname": "gce-1.c.dummyproj-987.internal",
		"id": 4567890123456789123,
		"image": "",
		"machineType": "projects/1234567890123/machineTypes/g1-small",
		"maintenanceEvent": "NONE",
		"networkInterfaces": [
		  {
			"accessConfigs": [
			  {
				"externalIp": "203.0.113.1",
				"type": "ONE_TO_ONE_NAT"
			  }
			],
			"forwardedIps": [],
			"ip": "192.0.2.1",
			"network": "projects/1234567890123/networks/default"
		  }
		],
		"scheduling": {
		  "automaticRestart": "TRUE",
		  "onHostMaintenance": "MIGRATE"
		},
		"serviceAccounts": {
		  "1234567890123-compute@developer.gserviceaccount.com": {
			"aliases": [
			  "default"
			],
			"email": "1234567890123-compute@developer.gserviceaccount.com",
			"scopes": [
			  "https://www.googleapis.com/auth/devstorage.read_only",
			  "https://www.googleapis.com/auth/logging.write"
			]
		  },
		  "default": {
			"aliases": [
			  "default"
			],
			"email": "1234567890123-compute@developer.gserviceaccount.com",
			"scopes": [
			  "https://www.googleapis.com/auth/devstorage.read_only",
			  "https://www.googleapis.com/auth/logging.write"
			]
		  }
		},
		"tags": [],
		"virtualClock": {
		  "driftToken": "12345678901234567890"
		},
		"zone": "projects/1234567890123/zones/asia-east1-a"
	  },
	  "project": {
		"attributes": {
		  "google-compute-default-region": "us-central1",
		  "google-compute-default-zone": "us-central1-f",
		  "sshKeys": "dummy_user:ssh-rsa AAAhogehoge google-ssh {\"userName\":\"dummy_user@example.com\",\"expireOn\":\"2015-07-12T11:11:43+0000\"}\ndummy_user:ecdsa-sha2-nistp256 AAAhogefuga google-ssh {\"userName\":\"dummy_user@example.com\",\"expireOn\":\"2015-07-12T11:11:39+0000\"}\n"
		},
		"numericProjectId": 1234567890123,
		"projectId": "dummyprof-987"
	  }
	}`)

	var data gceMeta
	json.Unmarshal(sampleJSON, &data)

	if !reflect.DeepEqual(data.Instance, &gceInstance{
		Zone:         "projects/1234567890123/zones/asia-east1-a",
		InstanceType: "projects/1234567890123/machineTypes/g1-small",
		Hostname:     "gce-1.c.dummyproj-987.internal",
		InstanceID:   4567890123456789123,
	}) {
		t.Errorf("data.Instance should be assigned")
	}

	if !reflect.DeepEqual(data.Project, &gceProject{
		ProjectID:        "dummyprof-987",
		NumericProjectID: 1234567890123,
	}) {
		t.Errorf("data.Project should be assigned")
	}

	if d := data.toGeneratorMeta(); !reflect.DeepEqual(d, map[string]string{
		"zone":          "asia-east1-a",
		"instance-type": "g1-small",
		"hostname":      "gce-1.c.dummyproj-987.internal",
		"instance-id":   "4567890123456789123",
		"projectId":     "dummyprof-987",
	}) {
		t.Errorf("data.Project should be assigned")
	}

}

func TestSuggestCloudGenerator(t *testing.T) {
	// All Cloud meta URLs are unreachable
	unreachableURL, _ := url.Parse("http://unreachable.localhost")
	ec2BaseURL = unreachableURL
	gceMetaURL = unreachableURL
	azureVMBaseURL = unreachableURL

	conf := config.Config{}

	cGen := SuggestCloudGenerator(&conf)
	if cGen != nil {
		t.Errorf("cGen should be nil but, %s", cGen)
	}

	func() { // ec2BaseURL is reachable but returns 404
		ts := httptest.NewServer(http.NotFoundHandler())
		defer ts.Close()
		u, _ := url.Parse(ts.URL)
		ec2BaseURL = u
		defer func() { ec2BaseURL = unreachableURL }()

		cGen = SuggestCloudGenerator(&conf)
		if cGen != nil {
			t.Errorf("cGen should be nil but, %s", cGen)
		}
	}()

	func() { // suggest GCEGenerator
		ts := httptest.NewServer(http.HandlerFunc(func(res http.ResponseWriter, req *http.Request) {
			fmt.Fprint(res, "GCE:OK")
		}))
		defer ts.Close()
		u, _ := url.Parse(ts.URL)
		gceMetaURL = u
		defer func() { gceMetaURL = unreachableURL }()

		cGen = SuggestCloudGenerator(&conf)
		if cGen == nil {
			t.Errorf("cGen should not be nil.")
		}

		gceGen, ok := cGen.CloudMetaGenerator.(*GCEGenerator)
		if !ok {
			t.Errorf("cGen should be *GCEGenerator")
		}
		if gceGen.metaURL != gceMetaURL {
			t.Errorf("something went wrong")
		}
	}()

	func() { // suggest AzureVMGenerator
		ts := httptest.NewServer(http.HandlerFunc(func(res http.ResponseWriter, req *http.Request) {
			if req.Header.Get("Metadata") != "true" {
				http.NotFound(res, req)
			}
			fmt.Fprint(res, "ok")
		}))
		defer ts.Close()
		u, _ := url.Parse(ts.URL)
		azureVMBaseURL = u
		defer func() { azureVMBaseURL = unreachableURL }()

		cGen = SuggestCloudGenerator(&conf)
		if cGen == nil {
			t.Errorf("cGen should not be nil.")
		}

		gen, ok := cGen.CloudMetaGenerator.(*AzureVMGenerator)
		if !ok {
			t.Errorf("cGen should be *AzureVMGenerator")
		}
		if gen.baseURL != azureVMBaseURL {
			t.Errorf("something went wrong")
		}
	}()
}

func TestSuggestCloudGenerator_CloudPlatformSpecified(t *testing.T) {
	// All Cloud meta URLs are unreachable
	unreachableURL, _ := url.Parse("http://unreachable.localhost")
	ec2BaseURL = unreachableURL
	gceMetaURL = unreachableURL
	azureVMBaseURL = unreachableURL

	func() {
		conf := config.Config{
			CloudPlatform: config.CloudPlatformNone,
		}

		cGen := SuggestCloudGenerator(&conf)
		if cGen != nil {
			t.Errorf("cGen should be nil.")
		}
	}()

	func() {
		conf := config.Config{
			CloudPlatform: config.CloudPlatformEC2,
		}

		cGen := SuggestCloudGenerator(&conf)
		if cGen == nil {
			t.Errorf("cGen should not be nil.")
		}

		_, ok := cGen.CloudMetaGenerator.(*EC2Generator)
		if !ok {
			t.Errorf("cGen should be *EC2Generator")
		}
	}()

	func() {
		conf := config.Config{
			CloudPlatform: config.CloudPlatformGCE,
		}

		cGen := SuggestCloudGenerator(&conf)
		if cGen == nil {
			t.Errorf("cGen should not be nil.")
		}

		_, ok := cGen.CloudMetaGenerator.(*GCEGenerator)
		if !ok {
			t.Errorf("cGen should be *GCEGenerator")
		}
	}()

	func() {
		conf := config.Config{
			CloudPlatform: config.CloudPlatformAzureVM,
		}

		cGen := SuggestCloudGenerator(&conf)
		if cGen == nil {
			t.Errorf("cGen should not be nil.")
		}

		_, ok := cGen.CloudMetaGenerator.(*AzureVMGenerator)
		if !ok {
			t.Errorf("cGen should be *AzureVMGenerator")
		}
	}()
}
<commit_msg>Use lexical scope<commit_after>package spec

import (
	"encoding/json"
	"fmt"
	"net/http"
	"net/http/httptest"
	"net/url"
	"reflect"
	"testing"

	"github.com/mackerelio/mackerel-agent/config"
)

func TestCloudKey(t *testing.T) {
	g := &CloudGenerator{}

	if g.Key() != "cloud" {
		t.Error("key should be cloud")
	}
}

func TestCloudGenerate(t *testing.T) {
	handler := func(res http.ResponseWriter, req *http.Request) {
		fmt.Fprint(res, "i-4f90d537")
	}
	ts := httptest.NewServer(http.HandlerFunc(func(res http.ResponseWriter, req *http.Request) {
		handler(res, req)
	}))
	defer ts.Close()

	u, err := url.Parse(ts.URL)
	if err != nil {
		t.Errorf("should not raise error: %s", err)
	}
	g := &CloudGenerator{&EC2Generator{u}}

	value, err := g.Generate()
	if err != nil {
		t.Errorf("should not raise error: %s", err)
	}

	cloud, typeOk := value.(map[string]interface{})
	if !typeOk {
		t.Errorf("value should be map. %+v", value)
	}

	value, ok := cloud["metadata"]
	if !ok {
		t.Error("results should have metadata.")
	}

	metadata, typeOk := value.(map[string]string)
	if !typeOk {
		t.Errorf("v should be map. %+v", value)
	}

	if len(metadata["instance-id"]) == 0 {
		t.Error("instance-id should be filled")
	}

	customIdentifier, err := g.SuggestCustomIdentifier()
	if err != nil {
		t.Errorf("should not raise error: %s", err)
	}

	if len(customIdentifier) == 0 {
		t.Error("customIdentifier should be retrieved")
	}
}

func TestGCEGenerate(t *testing.T) {
	// curl "http://metadata.google.internal/computeMetadata/v1/?recursive=true" -H "Metadata-Flavor: Google"
	sampleJSON := []byte(`{
	  "instance": {
		"attributes": {},
		"cpuPlatform": "Intel Ivy Bridge",
		"description": "",
		"disks": [
		  {
			"deviceName": "gce-1",
			"index": 0,
			"mode": "READ_WRITE",
			"type": "PERSISTENT"
		  }
		],
		"hostname": "gce-1.c.dummyproj-987.internal",
		"id": 4567890123456789123,
		"image": "",
		"machineType": "projects/1234567890123/machineTypes/g1-small",
		"maintenanceEvent": "NONE",
		"networkInterfaces": [
		  {
			"accessConfigs": [
			  {
				"externalIp": "203.0.113.1",
				"type": "ONE_TO_ONE_NAT"
			  }
			],
			"forwardedIps": [],
			"ip": "192.0.2.1",
			"network": "projects/1234567890123/networks/default"
		  }
		],
		"scheduling": {
		  "automaticRestart": "TRUE",
		  "onHostMaintenance": "MIGRATE"
		},
		"serviceAccounts": {
		  "1234567890123-compute@developer.gserviceaccount.com": {
			"aliases": [
			  "default"
			],
			"email": "1234567890123-compute@developer.gserviceaccount.com",
			"scopes": [
			  "https://www.googleapis.com/auth/devstorage.read_only",
			  "https://www.googleapis.com/auth/logging.write"
			]
		  },
		  "default": {
			"aliases": [
			  "default"
			],
			"email": "1234567890123-compute@developer.gserviceaccount.com",
			"scopes": [
			  "https://www.googleapis.com/auth/devstorage.read_only",
			  "https://www.googleapis.com/auth/logging.write"
			]
		  }
		},
		"tags": [],
		"virtualClock": {
		  "driftToken": "12345678901234567890"
		},
		"zone": "projects/1234567890123/zones/asia-east1-a"
	  },
	  "project": {
		"attributes": {
		  "google-compute-default-region": "us-central1",
		  "google-compute-default-zone": "us-central1-f",
		  "sshKeys": "dummy_user:ssh-rsa AAAhogehoge google-ssh {\"userName\":\"dummy_user@example.com\",\"expireOn\":\"2015-07-12T11:11:43+0000\"}\ndummy_user:ecdsa-sha2-nistp256 AAAhogefuga google-ssh {\"userName\":\"dummy_user@example.com\",\"expireOn\":\"2015-07-12T11:11:39+0000\"}\n"
		},
		"numericProjectId": 1234567890123,
		"projectId": "dummyprof-987"
	  }
	}`)

	var data gceMeta
	json.Unmarshal(sampleJSON, &data)

	if !reflect.DeepEqual(data.Instance, &gceInstance{
		Zone:         "projects/1234567890123/zones/asia-east1-a",
		InstanceType: "projects/1234567890123/machineTypes/g1-small",
		Hostname:     "gce-1.c.dummyproj-987.internal",
		InstanceID:   4567890123456789123,
	}) {
		t.Errorf("data.Instance should be assigned")
	}

	if !reflect.DeepEqual(data.Project, &gceProject{
		ProjectID:        "dummyprof-987",
		NumericProjectID: 1234567890123,
	}) {
		t.Errorf("data.Project should be assigned")
	}

	if d := data.toGeneratorMeta(); !reflect.DeepEqual(d, map[string]string{
		"zone":          "asia-east1-a",
		"instance-type": "g1-small",
		"hostname":      "gce-1.c.dummyproj-987.internal",
		"instance-id":   "4567890123456789123",
		"projectId":     "dummyprof-987",
	}) {
		t.Errorf("data.Project should be assigned")
	}

}

func TestSuggestCloudGenerator(t *testing.T) {
	// All Cloud meta URLs are unreachable
	unreachableURL, _ := url.Parse("http://unreachable.localhost")
	ec2BaseURL = unreachableURL
	gceMetaURL = unreachableURL
	azureVMBaseURL = unreachableURL

	conf := config.Config{}

	cGen := SuggestCloudGenerator(&conf)
	if cGen != nil {
		t.Errorf("cGen should be nil but, %s", cGen)
	}

	func() { // ec2BaseURL is reachable but returns 404
		ts := httptest.NewServer(http.NotFoundHandler())
		defer ts.Close()
		u, _ := url.Parse(ts.URL)
		ec2BaseURL = u
		defer func() { ec2BaseURL = unreachableURL }()

		cGen = SuggestCloudGenerator(&conf)
		if cGen != nil {
			t.Errorf("cGen should be nil but, %s", cGen)
		}
	}()

	func() { // suggest GCEGenerator
		ts := httptest.NewServer(http.HandlerFunc(func(res http.ResponseWriter, req *http.Request) {
			fmt.Fprint(res, "GCE:OK")
		}))
		defer ts.Close()
		u, _ := url.Parse(ts.URL)
		gceMetaURL = u
		defer func() { gceMetaURL = unreachableURL }()

		cGen = SuggestCloudGenerator(&conf)
		if cGen == nil {
			t.Errorf("cGen should not be nil.")
		}

		gceGen, ok := cGen.CloudMetaGenerator.(*GCEGenerator)
		if !ok {
			t.Errorf("cGen should be *GCEGenerator")
		}
		if gceGen.metaURL != gceMetaURL {
			t.Errorf("something went wrong")
		}
	}()

	func() { // suggest AzureVMGenerator
		ts := httptest.NewServer(http.HandlerFunc(func(res http.ResponseWriter, req *http.Request) {
			if req.Header.Get("Metadata") != "true" {
				http.NotFound(res, req)
			}
			fmt.Fprint(res, "ok")
		}))
		defer ts.Close()
		u, _ := url.Parse(ts.URL)
		azureVMBaseURL = u
		defer func() { azureVMBaseURL = unreachableURL }()

		cGen = SuggestCloudGenerator(&conf)
		if cGen == nil {
			t.Errorf("cGen should not be nil.")
		}

		gen, ok := cGen.CloudMetaGenerator.(*AzureVMGenerator)
		if !ok {
			t.Errorf("cGen should be *AzureVMGenerator")
		}
		if gen.baseURL != azureVMBaseURL {
			t.Errorf("something went wrong")
		}
	}()
}

func TestSuggestCloudGenerator_CloudPlatformSpecified(t *testing.T) {
	// All Cloud meta URLs are unreachable
	unreachableURL, _ := url.Parse("http://unreachable.localhost")
	ec2BaseURL = unreachableURL
	gceMetaURL = unreachableURL
	azureVMBaseURL = unreachableURL

	{
		conf := config.Config{
			CloudPlatform: config.CloudPlatformNone,
		}

		cGen := SuggestCloudGenerator(&conf)
		if cGen != nil {
			t.Errorf("cGen should be nil.")
		}
	}

	{
		conf := config.Config{
			CloudPlatform: config.CloudPlatformEC2,
		}

		cGen := SuggestCloudGenerator(&conf)
		if cGen == nil {
			t.Errorf("cGen should not be nil.")
		}

		_, ok := cGen.CloudMetaGenerator.(*EC2Generator)
		if !ok {
			t.Errorf("cGen should be *EC2Generator")
		}
	}

	{
		conf := config.Config{
			CloudPlatform: config.CloudPlatformGCE,
		}

		cGen := SuggestCloudGenerator(&conf)
		if cGen == nil {
			t.Errorf("cGen should not be nil.")
		}

		_, ok := cGen.CloudMetaGenerator.(*GCEGenerator)
		if !ok {
			t.Errorf("cGen should be *GCEGenerator")
		}
	}

	{
		conf := config.Config{
			CloudPlatform: config.CloudPlatformAzureVM,
		}

		cGen := SuggestCloudGenerator(&conf)
		if cGen == nil {
			t.Errorf("cGen should not be nil.")
		}

		_, ok := cGen.CloudMetaGenerator.(*AzureVMGenerator)
		if !ok {
			t.Errorf("cGen should be *AzureVMGenerator")
		}
	}
}
<|endoftext|>


<commit_before>package checkmgr

import (
	"testing"
)

func TestIsMetricActive(t *testing.T) {
	t.Log("Testing correct return from IsMetricActive")

	cm := &CheckManager{}

	cm.activeMetrics = map[string]bool{
		"foo": true,
	}

	t.Log("Testing for 'foo', foo in list")
	if !cm.IsMetricActive("foo") {
		t.Error("Expected true")
	}

	t.Log("Testing for 'bar', bar not in list")
	if cm.IsMetricActive("bar") {
		t.Error("Expected false")
	}
}
<commit_msg>add inventoryMetric test<commit_after>package checkmgr

import (
	"testing"

	"github.com/circonus-labs/circonus-gometrics/api"
)

func TestIsMetricActive(t *testing.T) {
	t.Log("Testing correct return from IsMetricActive")

	cm := &CheckManager{}

	cm.activeMetrics = map[string]bool{
		"foo": true,
	}

	t.Log("Testing for 'foo', foo in list")
	if !cm.IsMetricActive("foo") {
		t.Error("Expected true")
	}

	t.Log("Testing for 'bar', bar not in list")
	if cm.IsMetricActive("bar") {
		t.Error("Expected false")
	}
}

func TestInventoryMetrics(t *testing.T) {
	t.Log("Testing correct return from IsMetricActive")

	cm := &CheckManager{}
	cm.checkBundle = &api.CheckBundle{}
	cm.checkBundle.Metrics = []api.CheckBundleMetric{
		api.CheckBundleMetric{
			Name:   "foo",
			Type:   "text",
			Status: "active",
		},
	}

	cm.activeMetrics = make(map[string]bool)
	t.Log("Testing for 'foo', foo not in list")
	if cm.IsMetricActive("foo") {
		t.Error("Expected false")
	}

	t.Log("Inventory metrics in check bundle")
	cm.inventoryMetrics()

	t.Log("Testing for 'foo', foo in list")
	if !cm.IsMetricActive("foo") {
		t.Error("Expected true")
	}

	t.Log("Testing for 'bar', bar not in list")
	if cm.IsMetricActive("bar") {
		t.Error("Expected false")
	}
}
<|endoftext|>