<commit_before>package main

// The import section defines libraries that we are going to use in our program.
import (
	"fmt"
	"log"
	"net/http"

	"encoding/json"
	"github.com/gorilla/mux"
	"github.com/ory-am/common/env"
	"github.com/ory-am/common/pkg"
	"github.com/pborman/uuid"
	"github.com/rs/cors"
	"math"
	"strconv"

	"github.com/jmoiron/sqlx"
	_ "github.com/lib/pq"
	. "github.com/ory-am/workshop-dbg/store"
	"github.com/ory-am/workshop-dbg/store/memory"
	"github.com/ory-am/workshop-dbg/store/postgres"
)

// In a 12 factor app, we must obey the environment variables.
var envHost = env.Getenv("HOST", "")
var envPort = env.Getenv("PORT", "5678")
var databaseURL = env.Getenv("DATABASE_URL", "")
var thisID = uuid.New()

// MyContacts is an exemplary list of contacts.
var MyContacts = Contacts{
	// Each contact hs identified by its ID which is prepended with "my-id":
	// We are doing this because it is easier to manage and simpler to read.
	"john-bravo": &Contact{
		Name:       "Andreas Preuss",
		Department: "IT",
		Company:    "ACME Inc",
	},
	"cathrine-mueller": &Contact{
		Name:       "Cathrine Müller",
		Department: "HR",
		Company:    "Grove AG",
	},
	"maximilian-schmidt": &Contact{
		Name:       "Maximilian Schmidt",
		Department: "PR",
		Company:    "Titanpad AG",
	},
	"uwe-charly": &Contact{
		Name:       "Uwe Charly",
		Department: "FAC",
		Company:    "KPMG",
	},
}

var memoryStore = &memory.InMemoryStore{Contacts: MyContacts}

// The main routine is going the "entry" point.
func main() {
	// Create a new router.
	router := mux.NewRouter()

	// RESTful defines operations
	// * GET for fetching data
	// * POST for inserting data
	// * PUT for updating existing data
	// * DELETE for deleting data
	router.HandleFunc("/memory/contacts", ListContacts(memoryStore)).Methods("GET")
	router.HandleFunc("/memory/contacts", AddContact(memoryStore)).Methods("POST")
	router.HandleFunc("/memory/contacts/{id}", UpdateContact(memoryStore)).Methods("PUT")
	router.HandleFunc("/memory/contacts/{id}", DeleteContact(memoryStore)).Methods("DELETE")

	// Connect to database store
	db, err := sqlx.Connect("postgres", databaseURL)
	if err != nil {
		log.Printf("Could not connect to database because %s", err)
	} else {
		databaseStore := &postgres.PostgresStore{DB: db}
		if err := databaseStore.CreateSchemas(); err != nil {
			log.Printf("Could not set up relations %s", err)
		} else {
			router.HandleFunc("/database/contacts", ListContacts(databaseStore)).Methods("GET")
			router.HandleFunc("/database/contacts", AddContact(databaseStore)).Methods("POST")
			router.HandleFunc("/database/contacts/{id}", UpdateContact(databaseStore)).Methods("PUT")
			router.HandleFunc("/database/contacts/{id}", DeleteContact(databaseStore)).Methods("DELETE")
		}
	}

	// The info endpoint is for showing demonstration purposes only and is not subject to any task.
	router.HandleFunc("/info", InfoHandler).Methods("GET")
	router.HandleFunc("/pi", ComputePi).Methods("GET")

	// Print where to point the browser at.
	fmt.Printf("Listening on %s\n", "http://localhost:5678")

	// Cross origin resource requests
	c := cors.New(cors.Options{
		AllowedOrigins: []string{"*"},
		AllowedMethods: []string{"GET", "POST", "DELETE", "PUT"}},
	)

	// Start up the server and check for errors.
	listenOn := fmt.Sprintf("%s:%s", envHost, envPort)
	if err := http.ListenAndServe(listenOn, c.Handler(router)); err != nil {
		log.Fatalf("Could not set up server because %s", err)
	}
}

// ListContacts takes a contact list and outputs it.
func ListContacts(store ContactStorer) func(rw http.ResponseWriter, r *http.Request) {
	return func(rw http.ResponseWriter, r *http.Request) {

		// Write contact list to output
		contacts, err := store.FetchContacts()
		if err != nil {
			http.Error(rw, err.Error(), http.StatusInternalServerError)
			return
		}

		pkg.WriteIndentJSON(rw, contacts)
	}
}

// AddContact will add a contact to the list
func AddContact(contacts ContactStorer) func(rw http.ResponseWriter, r *http.Request) {
	return func(rw http.ResponseWriter, r *http.Request) {

		// We parse the request's information into contactToBeAdded
		contactToBeAdded, err := ReadContactData(rw, r)

		// Abort handling the request if an error occurs.
		if err != nil {
			http.Error(rw, err.Error(), http.StatusInternalServerError)
			return
		}

		// Save newContact to the list of contacts.
		if err = contacts.CreateContact(&contactToBeAdded); err != nil {
			http.Error(rw, err.Error(), http.StatusInternalServerError)
			return
		}

		// Output our newly created contact
		pkg.WriteIndentJSON(rw, contactToBeAdded)
	}
}

// DeleteContact will delete a contact from the list
func DeleteContact(contacts ContactStorer) func(rw http.ResponseWriter, r *http.Request) {
	return func(rw http.ResponseWriter, r *http.Request) {
		// Fetch the ID of the contact that is going to be deleted
		contactToBeDeleted := mux.Vars(r)["id"]

		// Delete the contact from the list
		if err := contacts.DeleteContact(contactToBeDeleted); err != nil {
			http.Error(rw, err.Error(), http.StatusInternalServerError)
			return
		}

		// Per specification, RESTful may return an empty response when a DELETE request was successful
		rw.WriteHeader(http.StatusNoContent)
	}
}

// UpdateContact will update a contact on the list
func UpdateContact(store ContactStorer) func(rw http.ResponseWriter, r *http.Request) {
	return func(rw http.ResponseWriter, r *http.Request) {
		// We parse the request's information into newContactData.
		newContactData, err := ReadContactData(rw, r)

		// Abort handling the request if an error occurs.
		if err != nil {
			http.Error(rw, err.Error(), http.StatusBadRequest)
			return
		}

		// Update the data in the contact list.
		if err := store.UpdateContact(&newContactData); err != nil {
			http.Error(rw, err.Error(), http.StatusInternalServerError)
			return
		}

		// Set the new data
		pkg.WriteIndentJSON(rw, newContactData)
	}
}

// ReadContactData is a helper function for parsing a HTTP request body. It returns a contact on success and an
// error if something went wrong.
func ReadContactData(rw http.ResponseWriter, r *http.Request) (contact Contact, err error) {
	err = json.NewDecoder(r.Body).Decode(&contact)
	if err != nil {
		http.Error(rw, fmt.Sprintf("Could not read input data because %s", err), http.StatusBadRequest)
		return contact, err
	}

	return contact, nil
}

func ComputePi(rw http.ResponseWriter, r *http.Request) {
	n, err := strconv.Atoi(r.URL.Query().Get("n"))
	if err != nil {
		n = 0
	}

	pkg.WriteIndentJSON(rw, struct {
		Pi string `json:"pi"`
		N  int    `json:"n"`
	}{
		Pi: strconv.FormatFloat(pi(n), 'E', -1, 64),
		N:  n,
	})
}

func InfoHandler(rw http.ResponseWriter, r *http.Request) {
	rw.Write([]byte(thisID))
}

// pi launches n goroutines to compute an
// approximation of pi.
func pi(n int) float64 {
	ch := make(chan float64)
	for k := 0; k <= n; k++ {
		go term(ch, float64(k))
	}
	f := 0.0
	for k := 0; k <= n; k++ {
		f += <-ch
	}
	return f
}

func term(ch chan float64, k float64) {
	ch <- 4 * math.Pow(-1, k) / (2 * k + 1)
}
<commit_msg>und weg damit ...<commit_after>package main

// The import section defines libraries that we are going to use in our program.
import (
	"fmt"
	"log"
	"net/http"

	"encoding/json"
	"github.com/gorilla/mux"
	"github.com/ory-am/common/env"
	"github.com/ory-am/common/pkg"
	"github.com/pborman/uuid"
	"github.com/rs/cors"
	"math"
	"strconv"

	"github.com/jmoiron/sqlx"
	_ "github.com/lib/pq"
	. "github.com/ory-am/workshop-dbg/store"
	"github.com/ory-am/workshop-dbg/store/memory"
	"github.com/ory-am/workshop-dbg/store/postgres"
)

// In a 12 factor app, we must obey the environment variables.
var envHost = env.Getenv("HOST", "")
var envPort = env.Getenv("PORT", "5678")
var databaseURL = env.Getenv("DATABASE_URL", "")
var thisID = uuid.New()

// MyContacts is an exemplary list of contacts.
var MyContacts = Contacts{
	// Each contact hs identified by its ID which is prepended with "my-id":
	// We are doing this because it is easier to manage and simpler to read.
	"john-bravo": &Contact{
		Name:       "Andreas Preuss",
		Department: "IT",
		Company:    "ACME Inc",
	},
	"cathrine-mueller": &Contact{
		Name:       "Cathrine Müller",
		Department: "HR",
		Company:    "Grove AG",
	},
	"maximilian-schmidt": &Contact{
		Name:       "Maximilian Schmidt",
		Department: "PR",
		Company:    "Titanpad AG",
	},
	"uwe-charly": &Contact{
		Name:       "Uwe Charly",
		Department: "FAC",
		Company:    "KPMG",
	},
	"frank-sec": &Contact{
		Name:       "Frank Secure",
		Department: "Unknown",
		Company:    "Secret",
	},
	"juergen-elsner": &Contact{
		Name:       "Jürgen Elsner",
		Department: "DaCS",
		Company:    "DBG",
	},
}

var memoryStore = &memory.InMemoryStore{Contacts: MyContacts}

// The main routine is going the "entry" point.
func main() {
	// Create a new router.
	router := mux.NewRouter()

	// RESTful defines operations
	// * GET for fetching data
	// * POST for inserting data
	// * PUT for updating existing data
	// * DELETE for deleting data
	router.HandleFunc("/memory/contacts", ListContacts(memoryStore)).Methods("GET")
	router.HandleFunc("/memory/contacts", AddContact(memoryStore)).Methods("POST")
	router.HandleFunc("/memory/contacts/{id}", UpdateContact(memoryStore)).Methods("PUT")
	router.HandleFunc("/memory/contacts/{id}", DeleteContact(memoryStore)).Methods("DELETE")

	// Connect to database store
	db, err := sqlx.Connect("postgres", databaseURL)
	if err != nil {
		log.Printf("Could not connect to database because %s", err)
	} else {
		databaseStore := &postgres.PostgresStore{DB: db}
		if err := databaseStore.CreateSchemas(); err != nil {
			log.Printf("Could not set up relations %s", err)
		} else {
			router.HandleFunc("/database/contacts", ListContacts(databaseStore)).Methods("GET")
			router.HandleFunc("/database/contacts", AddContact(databaseStore)).Methods("POST")
			router.HandleFunc("/database/contacts/{id}", UpdateContact(databaseStore)).Methods("PUT")
			router.HandleFunc("/database/contacts/{id}", DeleteContact(databaseStore)).Methods("DELETE")
		}
	}

	// The info endpoint is for showing demonstration purposes only and is not subject to any task.
	router.HandleFunc("/info", InfoHandler).Methods("GET")
	router.HandleFunc("/pi", ComputePi).Methods("GET")

	// Print where to point the browser at.
	fmt.Printf("Listening on %s\n", "http://localhost:5678")

	// Cross origin resource requests
	c := cors.New(cors.Options{
		AllowedOrigins: []string{"*"},
		AllowedMethods: []string{"GET", "POST", "DELETE", "PUT"}},
	)

	// Start up the server and check for errors.
	listenOn := fmt.Sprintf("%s:%s", envHost, envPort)
	if err := http.ListenAndServe(listenOn, c.Handler(router)); err != nil {
		log.Fatalf("Could not set up server because %s", err)
	}
}

// ListContacts takes a contact list and outputs it.
func ListContacts(store ContactStorer) func(rw http.ResponseWriter, r *http.Request) {
	return func(rw http.ResponseWriter, r *http.Request) {

		// Write contact list to output
		contacts, err := store.FetchContacts()
		if err != nil {
			http.Error(rw, err.Error(), http.StatusInternalServerError)
			return
		}

		pkg.WriteIndentJSON(rw, contacts)
	}
}

// AddContact will add a contact to the list
func AddContact(contacts ContactStorer) func(rw http.ResponseWriter, r *http.Request) {
	return func(rw http.ResponseWriter, r *http.Request) {

		// We parse the request's information into contactToBeAdded
		contactToBeAdded, err := ReadContactData(rw, r)

		// Abort handling the request if an error occurs.
		if err != nil {
			http.Error(rw, err.Error(), http.StatusInternalServerError)
			return
		}

		// Save newContact to the list of contacts.
		if err = contacts.CreateContact(&contactToBeAdded); err != nil {
			http.Error(rw, err.Error(), http.StatusInternalServerError)
			return
		}

		// Output our newly created contact
		pkg.WriteIndentJSON(rw, contactToBeAdded)
	}
}

// DeleteContact will delete a contact from the list
func DeleteContact(contacts ContactStorer) func(rw http.ResponseWriter, r *http.Request) {
	return func(rw http.ResponseWriter, r *http.Request) {
		// Fetch the ID of the contact that is going to be deleted
		contactToBeDeleted := mux.Vars(r)["id"]

		// Delete the contact from the list
		if err := contacts.DeleteContact(contactToBeDeleted); err != nil {
			http.Error(rw, err.Error(), http.StatusInternalServerError)
			return
		}

		// Per specification, RESTful may return an empty response when a DELETE request was successful
		rw.WriteHeader(http.StatusNoContent)
	}
}

