Skip to content

Commit 06af1fa

Browse files
committed
Merge pull request #44 from go-spatial/viewer
Added a self-contained viewer
2 parents c1cb520 + 4e8dbec commit 06af1fa

File tree

5 files changed

+814
-0
lines changed

5 files changed

+814
-0
lines changed

.travis.yml

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
language: node_js
2+
3+
apt:
4+
update: true
5+
6+
git:
7+
depth: 2
8+
9+
node_js:
10+
- node
11+
12+
go:
13+
- 1.x
14+
15+
script:
16+
- echo "skipping tests."
17+
- bash -x ci/build_viewer.sh
18+
19+
deploy:
20+
provider: releases
21+
api_key:
22+
secure: Bu21GK4lUA/h/d710zTvP9aS2oxzxiwgCETv7fDqJ86xeVla9PGUu1v0G60l5zmTBO9ft1fmdk5S3TinZWWT4Q+uRslzB6VEM/04+/ZnEdmDlfO0r0+K9MzVy6l5C1NVyA1f+Zp30fDKgKy/0qSo3bHs+eztvG9aFD2rkyj3K8cS+vTzxVzShdg5zFL+56rV+IwwV1D2bKzkY+6cbrd6657Uk2TpV6OILo3mjMRWJMR7NcHi8nGh3nAT1qMkP5mBnZfkKR5ni76qGBGeW2PexsPnlwNqgYCLugTqzO7HsIxiMSsaqJWvuY83jXzY9BqdyksRITD9lwCBUVUSVwXW5kelWvK3rb5QKTnqxcSh8gsle1QowZxxHbjfc3bn7GQhuYE5Ic+AYw3GMxBKxe7Ma38y354xsECjmRuXTgjoBw7iypJ/jPPdfLTxMYKtGNfpdFTySbOlyOyB8rvX1P7J86V+fTxklLrKeF2nwI27YkupBDu3WzQEwo+guWqNp+xIQuwXqiicTgabLnIbZIddk3L5Nmc38Y9EaxM6rW5Zfps821a0OEq/34HHirCSYrkFTy8Oqdqb9NDSV5UwcwdBCyavRnUAIwTWjzLcmAqaXTndGbenv+2Hl2J/MrgnaJT4lEedppZbdt9nVA5vfJEEjM18E8K0iy3wFb1d9sOR12g=
23+
file_glob: true
24+
file: releases/*
25+
skip_cleanup: true
26+
on:
27+
tags: true

ci/build_viewer.sh

Lines changed: 80 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,80 @@
1+
#!/bin/bash -x
2+
3+
set -e
4+
5+
################################################################################
6+
# This script will build the necessary binaries for the fresco viewer. #
7+
################################################################################
8+
9+
OLDIR=$(pwd)
10+
VERSION_TAG=$TRAVIS_TAG
11+
if [ -z ${PROJECT_DIR+x} ]; then
12+
PROJECT_DIR=`dirname $0`/..
13+
fi
14+
15+
cd $PROJECT_DIR
16+
17+
# Let's make it absolute
18+
PROJECT_DIR=$(pwd)
19+
20+
21+
if [ -z "$VERSION_TAG" ]; then
22+
VERSION_TAG=$(git rev-parse --short HEAD)
23+
fi
24+
25+
LDFLAGS="-w -X main.Version=${VERSION_TAG}"
26+
export CGO_ENABLED=0
27+
28+
if [ -z "$TRAVIS_BUILD_DIR" ]; then
29+
TRAVIS_BUILD_DIR=$PROJECT_DIR
30+
fi
31+
32+
RELEASE_DIR=${TRAVIS_BUILD_DIR}/releases
33+
34+
mkdir -p "${RELEASE_DIR}"
35+
36+
go get github.com/elazarl/go-bindata-assetfs
37+
go get github.com/jteeuwen/go-bindata/go-bindata
38+
39+
40+
ls -l "$GOPATH/bin"
41+
42+
# Disable warnings as fatal for npm
43+
unset CI
44+
echo "generating assets"
45+
go generate ./...
46+
47+
echo "build zip of assets"
48+
49+
cd $PROJECT_DIR/build
50+
zip -9 -r -D ${RELEASE_DIR}/dist.zip .
51+
cd $PROJECT_DIR
52+
53+
54+
echo "building bin into ${RELEASE_DIR}"
55+
56+
57+
for GOARCH in amd64
58+
do
59+
for GOOS in darwin linux windows
60+
do
61+
BINFN="fresco"
62+
63+
if [ "$GOOS" == "windows" ]; then
64+
BINFN="${BINFN}.exe"
65+
fi
66+
67+
GOOS=${GOOS} GOARCH=${GOARCH} go build -ldflags "${LDFLAGS}" -o "${RELEASE_DIR}/${BINFN}" cmd/viewer/*.go
68+
69+
cdir=$(pwd)
70+
cd $RELEASE_DIR
71+
72+
chmod a+x ${BINFN}
73+
fn="fresco_${GOOS}"
74+
zip -9 -D ${fn}.zip ${BINFN}
75+
rm ${BINFN}
76+
cd ${cdir}
77+
done
78+
done
79+
cd $OLDDIR
80+

cmd/viewer/assetfs.go

Lines changed: 185 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,185 @@
1+
// this package is a copy of "github.com/elazarl/go-bindata-assetfs"
2+
// with minor modifications making `assetFS` `public via `AssetFileServer`
3+
4+
package main
5+
6+
import (
7+
"bytes"
8+
"errors"
9+
"io"
10+
"io/ioutil"
11+
"log"
12+
"net/http"
13+
"os"
14+
"path"
15+
"path/filepath"
16+
"strings"
17+
"time"
18+
19+
assetfs "github.com/elazarl/go-bindata-assetfs"
20+
)
21+
22+
var (
23+
defaultFileTimestamp = time.Now()
24+
)
25+
26+
// FakeFile implements os.FileInfo interface for a given path and size
27+
type FakeFile struct {
28+
// Path is the path of this file
29+
Path string
30+
// Dir marks of the path is a directory
31+
Dir bool
32+
// Len is the length of the fake file, zero if it is a directory
33+
Len int64
34+
// Timestamp is the ModTime of this file
35+
Timestamp time.Time
36+
}
37+
38+
func (f *FakeFile) Name() string {
39+
_, name := filepath.Split(f.Path)
40+
return name
41+
}
42+
43+
func (f *FakeFile) Mode() os.FileMode {
44+
mode := os.FileMode(0644)
45+
if f.Dir {
46+
return mode | os.ModeDir
47+
}
48+
return mode
49+
}
50+
51+
func (f *FakeFile) ModTime() time.Time {
52+
return f.Timestamp
53+
}
54+
55+
func (f *FakeFile) Size() int64 {
56+
return f.Len
57+
}
58+
59+
func (f *FakeFile) IsDir() bool {
60+
return f.Mode().IsDir()
61+
}
62+
63+
func (f *FakeFile) Sys() interface{} {
64+
return nil
65+
}
66+
67+
// AssetFile implements http.File interface for a no-directory file with content
68+
type AssetFile struct {
69+
*bytes.Reader
70+
io.Closer
71+
FakeFile
72+
}
73+
74+
func NewAssetFile(name string, content []byte, timestamp time.Time) *AssetFile {
75+
if timestamp.IsZero() {
76+
timestamp = defaultFileTimestamp
77+
}
78+
return &AssetFile{
79+
bytes.NewReader(content),
80+
ioutil.NopCloser(nil),
81+
FakeFile{name, false, int64(len(content)), timestamp}}
82+
}
83+
84+
func (f *AssetFile) Readdir(count int) ([]os.FileInfo, error) {
85+
return nil, errors.New("not a directory")
86+
}
87+
88+
func (f *AssetFile) Size() int64 {
89+
return f.FakeFile.Size()
90+
}
91+
92+
func (f *AssetFile) Stat() (os.FileInfo, error) {
93+
return f, nil
94+
}
95+
96+
// AssetDirectory implements http.File interface for a directory
97+
type AssetDirectory struct {
98+
AssetFile
99+
ChildrenRead int
100+
Children []os.FileInfo
101+
}
102+
103+
func NewAssetDirectory(name string, children []string, fs *AssetFS) *AssetDirectory {
104+
fileinfos := make([]os.FileInfo, 0, len(children))
105+
for _, child := range children {
106+
_, err := fs.AssetDir(filepath.Join(name, child))
107+
fileinfos = append(fileinfos, &FakeFile{child, err == nil, 0, time.Time{}})
108+
}
109+
return &AssetDirectory{
110+
AssetFile{
111+
bytes.NewReader(nil),
112+
ioutil.NopCloser(nil),
113+
FakeFile{name, true, 0, time.Time{}},
114+
},
115+
0,
116+
fileinfos}
117+
}
118+
119+
func (f *AssetDirectory) Readdir(count int) ([]os.FileInfo, error) {
120+
if count <= 0 {
121+
return f.Children, nil
122+
}
123+
if f.ChildrenRead+count > len(f.Children) {
124+
count = len(f.Children) - f.ChildrenRead
125+
}
126+
rv := f.Children[f.ChildrenRead : f.ChildrenRead+count]
127+
f.ChildrenRead += count
128+
return rv, nil
129+
}
130+
131+
func (f *AssetDirectory) Stat() (os.FileInfo, error) {
132+
return f, nil
133+
}
134+
135+
// AssetFS implements http.FileSystem, allowing
136+
// embedded files to be served from net/http package.
137+
type AssetFS struct {
138+
// Asset should return content of file in path if exists
139+
Asset func(path string) ([]byte, error)
140+
// AssetDir should return list of files in the path
141+
AssetDir func(path string) ([]string, error)
142+
// AssetInfo should return the info of file in path if exists
143+
AssetInfo func(path string) (os.FileInfo, error)
144+
// Prefix would be prepended to http requests
145+
Prefix string
146+
}
147+
148+
func (fs *AssetFS) Open(name string) (http.File, error) {
149+
log.Printf("Looking for (pre): %v",name)
150+
name = path.Join(fs.Prefix, name)
151+
log.Printf("Looking for (post): %v",name)
152+
if len(name) > 0 && name[0] == '/' {
153+
name = name[1:]
154+
}
155+
if b, err := fs.Asset(name); err == nil {
156+
timestamp := defaultFileTimestamp
157+
if fs.AssetInfo != nil {
158+
if info, err := fs.AssetInfo(name); err == nil {
159+
timestamp = info.ModTime()
160+
}
161+
}
162+
return NewAssetFile(name, b, timestamp), nil
163+
}
164+
if children, err := fs.AssetDir(name); err == nil {
165+
return NewAssetDirectory(name, children, fs), nil
166+
} else {
167+
// If the error is not found, return an error that will
168+
// result in a 404 error. Otherwise the server returns
169+
// a 500 error for files not found.
170+
if strings.Contains(err.Error(), "not found") {
171+
return nil, os.ErrNotExist
172+
}
173+
return nil, err
174+
}
175+
}
176+
177+
func AssetFileSystem() *assetfs.AssetFS {
178+
assetInfo := func(path string) (os.FileInfo, error) {
179+
return os.Stat(path)
180+
}
181+
for k := range _bintree.Children {
182+
return &assetfs.AssetFS{Asset: Asset, AssetDir: AssetDir, AssetInfo: assetInfo, Prefix: k}
183+
}
184+
panic("unreachable")
185+
}

0 commit comments

Comments
 (0)