func path(uri string) string {
	parts := strings.SplitN(uri, "/", 4)
	if len(parts) != 4 || parts[0] != "gs:" || len(parts[3]) == 0 {
		return ""
	}
	return parts[3]
}
path returns the portion of the GCS path for a valid M-Lab GCS archive URI.
Because ValidateTestPath() verifies other aspects of DataPath.URI, path()
returns the empty string if it is malformed.
package etl
import (
	"encoding/base64"
	"errors"
	"fmt"
	"log"
	"net"
	"regexp"
	"strings"
)
var (
	IsBatch bool
	OmitDeltas bool
	GCloudProject string
	BigqueryProject string
	BigqueryDataset string
	BatchAnnotatorURL string
)
var (
	GitCommit = "nocommit"
	Version   = "noversion"
)
const YYYYMMDD = `\d{4}[01]\d[0123]\d`
const MlabDomain = `measurement-lab.org`
const BucketPattern = `gs: 
const ExpTypePattern = `(?:([a-z-]+)/)?([a-z0-9-]+)/`  
const DatePathPattern = `(\d{4}/[01]\d/[0123]\d)/`
const dateTime = `(\d{4}[01]\d[0123]\d)T(\d{6}(\.\d{0,6})?)Z`
const type2 = `(?:-([a-z0-9-]+))?`  
const mlabNSiteNN = `-(mlab\d)-([a-z]{3}\d[0-9t])-`
const expNNNNE = `([a-z-]+)(?:-(\d{4}))?(-e)?`
const suffix = `(\.tar|\.tar.gz|\.tgz)$`
var (
	basicTaskPattern = regexp.MustCompile(
		`(?P<preamble>.*)` + dateTime + `(?P<postamble>.*)`)
	startPattern = regexp.MustCompile(`^` + BucketPattern + ExpTypePattern + DatePathPattern + `$`)
	endPattern   = regexp.MustCompile(`^` +
		type2 +  
		mlabNSiteNN +  
		expNNNNE +  
		suffix + `$`)  
	dateTimePattern = regexp.MustCompile(dateTime)
	sitePattern     = regexp.MustCompile(type2 + mlabNSiteNN)
	justSitePattern = regexp.MustCompile(`.*` + mlabNSiteNN + `.*`)
)
type DataPath struct {
	URI  string  
	Path string  
	Bucket   string  
	ExpDir   string  
	DataType string  
	DatePath string  
	PackedDate string  
	PackedTime string  
	DataType2  string  
	Host       string  
	Site       string  
	Experiment string  
	FileNumber string  
	Embargo    string  
	Suffix     string  
}
func ValidateTestPath(uri string) (DataPath, error) {
	basic := basicTaskPattern.FindStringSubmatch(uri)
	if basic == nil {
		return DataPath{}, errors.New("Path missing date-time string")
	}
	preamble := startPattern.FindStringSubmatch(basic[1])
	if preamble == nil {
		return DataPath{}, errors.New("Invalid preamble: " + fmt.Sprint(basic))
	}
	post := endPattern.FindStringSubmatch(basic[5])
	if post == nil {
		return DataPath{}, errors.New("Invalid postamble: " + basic[5])
	}
	dp := DataPath{
		URI:        uri,
		Path:       path(uri),
		Bucket:     preamble[1],
		ExpDir:     preamble[2],
		DataType:   preamble[3],
		DatePath:   preamble[4],
		PackedDate: basic[2],
		PackedTime: basic[3],
		DataType2:  post[1],
		Host:       post[2],
		Site:       post[3],
		Experiment: post[4],
		FileNumber: post[5],
		Embargo:    post[6],
		Suffix:     post[7],
	}
	dataType := dp.GetDataType()
	if dataType == INVALID {
		log.Printf("Invalid filename: %s\n", uri)
		return DataPath{}, ErrBadDataType
	}
	return dp, nil
}
func (dp DataPath) GetDataType() DataType {
	dt, ok := dirToDataType[dp.DataType]
	if !ok {
		return INVALID
	}
	return dt
}
func (dp DataPath) TableBase() string {
	return dp.GetDataType().Table()
}