// UpdateContact will update a contact on the list
func UpdateContact(store ContactStorer) func(rw http.ResponseWriter, r *http.Request) {
	return func(rw http.ResponseWriter, r *http.Request) {
		// We parse the request's information into newContactData.
		newContactData, err := ReadContactData(rw, r)

		// Abort handling the request if an error occurs.
		if err != nil {
			http.Error(rw, err.Error(), http.StatusBadRequest)
			return
		}

		// Update the data in the contact list.
		if err := store.UpdateContact(&newContactData); err != nil {
			http.Error(rw, err.Error(), http.StatusInternalServerError)
			return
		}

		// Set the new data
		pkg.WriteIndentJSON(rw, newContactData)
	}
}

// ReadContactData is a helper function for parsing a HTTP request body. It returns a contact on success and an
// error if something went wrong.
func ReadContactData(rw http.ResponseWriter, r *http.Request) (contact Contact, err error) {
	err = json.NewDecoder(r.Body).Decode(&contact)
	if err != nil {
		http.Error(rw, fmt.Sprintf("Could not read input data because %s", err), http.StatusBadRequest)
		return contact, err
	}

	return contact, nil
}

func ComputePi(rw http.ResponseWriter, r *http.Request) {
	n, err := strconv.Atoi(r.URL.Query().Get("n"))
	if err != nil {
		n = 0
	}

	pkg.WriteIndentJSON(rw, struct {
		Pi string `json:"pi"`
		N  int    `json:"n"`
	}{
		Pi: strconv.FormatFloat(pi(n), 'E', -1, 64),
		N:  n,
	})
}

func InfoHandler(rw http.ResponseWriter, r *http.Request) {
	rw.Write([]byte(thisID))
}

// pi launches n goroutines to compute an
// approximation of pi.
func pi(n int) float64 {
	ch := make(chan float64)
	for k := 0; k <= n; k++ {
		go term(ch, float64(k))
	}
	f := 0.0
	for k := 0; k <= n; k++ {
		f += <-ch
	}
	return f
}

func term(ch chan float64, k float64) {
	ch <- 4 * math.Pow(-1, k) / (2 * k + 1)
}
<|endoftext|>


<commit_before>package main

import (
	"fmt"

	"github.com/golliher/go-sharptv/commands"
	"github.com/spf13/viper"
)

// Flags that are to be added to commands
// var ip, port string

func main() {

	viper.SetConfigName("config")
	viper.AddConfigPath("$HOME/.sharptv")
	viper.SetDefault("debug", false)

	err := viper.ReadInConfig() // Find and read the config file
	if err != nil {             // Handle errors reading the config file
		panic(fmt.Errorf("Fatal error config file: %s \n", err))
	}

	if viper.GetBool("debug") {
		fmt.Println("debug enabled")
	}

	commands.SharptvCmd.Execute()
}
<commit_msg>Added configuration via GOSHARPTV_XX environment variables for PORT, IP and DEBUG<commit_after>package main

import (
	"fmt"

	"github.com/golliher/go-sharptv/commands"
	"github.com/spf13/viper"
)

func main() {

	// Set config file
	viper.SetConfigName("config")

	// Add config path
	viper.AddConfigPath("$HOME/.sharptv")

	// Read in the config
	err := viper.ReadInConfig() // Find and read the config file
	if err != nil {             // Handle errors reading the config file
		panic(fmt.Errorf("Fatal error config file: %s \n", err))
	}

	// Load default settings
	viper.SetDefault("debug", false)

	viper.SetEnvPrefix("gosharptv") // will be uppercased automatically
	viper.BindEnv("debug")
	viper.BindEnv("ip")
	viper.BindEnv("port")

	if viper.IsSet("ip") {
		ip := viper.GetString("ip")
		fmt.Printf("IP of TV to connect to: %s\n", ip)
	}

	// Do some flag handling and any complicated config logic

	// Start using configuration

	if viper.GetBool("debug") {
		fmt.Println("debug enabled")
	}

	commands.SharptvCmd.Execute()
}
<|endoftext|>


<commit_before>package main

import (
	"flag"
	"os"
)

const (
	ExitCodeOK int = iota
	ExitCodeError
	ExitCodeFileError
)

var app App

func init() {
	var configPath string
	var index int
	var dryRun bool
	flag.StringVar(&configPath, "c", "", "/path/to/config.json. (default: $HOME/.config/prnotify/config.json)")
	flag.IntVar(&index, "swi", 0, "Slack Webhooks Index (default: 0)")
	flag.BoolVar(&dryRun, "d", false, "A dry run will not send any message to Slack. (defualt: false)")
	flag.Parse()

	// Prepare config
	config, err := NewConfig(configPath, index, dryRun)
	if err != nil {
		os.Exit(ExitCodeError)
	}

	// Prepare app
	app, err = NewApp(config)
	if err != nil {
		os.Exit(ExitCodeError)
	}
}

func main() {
	os.Exit(app.Run())
}
<commit_msg>Support print version<commit_after>package main

import (
	"flag"
	"fmt"
	"os"
)

const (
	ExitCodeOK int = iota
	ExitCodeError
	ExitCodeFileError
)

var (
	Version  string
	Revision string
)

var app App

func init() {
	var configPath string
	var index int
	var dryRun, version bool
	flag.StringVar(&configPath, "c", "", "/path/to/config.json. (default: $HOME/.config/prnotify/config.json)")
	flag.IntVar(&index, "swi", 0, "Slack Webhooks Index (default: 0)")
	flag.BoolVar(&dryRun, "d", false, "A dry run will not send any message to Slack. (defualt: false)")
	flag.BoolVar(&version, "v", false, "Print version.")
	flag.Parse()

	if version {
		fmt.Fprintln(os.Stdout, "Version:", Version)
		fmt.Fprintln(os.Stdout, "Revision:", Revision)
		os.Exit(ExitCodeOK)
	}

	// Prepare config
	config, err := NewConfig(configPath, index, dryRun)
	if err != nil {
		os.Exit(ExitCodeError)
	}

	// Prepare app
	app, err = NewApp(config)
	if err != nil {
		os.Exit(ExitCodeError)
	}
}

func main() {
	os.Exit(app.Run())
}
<|endoftext|>


<commit_before>// Rescue as much as possible from your Picturelife account
package main

import (
	"bufio"
	"encoding/json"
	"flag"
	"fmt"
	"io"
	"io/ioutil"
	"net/url"
	"os"
	"regexp"
	"strconv"
	"strings"
	"sync"

	"golang.org/x/crypto/ssh/terminal"

	"github.com/cheggaaa/pb"
)

type Media struct {
	Id             string `json:"id"`
	MediaType      string `json:"media_type"`
	Format         string `json:"format"`
	Processed      bool   `json:"processed"`
	CreatedAt      int    `json:"created_at"`
	UpdatedAt      int    `json:"updated_at"`
	TakenAt        int    `json:"taken_at"`
	Width          int    `json:"width"`
	Height         int    `json:"height"`
	Orientation    int    `json:"orientation"`
	Privacy        int    `json:"privacy"`
	IsBestPhoto    bool   `json:"is_best_photo"`
	TimeZoneOffset int    `json:"time_zone_offset"`
	Hidden         bool   `json:"hidden"`
	Visible        bool   `json:"visible"`
	Filesize       int    `json:"filesize"`
	BucketId       int    `json:"bucket_id"`
	Status         string `json:"status"`
	Retries        int    `json:"retries"`
}

type APIResponse struct {
	Status       int     `json:"status"`
	Media        []Media `json:"media"`
	Total        int     `json:"total"`
	Limit        int     `json:"limit"`
	Offset       int     `json:"offset"`
	UsingCache   bool    `json:"using_cache"`
	ResponseTime int     `json:"response_time"`
}

var (
	loginUrl    *url.URL
	signinUrl   *url.URL
	apiPageUrl  *url.URL
	apiUrl      *url.URL
	originalUrl *url.URL

	signinValues url.Values

	accessTokenRE *regexp.Regexp
	accessToken   string

	pathPerm os.FileMode = 0770
	filePerm os.FileMode = 0770

	mediaPath string = "picturelife"
	indexPath string = "pl_index.json"

	// Flags
	retryFlag  bool = false // Retry failed images and videos?
	helpFlag   bool = false // Retry failed images and videos?
	statusFlag bool = false // Retry failed images and videos?
)

func init() {
	var err error

	flag.BoolVar(&retryFlag, "retry", retryFlag, "Retry failed images and videos?")
	flag.BoolVar(&helpFlag, "help", helpFlag, "Print help text")
	flag.BoolVar(&statusFlag, "status", statusFlag, "Print out current status")

	loginUrl, err = url.Parse("http://picturelife.com/login")
	if err != nil {
		panic("Unable to parse login URL")
	}

	// Login posts to this
	signinUrl, err = url.Parse("http://picturelife.com/signin")
	if err != nil {
		panic("Unable to parse sign in URL")
	}

	apiPageUrl, err = url.Parse("http://picturelife.com/api")
	if err != nil {
		panic("Unable to parse API Page URL")
	}

	originalUrl, err = url.Parse("http://picturelife.com/d/original/")
	if err != nil {
		panic("Unable to parse API Page URL")
	}

	accessTokenRE = regexp.MustCompile("<script>\\s*pl\\.access_token\\s*=\\s*'([^']+)';\\s*pl\\.api_url\\s*=\\s*'([^']+)'\\s*</script>")

	err = os.MkdirAll(mediaPath, pathPerm)
	if err != nil {
		panic(err)
	}
}

func main() {
	flag.Parse()

	if helpFlag {
		printHelp()
		return
	}

	if statusFlag {
		printStatus()
		return
	}

	// Instantiate the crawler
	client := NewCrawler()

	// Ask for email and password
	signinValues := getCredentials()

	res := client.GetOrDie(loginUrl.String())
	res.Body.Close()

	res = client.PostFormOrDie(signinUrl.String(), signinValues)
	body, err := ioutil.ReadAll(res.Body)
	res.Body.Close()

	if strings.Contains(string(body), "Login error! Please check your email and password.") {
		fmt.Println("Login error! Please check your email and password.")
		return
	}

	res = client.GetOrDie(apiPageUrl.String())
	body, err = ioutil.ReadAll(res.Body)
	res.Body.Close()

	fmt.Print("Trying to extract Access Token and API URL...")
	parts := accessTokenRE.FindStringSubmatch(string(body))
	if len(parts) != 3 {
		fmt.Println("\nUnable to extract Access Token and API URL.")
		fmt.Println("This is the source code received:")
		fmt.Println(string(body))
		return
	}
	fmt.Println(" Done!")

	accessToken = parts[1]
	apiUrl, err = url.Parse(parts[2])
	if err != nil {
		fmt.Println("Unable to parse API Page URL")
		return
	}

	// So far, so good... Now extract the index json, if it hasn't already been done

	// If the JSON index file does not exist, we'll fetch it from the API and create it

	if _, err := os.Stat(indexPath); os.IsNotExist(err) {
		fmt.Println("\nTrying to extract index of all files...")

		var progress *pb.ProgressBar
		var allMedia []Media

		indexUrl := apiUrl.String() + "/media/index"

		offset := 0
		limit := 500
		total := -1

		formValues := url.Values{
			"taken_at_after":      {"0"},
			"include_hidden":      {"true"},
			"show_invisible":      {"true"},
			"warm_thumbs":         {"false"},
			"include_names":       {"false"},
			"include_comments":    {"false"},
			"include_signature":   {"false"},
			"include_access_info": {"false"},
			"include_likes":       {"false"},
			"offset":              {strconv.Itoa(offset)},
			"limit":               {strconv.Itoa(limit)},
			"access_token":        {accessToken},
		}

		for total == -1 || offset < total {
			formValues.Set("offset", strconv.Itoa(offset))

			res := client.PostFormOrDie(indexUrl, formValues)
			body, err = ioutil.ReadAll(res.Body)
			res.Body.Close()

			var apiResponse APIResponse
			err := json.Unmarshal(body, &apiResponse)
			if err != nil {
				fmt.Println("ERROR! Unable to read JSON response from API. Please try again later.")
				os.Exit(0)
			}

			allMedia = append(allMedia, apiResponse.Media...)
			total = apiResponse.Total

			if progress == nil {
				progress = pb.New(total)
				progress.ShowCounters = true
				progress.ShowTimeLeft = true
				progress.Start()
			}

			progress.Set(offset)

			offset += limit
		}

		progress.FinishPrint("Done fetching JSON index")

		mediaJson, _ := json.Marshal(allMedia)
		err = ioutil.WriteFile(indexPath, mediaJson, filePerm)

		if err != nil {
			fmt.Println("ERROR! Unable to write JSON index file to disk. Sorry...")
			fmt.Println("Please go to GitHub and open an issue.")
			os.Exit(0)
		}
	}

	if _, err := os.Stat(indexPath); os.IsNotExist(err) {
		fmt.Println("ERROR! Unable to find the JSON index file from disk. Sorry...")
		fmt.Println("Please go to GitHub and open an issue.")
		os.Exit(0)
	}

	src, err := ioutil.ReadFile(indexPath)
	if err != nil {
		fmt.Println("ERROR! Unable to read the JSON index file from disk. Sorry...")
		fmt.Println("Please go to GitHub and open an issue.")
		os.Exit(0)
	}

	var allMedia []Media

	json.Unmarshal(src, &allMedia)

	fmt.Println("\nTrying to extract pictures and videos...")

	ch := make(chan bool, 10)
	mediaLock := sync.Mutex{}

	progressCount := len(allMedia)
	for _, media := range allMedia {
		if media.Status == "done" {
			progressCount--
		} else if !retryFlag && media.Status == "failed" {
			progressCount--
		}
	}

	progress := pb.New(progressCount)
	progress.ShowCounters = true
	progress.ShowTimeLeft = true
	progress.Start()

	fails := 0
	success := 0
	for i, media := range allMedia {
		if allMedia[i].Status == "done" {
			success += 1
			continue
		}

		if !retryFlag && allMedia[i].Status == "failed" {
			fails += 1
			continue
		}

		ch <- true

		go func(index int, media *Media) {
			fetchMedia(&client, media)
			mediaLock.Lock()
			allMedia[index] = *media
			if media.Status == "done" {
				success += 1
			} else {
				fails += 1
			}
			progress.Increment()
			mediaLock.Unlock()
			<-ch
		}(i, &media)

		if i > 0 && i%10 == 0 {
			mediaJson, _ := json.Marshal(allMedia)
			err = ioutil.WriteFile(indexPath, mediaJson, filePerm)

			if err != nil {
				fmt.Println("ERROR! Unable to write update JSON index file to disk. Sorry...")
				fmt.Println("Please go to GitHub and open an issue.")
				os.Exit(0)
			}
		}
	}

	mediaJson, _ := json.Marshal(allMedia)
	err = ioutil.WriteFile(indexPath, mediaJson, filePerm)

	if err != nil {
		fmt.Println("ERROR! Unable to write update JSON index file to disk. Sorry...")
		fmt.Println("Please go to GitHub and open an issue.")
		os.Exit(0)
	}

	progress.Finish()

	fmt.Println("Done trying to fetch all pictures and videos.")
	fmt.Println("Result:")
	fmt.Println("\tSuccess:", success)
	fmt.Println("\tFailed: ", fails)
}

func fetchMedia(client *Crawler, media *Media) {
	media.Retries += 1
	media.Status = "started"

	extension := strings.ToLower(media.Format)
	extension = strings.Replace(extension, "jpeg", "jpg", 1)
	filename := media.Id + "." + extension
	filePath := mediaPath + "/" + filename
	url := originalUrl.String() + media.Id

	out, err := os.Create(filePath)
	if err != nil {
		media.Status = "failed"
		out.Close()
		os.Remove(filePath)
		return
	}

	res, err := client.Client.Get(url)
	if err != nil || res.StatusCode != 200 {
		media.Status = "failed"
		out.Close()
		if res != nil {
			res.Body.Close()
		}
		os.Remove(filePath)
		return
	}

	n, err := io.Copy(out, res.Body)
	if err != nil {
		media.Status = "failed"
		out.Close()
		res.Body.Close()
		os.Remove(filePath)
		return
	}

	if n < 1000 {
		media.Status = "failed"
		out.Close()
		res.Body.Close()
		os.Remove(filePath)

	} else {
		media.Status = "done"
		out.Close()
		res.Body.Close()
	}
}

func printHelp() {
	fmt.Println("Currently you can only choose whether or not to retry failed fetches")
	flag.PrintDefaults()
	fmt.Println("")
	fmt.Println("Usage:")
	fmt.Println(`./rescuelife -retry`)
	fmt.Println("")
}

func printStatus() {
	if _, err := os.Stat(indexPath); os.IsNotExist(err) {
		fmt.Println("ERROR! Unable to find the JSON index file from disk. Sorry...")
		return
	}

	src, err := ioutil.ReadFile(indexPath)
	if err != nil {
		fmt.Println("ERROR! Unable to read the JSON index file from disk. Sorry...")
		return
	}

	var allMedia []Media

	json.Unmarshal(src, &allMedia)

	var failed, started, done, waiting int
	total := len(allMedia)
	for _, media := range allMedia {
		switch media.Status {
		case "done":
			done++
		case "started":
			started++
		case "failed":
			failed++
		default:
			waiting++
		}
	}

	fmt.Println("\nStatus for fetching")
	fmt.Println("-----------------------------")
	fmt.Println("Succeeded:", done)
	fmt.Println("Failed:   ", failed)
	fmt.Println("Fetching: ", started)
	fmt.Println("Waiting:  ", waiting)
	fmt.Println("Total:    ", total)
	fmt.Println("")
}

func getCredentials() (signinValues url.Values) {
	fmt.Println("\n---------------------------------------------------------------------------------------------------------------------")
	fmt.Println("Your email and password is needed in order to get a cookie, extract Access Token and to fetch your images and videos.")
	fmt.Println("Nothing will be stored or copied to any other server.")
	fmt.Println("---------------------------------------------------------------------------------------------------------------------\n")

	reader := bufio.NewReader(os.Stdin)

	fmt.Print("Your email: ")
	email, _ := reader.ReadString('\n')
	email = strings.Trim(email, "\n")

	fmt.Print("Your password: ")
	bytePassword, _ := terminal.ReadPassword(0)
	password := strings.Trim(string(bytePassword), "\n")
	fmt.Println("\n")

	if email == "" || password == "" {
		fmt.Println("ERROR! Please provide email and password")
		os.Exit(0)
	}

	signinValues = url.Values{"email": {email}, "password": {password}}

	return
}
<commit_msg>Ensure that file exists, before marking them done<commit_after>// Rescue as much as possible from your Picturelife account
package main

import (
	"bufio"
	"encoding/json"
	"flag"
	"fmt"
	"io"
	"io/ioutil"
	"net/url"
	"os"
	"regexp"
	"strconv"
	"strings"
	"sync"

	"golang.org/x/crypto/ssh/terminal"

	"github.com/cheggaaa/pb"
)

type Media struct {
	Id             string `json:"id"`
	MediaType      string `json:"media_type"`
	Format         string `json:"format"`
	Processed      bool   `json:"processed"`
	CreatedAt      int    `json:"created_at"`
	UpdatedAt      int    `json:"updated_at"`
	TakenAt        int    `json:"taken_at"`
	Width          int    `json:"width"`
	Height         int    `json:"height"`
	Orientation    int    `json:"orientation"`
	Privacy        int    `json:"privacy"`
	IsBestPhoto    bool   `json:"is_best_photo"`
	TimeZoneOffset int    `json:"time_zone_offset"`
	Hidden         bool   `json:"hidden"`
	Visible        bool   `json:"visible"`
	Filesize       int    `json:"filesize"`
	BucketId       int    `json:"bucket_id"`
	Status         string `json:"status"`
	Retries        int    `json:"retries"`
}

type APIResponse struct {
	Status       int     `json:"status"`
	Media        []Media `json:"media"`
	Total        int     `json:"total"`
	Limit        int     `json:"limit"`
	Offset       int     `json:"offset"`
	UsingCache   bool    `json:"using_cache"`
	ResponseTime int     `json:"response_time"`
}

var (
	loginUrl    *url.URL
	signinUrl   *url.URL
	apiPageUrl  *url.URL
	apiUrl      *url.URL
	originalUrl *url.URL

	signinValues url.Values

	accessTokenRE *regexp.Regexp
	accessToken   string

	pathPerm os.FileMode = 0770
	filePerm os.FileMode = 0770

	mediaPath string = "picturelife"
	indexPath string = "pl_index.json"

	// Flags
	retryFlag  bool = false // Retry failed images and videos?
	helpFlag   bool = false // Retry failed images and videos?
	statusFlag bool = false // Retry failed images and videos?
)

func init() {
	var err error

	flag.BoolVar(&retryFlag, "retry", retryFlag, "Retry failed images and videos?")
	flag.BoolVar(&helpFlag, "help", helpFlag, "Print help text")
	flag.BoolVar(&statusFlag, "status", statusFlag, "Print out current status")

	loginUrl, err = url.Parse("http://picturelife.com/login")
	if err != nil {
		panic("Unable to parse login URL")
	}

	// Login posts to this
	signinUrl, err = url.Parse("http://picturelife.com/signin")
	if err != nil {
		panic("Unable to parse sign in URL")
	}

	apiPageUrl, err = url.Parse("http://picturelife.com/api")
	if err != nil {
		panic("Unable to parse API Page URL")
	}

	originalUrl, err = url.Parse("http://picturelife.com/d/original/")
	if err != nil {
		panic("Unable to parse API Page URL")
	}

	accessTokenRE = regexp.MustCompile("<script>\\s*pl\\.access_token\\s*=\\s*'([^']+)';\\s*pl\\.api_url\\s*=\\s*'([^']+)'\\s*</script>")

	err = os.MkdirAll(mediaPath, pathPerm)
	if err != nil {
		panic(err)
	}
}

func main() {
	flag.Parse()

	if helpFlag {
		printHelp()
		return
	}

	if statusFlag {
		printStatus()
		return
	}

	// Instantiate the crawler
	client := NewCrawler()

	// Ask for email and password
	signinValues := getCredentials()

	res := client.GetOrDie(loginUrl.String())
	res.Body.Close()

	res = client.PostFormOrDie(signinUrl.String(), signinValues)
	body, err := ioutil.ReadAll(res.Body)
	res.Body.Close()

	if strings.Contains(string(body), "Login error! Please check your email and password.") {
		fmt.Println("Login error! Please check your email and password.")
		return
	}

	res = client.GetOrDie(apiPageUrl.String())
	body, err = ioutil.ReadAll(res.Body)
	res.Body.Close()

	fmt.Print("Trying to extract Access Token and API URL...")
	parts := accessTokenRE.FindStringSubmatch(string(body))
	if len(parts) != 3 {
		fmt.Println("\nUnable to extract Access Token and API URL.")
		fmt.Println("This is the source code received:")
		fmt.Println(string(body))
		return
	}
	fmt.Println(" Done!")

	accessToken = parts[1]
	apiUrl, err = url.Parse(parts[2])
	if err != nil {
		fmt.Println("Unable to parse API Page URL")
		return
	}

	// So far, so good... Now extract the index json, if it hasn't already been done

	// If the JSON index file does not exist, we'll fetch it from the API and create it

	if _, err := os.Stat(indexPath); os.IsNotExist(err) {
		fmt.Println("\nTrying to extract index of all files...")

		var progress *pb.ProgressBar
		var allMedia []Media

		indexUrl := apiUrl.String() + "/media/index"

		offset := 0
		limit := 500
		total := -1

		formValues := url.Values{
			"taken_at_after":      {"0"},
			"include_hidden":      {"true"},
			"show_invisible":      {"true"},
			"warm_thumbs":         {"false"},
			"include_names":       {"false"},
			"include_comments":    {"false"},
			"include_signature":   {"false"},
			"include_access_info": {"false"},
			"include_likes":       {"false"},
			"offset":              {strconv.Itoa(offset)},
			"limit":               {strconv.Itoa(limit)},
			"access_token":        {accessToken},
		}

		for total == -1 || offset < total {
			formValues.Set("offset", strconv.Itoa(offset))

			res := client.PostFormOrDie(indexUrl, formValues)
			body, err = ioutil.ReadAll(res.Body)
			res.Body.Close()

			var apiResponse APIResponse
			err := json.Unmarshal(body, &apiResponse)
			if err != nil {
				fmt.Println("ERROR! Unable to read JSON response from API. Please try again later.")
				os.Exit(0)
			}

			allMedia = append(allMedia, apiResponse.Media...)
			total = apiResponse.Total

			if progress == nil {
				progress = pb.New(total)
				progress.ShowCounters = true
				progress.ShowTimeLeft = true
				progress.Start()
			}

			progress.Set(offset)

			offset += limit
		}

		progress.FinishPrint("Done fetching JSON index")

		mediaJson, _ := json.Marshal(allMedia)
		err = ioutil.WriteFile(indexPath, mediaJson, filePerm)

		if err != nil {
			fmt.Println("ERROR! Unable to write JSON index file to disk. Sorry...")
			fmt.Println("Please go to GitHub and open an issue.")
			os.Exit(0)
		}
	}

	if _, err := os.Stat(indexPath); os.IsNotExist(err) {
		fmt.Println("ERROR! Unable to find the JSON index file from disk. Sorry...")
		fmt.Println("Please go to GitHub and open an issue.")
		os.Exit(0)
	}

	src, err := ioutil.ReadFile(indexPath)
	if err != nil {
		fmt.Println("ERROR! Unable to read the JSON index file from disk. Sorry...")
		fmt.Println("Please go to GitHub and open an issue.")
		os.Exit(0)
	}

	var allMedia []Media

	json.Unmarshal(src, &allMedia)

	fmt.Println("\nTrying to extract pictures and videos...")

	ch := make(chan bool, 10)
	mediaLock := sync.Mutex{}

	progressCount := len(allMedia)
	for i, media := range allMedia {
		filePath := mediaPath + "/" + getMediaFilename(&media)

		if _, err := os.Stat(filePath); os.IsNotExist(err) {
			allMedia[i].Status = ""
		} else if media.Status == "done" {
			progressCount--
		} else if !retryFlag && media.Status == "failed" {
			progressCount--
		}
	}

	progress := pb.New(progressCount)
	progress.ShowCounters = true
	progress.ShowTimeLeft = true
	progress.Start()

	fails := 0
	success := 0
	for i, media := range allMedia {
		if allMedia[i].Status == "done" {
			success += 1
			continue
		}

		if !retryFlag && allMedia[i].Status == "failed" {
			fails += 1
			continue
		}

		ch <- true

		go func(index int, media *Media) {
			fetchMedia(&client, media)
			mediaLock.Lock()
			allMedia[index] = *media
			if media.Status == "done" {
				success += 1
			} else {
				fails += 1
			}
			progress.Increment()
			mediaLock.Unlock()
			<-ch
		}(i, &media)

		if i > 0 && i%10 == 0 {
			mediaJson, _ := json.Marshal(allMedia)
			err = ioutil.WriteFile(indexPath, mediaJson, filePerm)

			if err != nil {
				fmt.Println("ERROR! Unable to write update JSON index file to disk. Sorry...")
				fmt.Println("Please go to GitHub and open an issue.")
				os.Exit(0)
			}
		}
	}

	mediaJson, _ := json.Marshal(allMedia)
	err = ioutil.WriteFile(indexPath, mediaJson, filePerm)

	if err != nil {
		fmt.Println("ERROR! Unable to write update JSON index file to disk. Sorry...")
		fmt.Println("Please go to GitHub and open an issue.")
		os.Exit(0)
	}

	progress.Finish()

	fmt.Println("Done trying to fetch all pictures and videos.")
	fmt.Println("Result:")
	fmt.Println("\tSuccess:", success)
	fmt.Println("\tFailed: ", fails)
}

func fetchMedia(client *Crawler, media *Media) {
	media.Retries += 1
	media.Status = "started"

	filename := getMediaFilename(media)

	filePath := mediaPath + "/" + filename
	url := originalUrl.String() + media.Id

	out, err := os.Create(filePath)
	if err != nil {
		media.Status = "failed"
		out.Close()
		os.Remove(filePath)
		return
	}

	res, err := client.Client.Get(url)
	if err != nil || res.StatusCode != 200 {
		media.Status = "failed"
		out.Close()
		if res != nil {
			res.Body.Close()
		}
		os.Remove(filePath)
		return
	}

	n, err := io.Copy(out, res.Body)
	if err != nil {
		media.Status = "failed"
		out.Close()
		res.Body.Close()
		os.Remove(filePath)
		return
	}

	if n < 1000 {
		media.Status = "failed"
		out.Close()
		res.Body.Close()
		os.Remove(filePath)

	} else {
		media.Status = "done"
		out.Close()
		res.Body.Close()
	}
}

func getMediaFilename(media *Media) (filename string) {
	extension := strings.ToLower(media.Format)
	extension = strings.Replace(extension, "jpeg", "jpg", 1)
	filename = media.Id + "." + extension
	return
}

func printHelp() {
	fmt.Println("Currently you can only choose whether or not to retry failed fetches")
	flag.PrintDefaults()
	fmt.Println("")
	fmt.Println("Usage:")
	fmt.Println(`./rescuelife -retry`)
	fmt.Println("")
}

func printStatus() {
	if _, err := os.Stat(indexPath); os.IsNotExist(err) {
		fmt.Println("ERROR! Unable to find the JSON index file from disk. Sorry...")
		return
	}

	src, err := ioutil.ReadFile(indexPath)
	if err != nil {
		fmt.Println("ERROR! Unable to read the JSON index file from disk. Sorry...")
		return
	}

	var allMedia []Media

	json.Unmarshal(src, &allMedia)

	var failed, started, done, waiting int
	total := len(allMedia)
	for _, media := range allMedia {
		switch media.Status {
		case "done":
			done++
		case "started":
			started++
		case "failed":
			failed++
		default:
			waiting++
		}
	}

	fmt.Println("\nStatus for fetching")
	fmt.Println("-----------------------------")
	fmt.Println("Succeeded:", done)
	fmt.Println("Failed:   ", failed)
	fmt.Println("Fetching: ", started)
	fmt.Println("Waiting:  ", waiting)
	fmt.Println("Total:    ", total)
	fmt.Println("")
}

func getCredentials() (signinValues url.Values) {
	fmt.Println("\n---------------------------------------------------------------------------------------------------------------------")
	fmt.Println("Your email and password is needed in order to get a cookie, extract Access Token and to fetch your images and videos.")
	fmt.Println("Nothing will be stored or copied to any other server.")
	fmt.Println("---------------------------------------------------------------------------------------------------------------------\n")

	reader := bufio.NewReader(os.Stdin)

	fmt.Print("Your email: ")
	email, _ := reader.ReadString('\n')
	email = strings.Trim(email, "\n")

	fmt.Print("Your password: ")
	bytePassword, _ := terminal.ReadPassword(0)
	password := strings.Trim(string(bytePassword), "\n")
	fmt.Println("\n")

	if email == "" || password == "" {
		fmt.Println("ERROR! Please provide email and password")
		os.Exit(0)
	}

	signinValues = url.Values{"email": {email}, "password": {password}}

	return
}
<|endoftext|>


<commit_before>package main

import (
	"fmt"
	"github.com/gin-gonic/gin"
	"github.com/jessevdk/go-flags"
	_ "github.com/lib/pq"
	"os"
)

var options struct {
	Url    string `long:"url" description:"Database connection string"`
	Host   string `long:"host" description:"Server hostname or IP" default:"localhost"`
	Port   int    `long:"port" description:"Server port" default:"5432"`
	User   string `long:"user" description:"Database user" default:"postgres"`
	DbName string `long:"db" description:"Database name" default:"postgres"`
	Ssl    string `long:"ssl" description:"SSL option" default:"disable"`
	Static string `short:"s" description:"Path to static assets" default:"./static"`
}

var dbClient *Client

func exitWithMessage(message string) {
	fmt.Println("Error:", message)
	os.Exit(1)
}

func getConnectionString() string {
	if options.Url != "" {
		return options.Url
	}

	return fmt.Sprintf(
		"host=%s port=%d user=%s dbname=%s sslmode=disable",
		options.Host, options.Port,
		options.User, options.DbName,
	)
}

func initClient() {
	client, err := NewClient()
	if err != nil {
		exitWithMessage(err.Error())
	}

	fmt.Println("Connecting to server...")
	err = client.Test()
	if err != nil {
		exitWithMessage(err.Error())
	}

	fmt.Println("Checking tables...")
	tables, err := client.Tables()
	if err != nil {
		exitWithMessage(err.Error())
	}

	if len(tables) == 0 {
		exitWithMessage("Database does not have any tables")
	}

	dbClient = client
}

func initOptions() {
	_, err := flags.ParseArgs(&options, os.Args)

	if err != nil {
		os.Exit(1)
	}
}

func main() {
	initOptions()
	initClient()

	defer dbClient.db.Close()

	router := gin.Default()

	router.GET("/", API_Home)
	router.GET("/info", API_Info)
	router.GET("/tables", API_GetTables)
	router.GET("/tables/:table", API_GetTable)
	router.GET("/tables/:table/indexes", API_TableIndexes)
	router.GET("/query", API_RunQuery)
	router.POST("/query", API_RunQuery)
	router.GET("/explain", API_ExplainQuery)
	router.POST("/explain", API_ExplainQuery)
	router.GET("/history", API_History)
	router.GET("/static/:type/:name", API_ServeAsset)

	fmt.Println("Starting server...")
	fmt.Println("Once started you can view application at http://localhost:8080")
	router.Run(":8080")
}
<commit_msg>Remove unused options var<commit_after>package main

import (
	"fmt"
	"github.com/gin-gonic/gin"
	"github.com/jessevdk/go-flags"
	_ "github.com/lib/pq"
	"os"
)

var options struct {
	Url    string `long:"url" description:"Database connection string"`
	Host   string `long:"host" description:"Server hostname or IP" default:"localhost"`
	Port   int    `long:"port" description:"Server port" default:"5432"`
	User   string `long:"user" description:"Database user" default:"postgres"`
	DbName string `long:"db" description:"Database name" default:"postgres"`
	Ssl    string `long:"ssl" description:"SSL option" default:"disable"`
}

var dbClient *Client

func exitWithMessage(message string) {
	fmt.Println("Error:", message)
	os.Exit(1)
}

func getConnectionString() string {
	if options.Url != "" {
		return options.Url
	}

	return fmt.Sprintf(
		"host=%s port=%d user=%s dbname=%s sslmode=disable",
		options.Host, options.Port,
		options.User, options.DbName,
	)
}

func initClient() {
	client, err := NewClient()
	if err != nil {
		exitWithMessage(err.Error())
	}

	fmt.Println("Connecting to server...")
	err = client.Test()
	if err != nil {
		exitWithMessage(err.Error())
	}

	fmt.Println("Checking tables...")
	tables, err := client.Tables()
	if err != nil {
		exitWithMessage(err.Error())
	}

	if len(tables) == 0 {
		exitWithMessage("Database does not have any tables")
	}

	dbClient = client
}

func initOptions() {
	_, err := flags.ParseArgs(&options, os.Args)

	if err != nil {
		os.Exit(1)
	}
}

func main() {
	initOptions()
	initClient()

	defer dbClient.db.Close()

	router := gin.Default()

	router.GET("/", API_Home)
	router.GET("/info", API_Info)
	router.GET("/tables", API_GetTables)
	router.GET("/tables/:table", API_GetTable)
	router.GET("/tables/:table/indexes", API_TableIndexes)
	router.GET("/query", API_RunQuery)
	router.POST("/query", API_RunQuery)
	router.GET("/explain", API_ExplainQuery)
	router.POST("/explain", API_ExplainQuery)
	router.GET("/history", API_History)
	router.GET("/static/:type/:name", API_ServeAsset)

	fmt.Println("Starting server...")
	fmt.Println("Once started you can view application at http://localhost:8080")
	router.Run(":8080")
}
<|endoftext|>


<commit_before>package main

import (
	"fmt"
	neural "github.com/poseidon4o/go-neural/src/neural"
	flappy "github.com/poseidon4o/go-neural/src/problems/flappy"
	mario "github.com/poseidon4o/go-neural/src/problems/mario"
	util "github.com/poseidon4o/go-neural/src/util"
	sdl "github.com/veandco/go-sdl2/sdl"
	"math"
	"runtime"
	"time"
)

type DrawableProblem interface {
	SetDrawRectCb(cb func(pos, size *util.Vector, color uint32))
	LogicTick(dt float64)
	DrawTick()
	StatsReportTick()
	Complete() float64
	Done() bool
	Jump()
	Move(int)
	SaveNetsToFile()
	LoadNetsFromFile()
}

func main() {
	runtime.GOMAXPROCS(runtime.NumCPU())
	fmt.Println("Controls:")
	fmt.Println("end:\tfurthest action in the level")
	fmt.Println("home:\tmove back to level begining")
	fmt.Println("left:\tmove screen to the left")
	fmt.Println("right:\tmove screen to the right")
	fmt.Println("1:\tswitch to flappy")
	fmt.Println("2:\tswitch to mario")
	fmt.Println("enter:\tcycle trough mario/flappy")
	fmt.Println("esc:\teixt")
	fmt.Println("")

	doDraw := true
	doDev := false
	doFastForward := false

	W := 1300
	H := 700
	LVL_W := W * 50

	var FPS float64 = 60.0
	FRAME_TIME_MS := 1000 / FPS
	FRAME_TIME := time.Millisecond * time.Duration(FRAME_TIME_MS)

	sdl.Init(sdl.INIT_EVERYTHING)

	window, err := sdl.CreateWindow("test", sdl.WINDOWPOS_UNDEFINED, sdl.WINDOWPOS_UNDEFINED,
		int(W), int(H), sdl.WINDOW_SHOWN)
	if err != nil {
		panic(err)
	}
	defer window.Destroy()

	surface, err := window.GetSurface()
	if err != nil {
		panic(err)
	}

	clearRect := sdl.Rect{0, 0, int32(W), int32(H)}
	surface.FillRect(&clearRect, 0xffffffff)

	figCount := 100
	if doDev {
		figCount = 1
	}

	offset := 0
	visible := func(pos, size *util.Vector) bool {

		// r1 := sdl.Rect{int32(pos.X), int32(pos.Y), int32(pos.X + size.X), int32(pos.Y + size.Y)}
		// r2 := sdl.Rect{int32(offset), 0, int32(offset + W), int32(H)}
		// return !(r2.X > r1.W || r2.W < r1.X || r2.Y > r1.H || r2.H < r1.Y)

		// so beautiful
		return !(float64(offset) > pos.X+size.X ||
			float64(offset+W) < pos.X ||
			0 > pos.Y+size.Y ||
			float64(H) < pos.Y)
	}

	toScreen := func(pos, size *util.Vector) *sdl.Rect {
		return &sdl.Rect{
			X: int32(pos.X - float64(offset)),
			Y: int32(pos.Y),
			W: int32(size.X),
			H: int32(size.Y),
		}
	}

	drawCb := func(pos, size *util.Vector, color uint32) {
		if visible(pos, size) {
			surface.FillRect(toScreen(pos, size), color)
		}
	}

	fl := flappy.NewFlappy(figCount, util.NewVector(float64(LVL_W), float64(H)))
	mr := mario.NewMario(figCount, util.NewVector(float64(LVL_W), float64(H)))

	mr.LoadNetsFromFile()
	fl.LoadNetsFromFile()

	fl.SetDrawRectCb(drawCb)
	mr.SetDrawRectCb(drawCb)

	var game DrawableProblem = fl

	step := 65

	frame := 0
	var averageFrameTime float64 = FRAME_TIME_MS * 1000000 // in nanosec
	start := time.Now()
	lastDrawTime := time.Now()
	lastReportTime := time.Now()
	for {
		start = time.Now()

		if doDraw {
			if doFastForward {
				if !lastDrawTime.Add(FRAME_TIME).After(start) {
					lastDrawTime = start
					window.UpdateSurface()
					surface.FillRect(&clearRect, 0xffffffff)
					game.DrawTick()
				}
			} else {
				lastDrawTime = start
				window.UpdateSurface()
				surface.FillRect(&clearRect, 0xffffffff)
				game.DrawTick()
			}

		} else if frame%10 == 0 {
			// update only 10% of the frames
			window.UpdateSurface()
		}

		game.LogicTick(1 / FPS)

		stop := false
		for event := sdl.PollEvent(); event != nil; event = sdl.PollEvent() {
			switch t := event.(type) {
			case *sdl.QuitEvent:
				stop = true
			case *sdl.KeyDownEvent:
				switch t.Keysym.Sym {
				case sdl.K_LEFT:
					if doDev {
						game.Move(-1)
					} else {
						offset = int(math.Max(0, float64(offset-step)))
					}
				case sdl.K_RIGHT:
					if doDev {
						game.Move(1)
					} else {
						offset = int(math.Min(float64(LVL_W-W), float64(offset+step)))
					}
				case sdl.K_SPACE:
					if doDev {
						game.Jump()
					} else {
						doDraw = !doDraw
						surface.FillRect(&clearRect, 0xffaaaaaa)
						window.UpdateSurface()
					}
				case sdl.K_1:
					game = fl
				case sdl.K_2:
					game = mr
				case sdl.K_RETURN:
					if game == fl {
						game = mr
					} else {
						game = fl
					}
				case sdl.K_ESCAPE:
					stop = true
				case sdl.K_END:
					offset = int(math.Max(math.Min(float64(LVL_W-W), game.Complete()*float64(LVL_W)-float64(W)/2), 0))
				case sdl.K_HOME:
					offset = 0
				case sdl.K_f:
					doFastForward = !doFastForward
				case sdl.K_s:
					game.SaveNetsToFile()
				}
			}
		}

		if stop {
			break
		}

		frame++

		elapsed := time.Since(start)
		frameMs := float64(elapsed) / 1000000

		averageFrameTime = averageFrameTime*0.9 + float64(elapsed.Nanoseconds())*0.1

		if game.Done() {
			fmt.Println("Done")
			break
		}

		if !lastReportTime.Add(time.Second).After(start) {
			game.StatsReportTick()
			lastReportTime = start
			fmt.Printf("CHRand %d\tGRand %d\tG/C %f\n", neural.ChanRand, neural.GlobRand, float64(neural.GlobRand)/float64(neural.ChanRand))
			neural.ChanRand = 0
			neural.GlobRand = 0
			fmt.Printf("ftime last: %f\tftime average %f\tcompletion %f%%\n", frameMs, averageFrameTime/1000000, game.Complete()*100)
		}

		// sleep only if drawing and there is time to sleep more than 3ms
		if !doFastForward && doDraw && frameMs < FRAME_TIME_MS && FRAME_TIME_MS-frameMs > 3.0 {
			time.Sleep(time.Millisecond * time.Duration(FRAME_TIME_MS-frameMs))
		}
	}

	sdl.Quit()
}
<commit_msg>Change figures to default to 1000 and fix stats print<commit_after>package main

import (
	"fmt"
	neural "github.com/poseidon4o/go-neural/src/neural"
	flappy "github.com/poseidon4o/go-neural/src/problems/flappy"
	mario "github.com/poseidon4o/go-neural/src/problems/mario"
	util "github.com/poseidon4o/go-neural/src/util"
	sdl "github.com/veandco/go-sdl2/sdl"
	"math"
	"runtime"
	"time"
)

type DrawableProblem interface {
	SetDrawRectCb(cb func(pos, size *util.Vector, color uint32))
	LogicTick(dt float64)
	DrawTick()
	StatsReportTick()
	Complete() float64
	Done() bool
	Jump()
	Move(int)
	SaveNetsToFile()
	LoadNetsFromFile()
}

func main() {
	runtime.GOMAXPROCS(runtime.NumCPU())
	fmt.Println("Controls:")
	fmt.Println("end:\tfurthest action in the level")
	fmt.Println("home:\tmove back to level begining")
	fmt.Println("left:\tmove screen to the left")
	fmt.Println("right:\tmove screen to the right")
	fmt.Println("1:\tswitch to flappy")
	fmt.Println("2:\tswitch to mario")
	fmt.Println("enter:\tcycle trough mario/flappy")
	fmt.Println("esc:\teixt")
	fmt.Println("")

	doDraw := true
	doDev := false
	doFastForward := false

	W := 1300
	H := 700
	LVL_W := W * 50

	var FPS float64 = 60.0
	FRAME_TIME_MS := 1000 / FPS
	FRAME_TIME := time.Millisecond * time.Duration(FRAME_TIME_MS)

	sdl.Init(sdl.INIT_EVERYTHING)

	window, err := sdl.CreateWindow("test", sdl.WINDOWPOS_UNDEFINED, sdl.WINDOWPOS_UNDEFINED,
		int(W), int(H), sdl.WINDOW_SHOWN)
	if err != nil {
		panic(err)
	}
	defer window.Destroy()

	surface, err := window.GetSurface()
	if err != nil {
		panic(err)
	}

	clearRect := sdl.Rect{0, 0, int32(W), int32(H)}
	surface.FillRect(&clearRect, 0xffffffff)

	figCount := 1000
	if doDev {
		figCount = 1
	}

	offset := 0
	visible := func(pos, size *util.Vector) bool {

		// r1 := sdl.Rect{int32(pos.X), int32(pos.Y), int32(pos.X + size.X), int32(pos.Y + size.Y)}
		// r2 := sdl.Rect{int32(offset), 0, int32(offset + W), int32(H)}
		// return !(r2.X > r1.W || r2.W < r1.X || r2.Y > r1.H || r2.H < r1.Y)

		// so beautiful
		return !(float64(offset) > pos.X+size.X ||
			float64(offset+W) < pos.X ||
			0 > pos.Y+size.Y ||
			float64(H) < pos.Y)
	}

	toScreen := func(pos, size *util.Vector) *sdl.Rect {
		return &sdl.Rect{
			X: int32(pos.X - float64(offset)),
			Y: int32(pos.Y),
			W: int32(size.X),
			H: int32(size.Y),
		}
	}

	drawCb := func(pos, size *util.Vector, color uint32) {
		if visible(pos, size) {
			surface.FillRect(toScreen(pos, size), color)
		}
	}

	fl := flappy.NewFlappy(figCount, util.NewVector(float64(LVL_W), float64(H)))
	mr := mario.NewMario(figCount, util.NewVector(float64(LVL_W), float64(H)))

	mr.LoadNetsFromFile()
	fl.LoadNetsFromFile()

	fl.SetDrawRectCb(drawCb)
	mr.SetDrawRectCb(drawCb)

	var game DrawableProblem = fl

	step := 65

	frame := 0
	var averageFrameTime float64 = FRAME_TIME_MS * 1000000 // in nanosec
	start := time.Now()
	lastDrawTime := time.Now()
	lastReportTime := time.Now()
	for {
		start = time.Now()

		if doDraw {
			if doFastForward {
				if !lastDrawTime.Add(FRAME_TIME).After(start) {
					lastDrawTime = start
					window.UpdateSurface()
					surface.FillRect(&clearRect, 0xffffffff)
					game.DrawTick()
				}
			} else {
				lastDrawTime = start
				window.UpdateSurface()
				surface.FillRect(&clearRect, 0xffffffff)
				game.DrawTick()
			}

		} else if frame%10 == 0 {
			// update only 10% of the frames
			window.UpdateSurface()
		}

		game.LogicTick(1 / FPS)

		stop := false
		for event := sdl.PollEvent(); event != nil; event = sdl.PollEvent() {
			switch t := event.(type) {
			case *sdl.QuitEvent:
				stop = true
			case *sdl.KeyDownEvent:
				switch t.Keysym.Sym {
				case sdl.K_LEFT:
					if doDev {
						game.Move(-1)
					} else {
						offset = int(math.Max(0, float64(offset-step)))
					}
				case sdl.K_RIGHT:
					if doDev {
						game.Move(1)
					} else {
						offset = int(math.Min(float64(LVL_W-W), float64(offset+step)))
					}
				case sdl.K_SPACE:
					if doDev {
						game.Jump()
					} else {
						doDraw = !doDraw
						surface.FillRect(&clearRect, 0xffaaaaaa)
						window.UpdateSurface()
					}
				case sdl.K_1:
					game = fl
				case sdl.K_2:
					game = mr
				case sdl.K_RETURN:
					if game == fl {
						game = mr
					} else {
						game = fl
					}
				case sdl.K_ESCAPE:
					stop = true
				case sdl.K_END:
					offset = int(math.Max(math.Min(float64(LVL_W-W), game.Complete()*float64(LVL_W)-float64(W)/2), 0))
				case sdl.K_HOME:
					offset = 0
				case sdl.K_f:
					doFastForward = !doFastForward
				case sdl.K_s:
					game.SaveNetsToFile()
				}
			}
		}

		if stop {
			break
		}

		frame++

		elapsed := time.Since(start)
		frameMs := float64(elapsed) / 1000000

		averageFrameTime = averageFrameTime*0.9 + float64(elapsed.Nanoseconds())*0.1

		if game.Done() {
			fmt.Println("Done")
			break
		}

		if !lastReportTime.Add(time.Second).After(start) {
			fmt.Println("")
			game.StatsReportTick()
			lastReportTime = start
			neural.ChanRand = 0
			neural.GlobRand = 0
			fmt.Printf("Last FrameTime: %f\tAverage FrameTime %f\tCompletion %f%%\n", frameMs, averageFrameTime/1000000, game.Complete()*100)
			fmt.Printf("FastForward %t\n", doFastForward)
		}

		// sleep only if drawing and there is time to sleep more than 3ms
		if !doFastForward && doDraw && frameMs < FRAME_TIME_MS && FRAME_TIME_MS-frameMs > 3.0 {
			time.Sleep(time.Millisecond * time.Duration(FRAME_TIME_MS-frameMs))
		}
	}

	sdl.Quit()
}
<|endoftext|>


<commit_before>package main

import (
	"flag"
	"fmt"
	"io"
	"log"
	"net"
	"os"
	"os/signal"
	"syscall"

	"github.com/nobonobo/p2pfw/peerconn"
	"github.com/nobonobo/p2pfw/signaling/client"
	"github.com/nobonobo/webrtc"
)

const usage = `Usage: ssh-p2p SUBCMD [options]
sub-commands:
	newkey
		new generate key of connection
	server -key="..." [-dial="127.0.0.1:22"]
		ssh server side peer mode
	client -key="..." [-listen="127.0.0.1:2222"]
		ssh client side peer mode
`

func main() {
	cmd := ""
	if len(os.Args) > 1 {
		cmd = os.Args[1]
	}
	var flags *flag.FlagSet
	flags = flag.NewFlagSet("", flag.ExitOnError)
	flags.Usage = func() {
		fmt.Fprintf(os.Stderr, usage)
		flags.PrintDefaults()
		os.Exit(1)
	}

	switch cmd {
	default:
		flags.Usage()
	case "newkey":
		key, err := client.UUID()
		if err != nil {
			log.Fatalln(err)
		}
		fmt.Println(key)
		os.Exit(0)
	case "server":
		var addr, key string
		flags.StringVar(&addr, "dial", "127.0.0.1:22", "dial addr = host:port")
		flags.StringVar(&key, "key", "sample", "connection key")
		if err := flags.Parse(os.Args[2:]); err != nil {
			log.Fatalln(err)
		}
		sig := make(chan os.Signal, 1)
		signal.Notify(sig, syscall.SIGINT)
		defer serve(key, addr)()
		<-sig
	case "client":
		var addr, key string
		flags.StringVar(&addr, "listen", "127.0.0.1:2222", "listen addr = host:port")
		flags.StringVar(&key, "key", "sample", "connection key")
		if err := flags.Parse(os.Args[2:]); err != nil {
			log.Fatalln(err)
		}
		l, err := net.Listen("tcp", addr)
		if err != nil {
			log.Fatalln(err)
		}
		log.Println("listen:", addr)
		for {
			sock, err := l.Accept()
			if err != nil {
				log.Println(err)
				continue
			}
			go connect(key, sock)
		}
	}
}

func serve(key, addr string) func() error {
	dial := new(client.Config)
	dial.RoomID = key
	dial.UserID = "***server***"
	dial.URL = "wss://signaling.arukascloud.io/ws"

	stun, err := peerconn.GetDefaultStunHosts()
	if err != nil {
		log.Fatalln(err)
	}
	config := webrtc.NewConfiguration()
	config.AddIceServer(stun)
	node, err := peerconn.NewNode(dial, config)
	if err != nil {
		log.Fatalln(err)
	}
	node.OnPeerConnection = func(dest string, conn *peerconn.Conn) error {
		dc, err := conn.CreateDataChannel("default")
		if err != nil {
			return err
		}
		dc.OnOpen(func() {
			go func() {
				c := peerconn.NewDCConn(dc)
				defer c.Close()
				ssh, err := net.Dial("tcp", addr)
				if err != nil {
					log.Println("dial failed:", err)
					return
				}
				defer ssh.Close()
				log.Println("connected:", c)
				go io.Copy(ssh, c)
				io.Copy(c, ssh)
			}()
		})
		return nil
	}
	if err := node.Start(true); err != nil {
		log.Fatalln(err)
	}
	return node.Close
}

func connect(key string, sock net.Conn) {
	id, err := client.UUID()
	if err != nil {
		log.Fatalln(err)
	}

	dial := new(client.Config)
	dial.RoomID = key
	dial.UserID = id
	dial.URL = "wss://signaling.arukascloud.io/ws"

	stun, err := peerconn.GetDefaultStunHosts()
	if err != nil {
		log.Fatalln(err)
	}
	config := webrtc.NewConfiguration()
	config.AddIceServer(stun)
	node, err := peerconn.NewNode(dial, config)
	if err != nil {
		log.Fatalln(err)
	}
	if err := node.Start(false); err != nil {
		log.Fatalln(err)
	}
	members, err := node.Members()
	if err != nil {
		log.Fatalln(err)
	}
	conn, err := node.Connect(members.Owner)
	if err != nil {
		log.Fatalln(err)
	}
	conn.OnDataChannel(func(dc *webrtc.DataChannel) {
		go func() {
			log.Println("data channel open:", dc)
			defer log.Println("data channel close:", dc)
			c := peerconn.NewDCConn(dc)
			go func() {
				if _, err := io.Copy(c, sock); err != nil {
					log.Println(err)
				}
				if err := c.Close(); err != nil {
					log.Println(err)
				}
			}()
			if _, err := io.Copy(sock, c); err != nil {
				log.Println(err)
			}
			if err := sock.Close(); err != nil {
				log.Println(err)
			}
			if err := node.Close(); err != nil {
				log.Println(err)
			}
		}()
	})
}
<commit_msg>bug fix<commit_after>package main

import (
	"flag"
	"fmt"
	"io"
	"log"
	"net"
	"os"
	"os/signal"
	"syscall"

	"github.com/nobonobo/p2pfw/peerconn"
	"github.com/nobonobo/p2pfw/signaling/client"
	"github.com/nobonobo/webrtc"
)

const usage = `Usage: ssh-p2p SUBCMD [options]
sub-commands:
	newkey
		new generate key of connection
	server -key="..." [-dial="127.0.0.1:22"]
		ssh server side peer mode
	client -key="..." [-listen="127.0.0.1:2222"]
		ssh client side peer mode
`

func main() {
	cmd := ""
	if len(os.Args) > 1 {
		cmd = os.Args[1]
	}
	var flags *flag.FlagSet
	flags = flag.NewFlagSet("", flag.ExitOnError)
	flags.Usage = func() {
		fmt.Fprintf(os.Stderr, usage)
		flags.PrintDefaults()
		os.Exit(1)
	}

	switch cmd {
	default:
		flags.Usage()
	case "newkey":
		key, err := client.UUID()
		if err != nil {
			log.Fatalln(err)
		}
		fmt.Println(key)
		os.Exit(0)
	case "server":
		var addr, key string
		flags.StringVar(&addr, "dial", "127.0.0.1:22", "dial addr = host:port")
		flags.StringVar(&key, "key", "sample", "connection key")
		if err := flags.Parse(os.Args[2:]); err != nil {
			log.Fatalln(err)
		}
		sig := make(chan os.Signal, 1)
		signal.Notify(sig, syscall.SIGINT)
		defer serve(key, addr)()
		<-sig
	case "client":
		var addr, key string
		flags.StringVar(&addr, "listen", "127.0.0.1:2222", "listen addr = host:port")
		flags.StringVar(&key, "key", "sample", "connection key")
		if err := flags.Parse(os.Args[2:]); err != nil {
			log.Fatalln(err)
		}
		l, err := net.Listen("tcp", addr)
		if err != nil {
			log.Fatalln(err)
		}
		log.Println("listen:", addr)
		for {
			sock, err := l.Accept()
			if err != nil {
				log.Println(err)
				continue
			}
			go connect(key, sock)
		}
	}
}

func serve(key, addr string) func() error {
	dial := new(client.Config)
	dial.RoomID = key
	dial.UserID = "***server***"
	dial.URL = "wss://signaling.arukascloud.io/ws"

	stun, err := peerconn.GetDefaultStunHosts()
	if err != nil {
		log.Fatalln(err)
	}
	config := webrtc.NewConfiguration()
	config.AddIceServer(stun)
	node, err := peerconn.NewNode(dial, config)
	if err != nil {
		log.Fatalln(err)
	}
	node.OnLeave = func(member string) {
		log.Println("leave:", member)
		node.Clients.Del(member)
	}
	node.OnPeerConnection = func(dest string, conn *peerconn.Conn) error {
		dc, err := conn.CreateDataChannel("default")
		if err != nil {
			return err
		}
		dc.OnOpen(func() {
			go func() {
				c := peerconn.NewDCConn(dc)
				defer c.Close()
				ssh, err := net.Dial("tcp", addr)
				if err != nil {
					log.Println("dial failed:", err)
					return
				}
				defer ssh.Close()
				log.Println("connected:", dest)
				go io.Copy(ssh, c)
				io.Copy(c, ssh)
			}()
		})
		dc.OnClose(func() {
			log.Println("disconnected:", dest)
			dc.Close()
		})
		return nil
	}
	if err := node.Start(true); err != nil {
		log.Fatalln(err)
	}
	return node.Close
}

func connect(key string, sock net.Conn) {
	id, err := client.UUID()
	if err != nil {
		log.Fatalln(err)
	}

	dial := new(client.Config)
	dial.RoomID = key
	dial.UserID = id
	dial.URL = "wss://signaling.arukascloud.io/ws"

	stun, err := peerconn.GetDefaultStunHosts()
	if err != nil {
		log.Fatalln(err)
	}
	config := webrtc.NewConfiguration()
	config.AddIceServer(stun)
	node, err := peerconn.NewNode(dial, config)
	if err != nil {
		log.Fatalln(err)
	}
	if err := node.Start(false); err != nil {
		log.Fatalln(err)
	}
	members, err := node.Members()
	if err != nil {
		log.Fatalln(err)
	}
	conn, err := node.Connect(members.Owner)
	if err != nil {
		log.Fatalln(err)
	}
	conn.OnDataChannel(func(dc *webrtc.DataChannel) {
		go func() {
			defer func() {
				if err := node.Close(); err != nil {
					log.Println(err)
				}
			}()
			log.Println("data channel open:", dc)
			defer log.Println("data channel close:", dc)
			c := peerconn.NewDCConn(dc)
			go func() {
				defer func() {
					if err := c.Close(); err != nil {
						log.Println(err)
					}
				}()
				if _, err := io.Copy(c, sock); err != nil {
					log.Println(err)
				}
			}()
			defer func() {
				if err := sock.Close(); err != nil {
					log.Println(err)
				}
			}()
			if _, err := io.Copy(sock, c); err != nil {
				log.Println(err)
			}
		}()
	})
}
<|endoftext|>


<commit_before>package main

import (
	"github.com/MSOpenTech/azure-sdk-for-go/storage"
	"io/ioutil"
	"os"
	"path"

	"github.com/paulmey/inspect-azure-vhd/ext4"

	"encoding/binary"
	"flag"
	"fmt"
	"io"
	"net/http"
)

const (
	apiVersion = "2014-02-14"
)

var (
	help      bool
	ouputPath string
)

func init() {
	flag.BoolVar(&help, "help", false, "Prints this help.")
	flag.StringVar(&ouputPath, "outputPath", "out", "Specifies the path where logs and files are placed.")
}

func main() {
	flag.Parse()
	if flag.NArg() != 1 || help {
		fmt.Printf("Usage: ./inspect-remote-vhd <vhd-read-uri>\n")
		flag.PrintDefaults()
		return
	}

	uri := flag.Arg(0)

	s := SasPageBlobAccessor(uri)

	fmt.Printf("Reading partition table...\n")
	// location of MBR partition table http://en.wikipedia.org/wiki/Master_boot_record#Sector_layout
	s.Seek(446, 0)
	var p partitionEntry
	err := binary.Read(s, binary.LittleEndian, &p)
	if err != nil {
		panic(err)
	}

	fmt.Printf("Inspecting ext4 filesystem on first partition...\n")
	// assume that partition 0 is linux with ext4
	if p.Type != 0x83 {
		err = fmt.Errorf("Not a linux partition!")
		return
	}

	r, err := ext4.NewReader(s, p.LBAfirst, p.Sectors)
	if err != nil {
		panic(err)
	}

	globs := []string{
		"/etc/ssh*/*",
		"/etc/ssh*",
		"/etc/fstab",
		"/etc/mtab",
		"/etc/waagent.conf",
		"/var/log/messages",
		"/var/log/boot.log",
		"/var/log/dmesg",
		"/var/log/syslog",
		"/var/log/waagent/*",
		"/var/log/waagent*",
		"/var/log/walinuxagent/*",
		"/var/log/walinuxagent*",
		"/var/log/azure/*",
		"/var/log/azure/*/*",
		"/var/log/*",
	}

	fs, err := r.Root()
	if err != nil {
		panic(err)
	}

	fmt.Printf("Downloading interesting files...\n")
	for _, glob := range globs {
		files, err := fs.Match(glob)
		if err != nil {
			panic(err)
		}
		for _, f := range files {
			orig := f
			for f.FileType == ext4.FileTypeSymlink {
				f, err = f.ResolveSymlink()
				if err != nil {
					fmt.Printf("WARN: failed to resolve symlink %s: %v\n", orig.Fullname(), err)
					continue
				}
			}
			if f.FileType != ext4.FileTypeFile {
				continue
			}
			inode, err := r.GetInode(f.Inode)
			if err != nil {
				fmt.Printf("WARN: could not read inode %d (%s -> %s): %v\n", f.Inode, orig.Fullname(), f.Fullname(), err)
				continue
			}

			fmt.Printf("   %s (%s) \n", orig.Fullname(), orig.FileType)
			fmt.Printf("     \\-> downloading %d bytes\n", inode.Size())

			data, err := r.GetInodeContent(inode)
			if err != nil {
				fmt.Printf("WARN: could not read data for %s: %s", orig.Fullname(), err)
				continue
			}

			outFile := ouputPath + "/" + orig.Fullname()
			if err := os.MkdirAll(path.Dir(outFile), 0777); err != nil {
				fmt.Printf("ERR: could not create path %s: %s", path.Dir(outFile), err)
				return
			}
			err = ioutil.WriteFile(outFile, data, 0666)
			if err != nil {
				fmt.Printf("ERR: could not write file %s: %s", path.Dir(outFile), err)
				return
			}
		}
	}
}

type partitionEntry struct {
	Active   byte
	CHSFirst [3]byte
	Type     byte
	CHSLast  [3]byte
	LBAfirst uint32
	Sectors  uint32
}

func SasPageBlobAccessor(url string) io.ReadSeeker {
	return &readSeekablePageBlob{
		url: url,
	}
}

type readSeekablePageBlob struct {
	url    string
	offset int64
}

func (b *readSeekablePageBlob) Read(buffer []byte) (n int, err error) {
	if len(buffer) == 0 {
		return
	}

	req, err := http.NewRequest("GET", b.url, nil)
	if err != nil {
		return
	}
	req.Header.Set("x-ms-version", apiVersion)
	req.Header.Set("x-ms-range", fmt.Sprintf("bytes=%d-%d", b.offset, b.offset+int64(len(buffer))))

	res, err := http.DefaultClient.Do(req)
	if err != nil {
		return
	}
	if !(res.StatusCode == http.StatusOK ||
		res.StatusCode == http.StatusPartialContent) {
		return 0, fmt.Errorf("Non success status code: %s", res.Status)
	}

	defer res.Body.Close()

	// paulmey: for some reason, ioutil.ReadAll reads on infinitely on res.Body ?
	for n < len(buffer) && err == nil {
		nn, nerr := res.Body.Read(buffer[n:])
		err = nerr
		n += nn
	}
	//	fmt.Printf("### read %d bytes, err=%v\n", n, err)
	b.offset += int64(n)
	return
}

func (b *readSeekablePageBlob) Seek(offset int64, whence int) (int64, error) {
	if offset < 0 {
		return 0, fmt.Errorf("Cannot seek with negative offset: %d", offset)
	}
	if whence < 0 || whence > 2 {
		return 0, fmt.Errorf("Illegal value for parameter whence: %s", whence)
	}

	switch whence {
	case 0:
		if offset != b.offset {
			props, err := b.getProperties()
			if err != nil {
				return 0, err
			}

			if offset > props.ContentLength {
				return 0, fmt.Errorf("Cannot seek beyond end of blob (%d > %d)", offset, props.ContentLength)
			}
			b.offset = offset
		}
	case 1:
		if offset != 0 {
			props, err := b.getProperties()
			if err != nil {
				return 0, err
			}

			if b.offset+offset > props.ContentLength {
				return 0, fmt.Errorf("Cannot seek beyond end of blob (%d > %d)", b.offset+offset, props.ContentLength)
			}
			b.offset += offset
		}
	case 2:
		if offset != 0 {
			return 0, fmt.Errorf("Cannot seek beyond end of blob")
		}

		props, err := b.getProperties()
		if err != nil {
			return 0, err
		}
		b.offset = props.ContentLength
	default:
		return 0, errNotImplemented
	}

	return b.offset, nil
}

func (b readSeekablePageBlob) getProperties() (storage.BlobProperties, error) {
	var rv storage.BlobProperties

	req, err := http.NewRequest("HEAD", b.url, nil)
	if err != nil {
		return rv, err
	}
	req.Header.Set("x-ms-version", apiVersion)

	res, err := http.DefaultClient.Do(req)
	if err != nil {
		return rv, err
	}
	if !(res.StatusCode == http.StatusOK) {
		return rv, fmt.Errorf("Non success status code: %s", res.Status)
	}
	defer res.Body.Close()

	rv.BlobType = storage.BlobType(res.Header.Get("x-ms-blob-type"))
	fmt.Sscanf(res.Header.Get("Content-Length"), "%d", &rv.ContentLength)
	return rv, nil
}

var errNotImplemented = fmt.Errorf("Not implemented")
<commit_msg>update Azure SDK location<commit_after>package main

import (
	"github.com/Azure/azure-sdk-for-go/storage"
	"io/ioutil"
	"os"
	"path"

	"github.com/paulmey/inspect-azure-vhd/ext4"

	"encoding/binary"
	"flag"
	"fmt"
	"io"
	"net/http"
)

const (
	apiVersion = "2014-02-14"
)

var (
	help      bool
	ouputPath string
)

func init() {
	flag.BoolVar(&help, "help", false, "Prints this help.")
	flag.StringVar(&ouputPath, "outputPath", "out", "Specifies the path where logs and files are placed.")
}

func main() {
	flag.Parse()
	if flag.NArg() != 1 || help {
		fmt.Printf("Usage: ./inspect-remote-vhd <vhd-read-uri>\n")
		flag.PrintDefaults()
		return
	}

	uri := flag.Arg(0)

	s := SasPageBlobAccessor(uri)

	fmt.Printf("Reading partition table...\n")
	// location of MBR partition table http://en.wikipedia.org/wiki/Master_boot_record#Sector_layout
	s.Seek(446, 0)
	var p partitionEntry
	err := binary.Read(s, binary.LittleEndian, &p)
	if err != nil {
		panic(err)
	}

	fmt.Printf("Inspecting ext4 filesystem on first partition...\n")
	// assume that partition 0 is linux with ext4
	if p.Type != 0x83 {
		err = fmt.Errorf("Not a linux partition!")
		return
	}

	r, err := ext4.NewReader(s, p.LBAfirst, p.Sectors)
	if err != nil {
		panic(err)
	}

	globs := []string{
		"/etc/ssh*/*",
		"/etc/ssh*",
		"/etc/fstab",
		"/etc/mtab",
		"/etc/waagent.conf",
		"/var/log/messages",
		"/var/log/boot.log",
		"/var/log/dmesg",
		"/var/log/syslog",
		"/var/log/waagent/*",
		"/var/log/waagent*",
		"/var/log/walinuxagent/*",
		"/var/log/walinuxagent*",
		"/var/log/azure/*",
		"/var/log/azure/*/*",
		"/var/log/*",
	}

	fs, err := r.Root()
	if err != nil {
		panic(err)
	}

	fmt.Printf("Downloading interesting files...\n")
	for _, glob := range globs {
		files, err := fs.Match(glob)
		if err != nil {
			panic(err)
		}
		for _, f := range files {
			orig := f
			for f.FileType == ext4.FileTypeSymlink {
				f, err = f.ResolveSymlink()
				if err != nil {
					fmt.Printf("WARN: failed to resolve symlink %s: %v\n", orig.Fullname(), err)
					continue
				}
			}
			if f.FileType != ext4.FileTypeFile {
				continue
			}
			inode, err := r.GetInode(f.Inode)
			if err != nil {
				fmt.Printf("WARN: could not read inode %d (%s -> %s): %v\n", f.Inode, orig.Fullname(), f.Fullname(), err)
				continue
			}

			fmt.Printf("   %s (%s) \n", orig.Fullname(), orig.FileType)
			fmt.Printf("     \\-> downloading %d bytes\n", inode.Size())

			data, err := r.GetInodeContent(inode)
			if err != nil {
				fmt.Printf("WARN: could not read data for %s: %s", orig.Fullname(), err)
				continue
			}

			outFile := ouputPath + "/" + orig.Fullname()
			if err := os.MkdirAll(path.Dir(outFile), 0777); err != nil {
				fmt.Printf("ERR: could not create path %s: %s", path.Dir(outFile), err)
				return
			}
			err = ioutil.WriteFile(outFile, data, 0666)
			if err != nil {
				fmt.Printf("ERR: could not write file %s: %s", path.Dir(outFile), err)
				return
			}
		}
	}
}

type partitionEntry struct {
	Active   byte
	CHSFirst [3]byte
	Type     byte
	CHSLast  [3]byte
	LBAfirst uint32
	Sectors  uint32
}

func SasPageBlobAccessor(url string) io.ReadSeeker {
	return &readSeekablePageBlob{
		url: url,
	}
}

type readSeekablePageBlob struct {
	url    string
	offset int64
}

func (b *readSeekablePageBlob) Read(buffer []byte) (n int, err error) {
	if len(buffer) == 0 {
		return
	}

	req, err := http.NewRequest("GET", b.url, nil)
	if err != nil {
		return
	}
	req.Header.Set("x-ms-version", apiVersion)
	req.Header.Set("x-ms-range", fmt.Sprintf("bytes=%d-%d", b.offset, b.offset+int64(len(buffer))))

	res, err := http.DefaultClient.Do(req)
	if err != nil {
		return
	}
	if !(res.StatusCode == http.StatusOK ||
		res.StatusCode == http.StatusPartialContent) {
		return 0, fmt.Errorf("Non success status code: %s", res.Status)
	}

	defer res.Body.Close()

	// paulmey: for some reason, ioutil.ReadAll reads on infinitely on res.Body ?
	for n < len(buffer) && err == nil {
		nn, nerr := res.Body.Read(buffer[n:])
		err = nerr
		n += nn
	}
	//	fmt.Printf("### read %d bytes, err=%v\n", n, err)
	b.offset += int64(n)
	return
}

func (b *readSeekablePageBlob) Seek(offset int64, whence int) (int64, error) {
	if offset < 0 {
		return 0, fmt.Errorf("Cannot seek with negative offset: %d", offset)
	}
	if whence < 0 || whence > 2 {
		return 0, fmt.Errorf("Illegal value for parameter whence: %s", whence)
	}

	switch whence {
	case 0:
		if offset != b.offset {
			props, err := b.getProperties()
			if err != nil {
				return 0, err
			}

			if offset > props.ContentLength {
				return 0, fmt.Errorf("Cannot seek beyond end of blob (%d > %d)", offset, props.ContentLength)
			}
			b.offset = offset
		}
	case 1:
		if offset != 0 {
			props, err := b.getProperties()
			if err != nil {
				return 0, err
			}

			if b.offset+offset > props.ContentLength {
				return 0, fmt.Errorf("Cannot seek beyond end of blob (%d > %d)", b.offset+offset, props.ContentLength)
			}
			b.offset += offset
		}
	case 2:
		if offset != 0 {
			return 0, fmt.Errorf("Cannot seek beyond end of blob")
		}

		props, err := b.getProperties()
		if err != nil {
			return 0, err
		}
		b.offset = props.ContentLength
	default:
		return 0, errNotImplemented
	}

	return b.offset, nil
}

func (b readSeekablePageBlob) getProperties() (storage.BlobProperties, error) {
	var rv storage.BlobProperties

	req, err := http.NewRequest("HEAD", b.url, nil)
	if err != nil {
		return rv, err
	}
	req.Header.Set("x-ms-version", apiVersion)

	res, err := http.DefaultClient.Do(req)
	if err != nil {
		return rv, err
	}
	if !(res.StatusCode == http.StatusOK) {
		return rv, fmt.Errorf("Non success status code: %s", res.Status)
	}
	defer res.Body.Close()

	rv.BlobType = storage.BlobType(res.Header.Get("x-ms-blob-type"))
	fmt.Sscanf(res.Header.Get("Content-Length"), "%d", &rv.ContentLength)
	return rv, nil
}

var errNotImplemented = fmt.Errorf("Not implemented")
<|endoftext|>


<commit_before>package main

import (
	"bytes"
	"fmt"
	"io/ioutil"
	"net/http"
	"os"
	"path"
	"strings"
	"text/template"
	"time"

	"github.com/apex/log"
	"github.com/apex/log/handlers/cli"
	"github.com/client9/codegen/shell"
	"github.com/goreleaser/goreleaser/pkg/config"
	"github.com/goreleaser/goreleaser/pkg/context"
	"github.com/goreleaser/goreleaser/pkg/defaults"
	"github.com/pkg/errors"
	kingpin "gopkg.in/alecthomas/kingpin.v2"
)

// nolint: gochecknoglobals
var (
	version = "dev"
	commit  = "none"
	datestr = "unknown"
)

// given a template, and a config, generate shell script
func makeShell(tplsrc string, cfg *config.Project) ([]byte, error) {
	// if we want to add a timestamp in the templates this
	//  function will generate it
	funcMap := template.FuncMap{
		"join":             strings.Join,
		"platformBinaries": makePlatformBinaries,
		"timestamp": func() string {
			return time.Now().UTC().Format(time.RFC3339)
		},
	}

	out := bytes.Buffer{}
	t, err := template.New("shell").Funcs(funcMap).Parse(tplsrc)
	if err != nil {
		return nil, err
	}
	err = t.Execute(&out, cfg)
	return out.Bytes(), err
}

// makePlatform returns a platform string combining goos, goarch, and goarm.
func makePlatform(goos, goarch, goarm string) string {
	platform := goos + "/" + goarch
	if goarch == "arm" && goarm != "" {
		platform += "v" + goarm
	}
	return platform
}

// makePlatformBinaries returns a map from platforms to a slice of binaries
// built for that platform.
func makePlatformBinaries(cfg *config.Project) map[string][]string {
	platformBinaries := make(map[string][]string)
	for _, build := range cfg.Builds {
		ignore := make(map[string]bool)
		for _, ignoredBuild := range build.Ignore {
			platform := makePlatform(ignoredBuild.Goos, ignoredBuild.Goarch, ignoredBuild.Goarm)
			ignore[platform] = true
		}
		for _, goos := range build.Goos {
			for _, goarch := range build.Goarch {
				switch goarch {
				case "arm":
					for _, goarm := range build.Goarm {
						platform := makePlatform(goos, goarch, goarm)
						if !ignore[platform] {
							platformBinaries[platform] = append(platformBinaries[platform], build.Binary)
						}
					}
				default:
					platform := makePlatform(goos, goarch, "")
					if !ignore[platform] {
						platformBinaries[platform] = append(platformBinaries[platform], build.Binary)
					}
				}
			}
		}
	}
	return platformBinaries
}

// converts the given name template to it's equivalent in shell
// except for the default goreleaser templates, templates with
// conditionals will return an error
//
// {{ .Binary }} --->  [prefix]${BINARY}, etc.
//
func makeName(prefix, target string) (string, error) {
	// armv6 is the default in the shell script
	// so do not need special template condition for ARM
	armversion := "{{ .Arch }}{{ if .Arm }}v{{ .Arm }}{{ end }}"
	target = strings.Replace(target, armversion, "{{ .Arch }}", -1)

	// hack for https://github.com/goreleaser/godownloader/issues/70
	armversion = "{{ .Arch }}{{ if .Arm }}{{ .Arm }}{{ end }}"
	target = strings.Replace(target, armversion, "{{ .Arch }}", -1)

	target = strings.Replace(target, "{{.Arm}}", "{{ .Arch }}", -1)
	target = strings.Replace(target, "{{ .Arm }}", "{{ .Arch }}", -1)

	// otherwise if it contains a conditional, we can't (easily)
	// translate that to bash.  Ask for bug report.
	if strings.Contains(target, "{{ if") ||
		strings.Contains(target, "{{if") {
		//nolint: lll
		return "", fmt.Errorf("name_template %q contains unknown conditional or ARM format. Please file bug at https://github.com/goreleaser/godownloader", target)
	}

	varmap := map[string]string{
		"Os":          "${OS}",
		"Arch":        "${ARCH}",
		"Version":     "${VERSION}",
		"Tag":         "${TAG}",
		"Binary":      "${BINARY}",
		"ProjectName": "${PROJECT_NAME}",
	}

	out := bytes.Buffer{}
	if _, err := out.WriteString(prefix); err != nil {
		return "", err
	}
	t, err := template.New("name").Parse(target)
	if err != nil {
		return "", err
	}
	err = t.Execute(&out, varmap)
	return out.String(), err
}

// returns the owner/name repo from input
//
// see https://github.com/goreleaser/godownloader/issues/55
func normalizeRepo(repo string) string {
	// handle full or partial URLs
	repo = strings.TrimPrefix(repo, "https://github.com/")
	repo = strings.TrimPrefix(repo, "http://github.com/")
	repo = strings.TrimPrefix(repo, "github.com/")

	// hande /name/repo or name/repo/ cases
	repo = strings.Trim(repo, "/")

	return repo
}

func loadURLs(path, configPath string) (*config.Project, error) {
	for _, file := range []string{configPath, "goreleaser.yml", ".goreleaser.yml", "goreleaser.yaml", ".goreleaser.yaml"} {
		if file == "" {
			continue
		}
		url := fmt.Sprintf("%s/%s", path, file)
		log.Infof("reading %s", url)
		project, err := loadURL(url)
		if err != nil {
			return nil, err
		}
		if project != nil {
			return project, nil
		}
	}
	return nil, fmt.Errorf("could not fetch a goreleaser configuration file")
}

func loadURL(file string) (*config.Project, error) {
	// nolint: gosec
	resp, err := http.Get(file)
	if err != nil {
		return nil, err
	}
	if resp.StatusCode != 200 {
		log.Errorf("reading %s returned %d %s\n", file, resp.StatusCode, http.StatusText(resp.StatusCode))
		return nil, nil
	}
	p, err := config.LoadReader(resp.Body)

	// to make errcheck happy
	errc := resp.Body.Close()
	if errc != nil {
		return nil, errc
	}
	return &p, err
}

func loadFile(file string) (*config.Project, error) {
	p, err := config.Load(file)
	return &p, err
}

// Load project configuration from a given repo name or filepath/url.
func Load(repo, configPath, file string) (project *config.Project, err error) {
	if repo == "" && file == "" {
		return nil, fmt.Errorf("repo or file not specified")
	}
	if file == "" {
		repo = normalizeRepo(repo)
		log.Infof("reading repo %q on github", repo)
		project, err = loadURLs(
			fmt.Sprintf("https://raw.githubusercontent.com/%s/master", repo),
			configPath,
		)
	} else {
		log.Infof("reading file %q", file)
		project, err = loadFile(file)
	}
	if err != nil {
		return nil, err
	}

	// if not specified add in GitHub owner/repo info
	if project.Release.GitHub.Owner == "" {
		if repo == "" {
			return nil, fmt.Errorf("owner/name repo not specified")
		}
		project.Release.GitHub.Owner = path.Dir(repo)
		project.Release.GitHub.Name = path.Base(repo)
	}

	// avoid errors in docker defaulter
	for i := range project.Dockers {
		project.Dockers[i].Files = []string{}
	}

	var ctx = context.New(*project)
	for _, defaulter := range defaults.Defaulters {
		log.Infof("setting defaults for %s", defaulter)
		if err := defaulter.Default(ctx); err != nil {
			return nil, errors.Wrap(err, "failed to set defaults")
		}
	}
	project = &ctx.Config

	// set default binary name
	if len(project.Builds) == 0 {
		project.Builds = []config.Build{
			{Binary: path.Base(repo)},
		}
	}
	if project.Builds[0].Binary == "" {
		project.Builds[0].Binary = path.Base(repo)
	}

	return project, err
}

func main() {
	log.SetHandler(cli.Default)

	var (
		repo    = kingpin.Flag("repo", "owner/name or URL of GitHub repository").Short('r').String()
		output  = kingpin.Flag("output", "output file, default stdout").Short('o').String()
		force   = kingpin.Flag("force", "force writing of output").Short('f').Bool()
		source  = kingpin.Flag("source", "source type [godownloader|raw|equinoxio]").Default("godownloader").String()
		exe     = kingpin.Flag("exe", "name of binary, used only in raw").String()
		nametpl = kingpin.Flag("nametpl", "name template, used only in raw").String()
		tree    = kingpin.Flag("tree", "use tree to generate multiple outputs").String()
		file    = kingpin.Arg("file", "??").String()
	)

	kingpin.CommandLine.Version(fmt.Sprintf("%v, commit %v, built at %v", version, commit, datestr))
	kingpin.CommandLine.VersionFlag.Short('v')
	kingpin.CommandLine.HelpFlag.Short('h')
	kingpin.Parse()

	if *tree != "" {
		err := treewalk(*tree, *file, *force)
		if err != nil {
			log.WithError(err).Error("treewalker failed")
			os.Exit(1)
		}
		return
	}

	// gross.. need config
	out, err := processSource(*source, *repo, "", *file, *exe, *nametpl)

	if err != nil {
		log.WithError(err).Error("failed")
		os.Exit(1)
	}

	// stdout case
	if *output == "" {
		if _, err = os.Stdout.Write(out); err != nil {
			log.WithError(err).Error("unable to write")
			os.Exit(1)
		}
		return
	}

	// only write out if forced to, OR if output is effectively different
	// than what the file has.
	if *force || shell.ShouldWriteFile(*output, out) {
		if err = ioutil.WriteFile(*output, out, 0666); err != nil {
			log.WithError(err).Errorf("unable to write to %s", *output)
			os.Exit(1)
		}
		return
	}

	// output is effectively the same as new content
	// (comments and most whitespace doesn't matter)
	// nothing to do
}
<commit_msg>fix: replace template function<commit_after>package main

import (
	"bytes"
	"fmt"
	"io/ioutil"
	"net/http"
	"os"
	"path"
	"strings"
	"text/template"
	"time"

	"github.com/apex/log"
	"github.com/apex/log/handlers/cli"
	"github.com/client9/codegen/shell"
	"github.com/goreleaser/goreleaser/pkg/config"
	"github.com/goreleaser/goreleaser/pkg/context"
	"github.com/goreleaser/goreleaser/pkg/defaults"
	"github.com/pkg/errors"
	kingpin "gopkg.in/alecthomas/kingpin.v2"
)

// nolint: gochecknoglobals
var (
	version = "dev"
	commit  = "none"
	datestr = "unknown"
)

// given a template, and a config, generate shell script
func makeShell(tplsrc string, cfg *config.Project) ([]byte, error) {
	// if we want to add a timestamp in the templates this
	//  function will generate it
	funcMap := template.FuncMap{
		"join":             strings.Join,
		"platformBinaries": makePlatformBinaries,
		"timestamp": func() string {
			return time.Now().UTC().Format(time.RFC3339)
		},
		"replace": strings.ReplaceAll,
		"time": func(s string) string {
			return time.Now().UTC().Format(s)
		},
		"tolower": strings.ToLower,
		"toupper": strings.ToUpper,
		"trim":    strings.TrimSpace,
	}

	out := bytes.Buffer{}
	t, err := template.New("shell").Funcs(funcMap).Parse(tplsrc)
	if err != nil {
		return nil, err
	}
	err = t.Execute(&out, cfg)
	return out.Bytes(), err
}

// makePlatform returns a platform string combining goos, goarch, and goarm.
func makePlatform(goos, goarch, goarm string) string {
	platform := goos + "/" + goarch
	if goarch == "arm" && goarm != "" {
		platform += "v" + goarm
	}
	return platform
}

// makePlatformBinaries returns a map from platforms to a slice of binaries
// built for that platform.
func makePlatformBinaries(cfg *config.Project) map[string][]string {
	platformBinaries := make(map[string][]string)
	for _, build := range cfg.Builds {
		ignore := make(map[string]bool)
		for _, ignoredBuild := range build.Ignore {
			platform := makePlatform(ignoredBuild.Goos, ignoredBuild.Goarch, ignoredBuild.Goarm)
			ignore[platform] = true
		}
		for _, goos := range build.Goos {
			for _, goarch := range build.Goarch {
				switch goarch {
				case "arm":
					for _, goarm := range build.Goarm {
						platform := makePlatform(goos, goarch, goarm)
						if !ignore[platform] {
							platformBinaries[platform] = append(platformBinaries[platform], build.Binary)
						}
					}
				default:
					platform := makePlatform(goos, goarch, "")
					if !ignore[platform] {
						platformBinaries[platform] = append(platformBinaries[platform], build.Binary)
					}
				}
			}
		}
	}
	return platformBinaries
}

// converts the given name template to it's equivalent in shell
// except for the default goreleaser templates, templates with
// conditionals will return an error
//
// {{ .Binary }} --->  [prefix]${BINARY}, etc.
//
func makeName(prefix, target string) (string, error) {
	// armv6 is the default in the shell script
	// so do not need special template condition for ARM
	armversion := "{{ .Arch }}{{ if .Arm }}v{{ .Arm }}{{ end }}"
	target = strings.Replace(target, armversion, "{{ .Arch }}", -1)

	// hack for https://github.com/goreleaser/godownloader/issues/70
	armversion = "{{ .Arch }}{{ if .Arm }}{{ .Arm }}{{ end }}"
	target = strings.Replace(target, armversion, "{{ .Arch }}", -1)

	target = strings.Replace(target, "{{.Arm}}", "{{ .Arch }}", -1)
	target = strings.Replace(target, "{{ .Arm }}", "{{ .Arch }}", -1)

	// otherwise if it contains a conditional, we can't (easily)
	// translate that to bash.  Ask for bug report.
	if strings.Contains(target, "{{ if") ||
		strings.Contains(target, "{{if") {
		//nolint: lll
		return "", fmt.Errorf("name_template %q contains unknown conditional or ARM format. Please file bug at https://github.com/goreleaser/godownloader", target)
	}

	varmap := map[string]string{
		"Os":          "${OS}",
		"Arch":        "${ARCH}",
		"Version":     "${VERSION}",
		"Tag":         "${TAG}",
		"Binary":      "${BINARY}",
		"ProjectName": "${PROJECT_NAME}",
	}

	out := bytes.Buffer{}
	if _, err := out.WriteString(prefix); err != nil {
		return "", err
	}
	t, err := template.New("name").Parse(target)
	if err != nil {
		return "", err
	}
	err = t.Execute(&out, varmap)
	return out.String(), err
}

// returns the owner/name repo from input
//
// see https://github.com/goreleaser/godownloader/issues/55
func normalizeRepo(repo string) string {
	// handle full or partial URLs
	repo = strings.TrimPrefix(repo, "https://github.com/")
	repo = strings.TrimPrefix(repo, "http://github.com/")
	repo = strings.TrimPrefix(repo, "github.com/")

	// hande /name/repo or name/repo/ cases
	repo = strings.Trim(repo, "/")

	return repo
}

func loadURLs(path, configPath string) (*config.Project, error) {
	for _, file := range []string{configPath, "goreleaser.yml", ".goreleaser.yml", "goreleaser.yaml", ".goreleaser.yaml"} {
		if file == "" {
			continue
		}
		url := fmt.Sprintf("%s/%s", path, file)
		log.Infof("reading %s", url)
		project, err := loadURL(url)
		if err != nil {
			return nil, err
		}
		if project != nil {
			return project, nil
		}
	}
	return nil, fmt.Errorf("could not fetch a goreleaser configuration file")
}

func loadURL(file string) (*config.Project, error) {
	// nolint: gosec
	resp, err := http.Get(file)
	if err != nil {
		return nil, err
	}
	if resp.StatusCode != 200 {
		log.Errorf("reading %s returned %d %s\n", file, resp.StatusCode, http.StatusText(resp.StatusCode))
		return nil, nil
	}
	p, err := config.LoadReader(resp.Body)

	// to make errcheck happy
	errc := resp.Body.Close()
	if errc != nil {
		return nil, errc
	}
	return &p, err
}

func loadFile(file string) (*config.Project, error) {
	p, err := config.Load(file)
	return &p, err
}

// Load project configuration from a given repo name or filepath/url.
func Load(repo, configPath, file string) (project *config.Project, err error) {
	if repo == "" && file == "" {
		return nil, fmt.Errorf("repo or file not specified")
	}
	if file == "" {
		repo = normalizeRepo(repo)
		log.Infof("reading repo %q on github", repo)
		project, err = loadURLs(
			fmt.Sprintf("https://raw.githubusercontent.com/%s/master", repo),
			configPath,
		)
	} else {
		log.Infof("reading file %q", file)
		project, err = loadFile(file)
	}
	if err != nil {
		return nil, err
	}

	// if not specified add in GitHub owner/repo info
	if project.Release.GitHub.Owner == "" {
		if repo == "" {
			return nil, fmt.Errorf("owner/name repo not specified")
		}
		project.Release.GitHub.Owner = path.Dir(repo)
		project.Release.GitHub.Name = path.Base(repo)
	}

	// avoid errors in docker defaulter
	for i := range project.Dockers {
		project.Dockers[i].Files = []string{}
	}

	var ctx = context.New(*project)
	for _, defaulter := range defaults.Defaulters {
		log.Infof("setting defaults for %s", defaulter)
		if err := defaulter.Default(ctx); err != nil {
			return nil, errors.Wrap(err, "failed to set defaults")
		}
	}
	project = &ctx.Config

	// set default binary name
	if len(project.Builds) == 0 {
		project.Builds = []config.Build{
			{Binary: path.Base(repo)},
		}
	}
	if project.Builds[0].Binary == "" {
		project.Builds[0].Binary = path.Base(repo)
	}

	return project, err
}

func main() {
	log.SetHandler(cli.Default)

	var (
		repo    = kingpin.Flag("repo", "owner/name or URL of GitHub repository").Short('r').String()
		output  = kingpin.Flag("output", "output file, default stdout").Short('o').String()
		force   = kingpin.Flag("force", "force writing of output").Short('f').Bool()
		source  = kingpin.Flag("source", "source type [godownloader|raw|equinoxio]").Default("godownloader").String()
		exe     = kingpin.Flag("exe", "name of binary, used only in raw").String()
		nametpl = kingpin.Flag("nametpl", "name template, used only in raw").String()
		tree    = kingpin.Flag("tree", "use tree to generate multiple outputs").String()
		file    = kingpin.Arg("file", "??").String()
	)

	kingpin.CommandLine.Version(fmt.Sprintf("%v, commit %v, built at %v", version, commit, datestr))
	kingpin.CommandLine.VersionFlag.Short('v')
	kingpin.CommandLine.HelpFlag.Short('h')
	kingpin.Parse()

	if *tree != "" {
		err := treewalk(*tree, *file, *force)
		if err != nil {
			log.WithError(err).Error("treewalker failed")
			os.Exit(1)
		}
		return
	}

	// gross.. need config
	out, err := processSource(*source, *repo, "", *file, *exe, *nametpl)

	if err != nil {
		log.WithError(err).Error("failed")
		os.Exit(1)
	}

	// stdout case
	if *output == "" {
		if _, err = os.Stdout.Write(out); err != nil {
			log.WithError(err).Error("unable to write")
			os.Exit(1)
		}
		return
	}

	// only write out if forced to, OR if output is effectively different
	// than what the file has.
	if *force || shell.ShouldWriteFile(*output, out) {
		if err = ioutil.WriteFile(*output, out, 0666); err != nil {
			log.WithError(err).Errorf("unable to write to %s", *output)
			os.Exit(1)
		}
		return
	}

	// output is effectively the same as new content
	// (comments and most whitespace doesn't matter)
	// nothing to do
}
<|endoftext|>


<commit_before>package main

import (
	"fmt"
	"os"
	"time"

	"github.com/iris-contrib/graceful"
	"github.com/iris-contrib/middleware/cors"
	"github.com/iris-contrib/middleware/logger"
	"github.com/iris-contrib/middleware/recovery"
	"github.com/kataras/iris"
)

func main() {
	web := iris.New()

	web.Use(logger.New(iris.Logger))
	web.Use(recovery.New(os.Stderr))

	c := cors.New(cors.Options{
		AllowedOrigins:   []string{"*"},
		AllowedMethods:   []string{"GET", "POST", "DELETE", "PUT", "OPTIONS"},
		AllowedHeaders:   []string{"Content-Type", "X-ENDPOINT", "X-SERVICE", "ACCEPT", "ORIGIN", "Authorization", "X-CSRF-TOKEN", "Cookie"},
		AllowCredentials: true,
		Debug:            true,
	})

	web.Use(c)
	web.Config.Render.Template.Directory = "./app/views"

	web.Get("/", indexHandler)
	web.Static("/assets", "./app/assets", 1)

	//Get port from environment variables, default port number is 7000
	port := os.Getenv("PORT")

	if port == "" {
		port = "7000"
	}

	fmt.Println("Service is listening at:" + port)
	graceful.Run(":"+port, time.Duration(10)*time.Second, web)
}

func indexHandler(ctx *iris.Context) {
	ctx.Response.Header.Add("Access-Control-Allow-Origin", "*")
	if err := ctx.Render("index.html", nil); err != nil {
		fmt.Println(err.Error())
		panic(err)
	}
}
<commit_msg>Update iris initialize logic<commit_after>package main

import (
	"fmt"
	"os"
	"time"

	"github.com/iris-contrib/graceful"
	"github.com/iris-contrib/middleware/cors"
	"github.com/iris-contrib/middleware/logger"
	"github.com/iris-contrib/middleware/recovery"
	"github.com/kataras/go-template/html"
	"github.com/kataras/iris"
)

func main() {
	web := iris.New()

	web.Use(logger.New())
	web.Use(recovery.Handler)

	c := cors.New(cors.Options{
		AllowedOrigins:   []string{"*"},
		AllowedMethods:   []string{"GET", "POST", "OPTIONS"},
		AllowedHeaders:   []string{"Content-Type", "ACCEPT", "ORIGIN"},
		AllowCredentials: true,
		Debug:            true,
	})

	web.Use(c)
	web.UseTemplate(html.New()).Directory("./app/views", ".html")

	web.Get("/", indexHandler)
	web.Static("/assets", "./app/assets", 1)

	//Get port from environment variables, default port number is 7000
	port := os.Getenv("PORT")

	if port == "" {
		port = "7000"
	}

	fmt.Println("Service is listening at:" + port)
	graceful.Run(":"+port, time.Duration(10)*time.Second, web)
}

func indexHandler(ctx *iris.Context) {
	ctx.Response.Header.Add("Access-Control-Allow-Origin", "*")
	if err := ctx.Render("index.html", nil); err != nil {
		fmt.Println(err.Error())
		panic(err)
	}
}
<|endoftext|>