fix(docker): add dockfile and small fixes (#38)

* fix(docker): add dockfile and small fixes

* chore(readme): small fixes
This commit is contained in:
Hexxa 2021-02-01 21:36:56 +08:00 committed by GitHub
parent c8a3f911e8
commit b0d1cdccfc
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
11 changed files with 126 additions and 36 deletions

16
Dockerfile Normal file
View file

@ -0,0 +1,16 @@
FROM golang:1.15 as build-be
ADD . /quickshare
WORKDIR /quickshare
RUN /quickshare/scripts/build_be_docker.sh
FROM node as build-fe
COPY --from=build-be /quickshare /quickshare
WORKDIR /quickshare
RUN yarn install \
&& yarn --cwd "src/client/web" run build \
&& cp -R /quickshare/public /quickshare/dist/quickshare
FROM gcr.io/distroless/base-debian10
COPY --from=build-fe /quickshare/dist/quickshare /quickshare
ADD configs/docker.yml /quickshare
CMD ["/quickshare/start", "-c", "/quickshare/docker.yml"]

View file

@ -2,7 +2,7 @@
Quickshare
</h1>
<p align="center">
Simple file sharing service built with Go/Golang, Typescript, Gin, React, Boltdb, etc.
Quick and simple file sharing between different devices.
</p>
<p align="center">
<a href="https://github.com/ihexxa/quickshare/actions">
@ -24,26 +24,55 @@ Choose Language: English | [简体中文](./docs/README_zh-cn.md)
## Main Features
- Sharing files among different devices (Adaptive UI)
- Sharing and accessing from different devices (Adaptive UI)
- Be compatible with Linux, Mac and Windows
- Stopping and resuming uploading/downloading
- Do uploading and downloading in web browser
- Manage files in browser or in OS
## Quick Start
**Downloading**: Download last distribution(s) in [Release Page](https://github.com/ihexxa/quickshare/releases).
### Run in Docker
**Unzipping**: Unzip it and run following command `./quickshare`. (You may update its execution permission: e.g. run `chmod u+x quickshare` on Linux)
Following will start a `quickshare` docker and listen to `8686` port.
**Starting**: At the first run, Quickshare will let you input your user name and generate a random password for you (here `quickshare` is the user name). It may output something like following (password is `2fdc98`):
Then you can open `http://127.0.0.1:8686` and log in with user name `qs` and password `1234`:
```
Please input admin name: quickshare
password is generated: 2fdc98, please update it after login
user (quickshare) is created
docker run \
--name quickshare \
-d -p :8686:8686 \
-v `pwd`/quickshare/root:/quickshare/root \
-e DEFAULTADMIN=qs \
-e DEFAULTADMINPWD=1234 \
hexxa/quickshare:0.3.0
```
**Accessing**: At last, open your browser and visit `http://127.0.0.1:8686`.
- `DEFAULTADMIN` is the default user name
- `DEFAULTADMINPWD` is the default user password
- `/quickshare/root` is where Quickshare stores files and directories.
### Run from source code
Before start, please ensure Go/Golang (>1.15), Node.js and Yarn are installed on your machine.
```
# clone this repo
git clone git@github.com:ihexxa/quickshare.git
# go to repo's folder
cd quickshare
DEFAULTADMIN=qs DEFAULTADMINPWD=1234 yarn start
```
OK! Open `http://127.0.0.1:8686` in browser, and log in with user name `qs` and password `1234`.
### Run executable file
- **Downloading**: Download last distribution(s) in [Release Page](https://github.com/ihexxa/quickshare/releases).
- **Unzipping**: Unzip it and run following command `DEFAULTADMIN=qs DEFAULTADMINPWD=1234 ./quickshare`. (You may update its execution permission: e.g. run `chmod u+x quickshare`)
- **Accessing**: At last, open `http://127.0.0.1:8686` in browser, and log in with user name `qs` and password `1234`.
### FAQ

View file

@ -31,11 +31,14 @@ func main() {
if err != nil {
panic(err)
}
if len(opts.Configs) > 0 {
for _, configPath := range opts.Configs {
if strings.HasSuffix(configPath, ".yml") || strings.HasSuffix(configPath, ".yaml") {
fmt.Printf("launching config: %s\n", configPath)
cfg, err = cfg.Load(gocfg.YAML(configPath))
} else if strings.HasSuffix(configPath, ".json") {
fmt.Printf("launching config: %s\n", configPath)
cfg, err = cfg.Load(gocfg.JSON(configPath))
} else {
panic(fmt.Sprintf("unknown config file type (.yml .yaml .json are supported): %s", configPath))
@ -62,6 +65,7 @@ func main() {
panic(err)
}
fmt.Printf("quickshare is listening %d\n", cfg.GrabInt("Server.Port"))
err = srv.Start()
if err != nil {
panic(err)

21
configs/docker.yml Normal file
View file

@ -0,0 +1,21 @@
fs:
root: "/quickshare/root"
opensLimit: 128
openTTL: 60 # 1 min
secrets:
tokenSecret: ""
server:
debug: false
host: "0.0.0.0"
port: 8686
readTimeout: 2000
writerTimeout: 86400000 # 1 day
maxHeaderBytes: 512
publicPath: "/quickshare/public"
users:
enableAuth: true
defaultAdmin: ""
defaultAdminPwd: ""
cookieTTL: 604800 # 1 week
cookieSecure: false
cookieHttpOnly: true

View file

@ -4,7 +4,7 @@
"src/client/web"
],
"scripts": {
"build": "scripts/build",
"start": "go run cmd/start/main.go -c `pwd`/configs/dev.yml"
"build": "scripts/build.sh",
"start": "cd src/client/web/ && yarn && yarn build && cd ../../.. && go run cmd/start/main.go -c `pwd`/configs/dev.yml"
}
}

11
scripts/build_be_docker.sh Executable file
View file

@ -0,0 +1,11 @@
export QSROOT=`pwd`
rm -r dist && mkdir dist
# set this for builders behind GFW...
go env -w GOPROXY=https://goproxy.cn,direct
go get -d -v ./...
go get github.com/mitchellh/gox
cd cmd/start
gox \
-osarch="linux/amd64" \
-output "$QSROOT/dist/quickshare/start"

7
scripts/docker_run.sh Normal file
View file

@ -0,0 +1,7 @@
docker run \
--name quickshare \
-d -p :8686:8686 \
-v `pwd`/quickshare/root:/quickshare/root \
-e DEFAULTADMIN=qs \
-e DEFAULTADMINPWD=1234 \
hexxa/quickshare:0.3.0

View file

@ -4,7 +4,8 @@
"description": "web client for quickshare",
"main": "",
"scripts": {
"build": "yarn prod:addjs && webpack --config webpack.app.prod.js",
"build": "yarn prod:addjs && yarn build:prod:wp",
"build:prod:wp": "webpack --config webpack.app.prod.js",
"build:watch": "webpack --config webpack.app.prod.js --watch",
"build:dev": "yarn dev:addjs && webpack --config webpack.app.dev.js --watch",
"test": "jest test --maxWorkers=2",

View file

@ -46,6 +46,7 @@ type FileHandlers struct {
func NewFileHandlers(cfg gocfg.ICfg, deps *depidx.Deps) (*FileHandlers, error) {
var err error
if err = deps.FS().MkdirAll(UploadDir); err != nil {
return nil, err
}
@ -113,7 +114,7 @@ func (h *FileHandlers) Create(c *gin.Context) {
}
userName := c.MustGet(singleuserhdr.UserParam).(string)
tmpFilePath := getTmpPath(req.Path)
tmpFilePath := h.getTmpPath(req.Path)
locker := h.NewAutoLocker(c, lockName(userName, tmpFilePath))
locker.Exec(func() {
err := h.deps.FS().Create(tmpFilePath)
@ -261,7 +262,7 @@ func (h *FileHandlers) UploadChunk(c *gin.Context) {
}
userName := c.MustGet(singleuserhdr.UserParam).(string)
tmpFilePath := getTmpPath(req.Path)
tmpFilePath := h.getTmpPath(req.Path)
locker := h.NewAutoLocker(c, lockName(userName, tmpFilePath))
locker.Exec(func() {
var err error
@ -331,7 +332,7 @@ func (h *FileHandlers) UploadStatus(c *gin.Context) {
}
userName := c.MustGet(singleuserhdr.UserParam).(string)
tmpFilePath := getTmpPath(filePath)
tmpFilePath := h.getTmpPath(filePath)
locker := h.NewAutoLocker(c, lockName(userName, tmpFilePath))
locker.Exec(func() {
_, fileSize, uploaded, err := h.uploadMgr.GetInfo(userName, tmpFilePath)
@ -468,7 +469,7 @@ func (h *FileHandlers) CopyDir(c *gin.Context) {
c.JSON(q.NewMsgResp(501, "Not Implemented"))
}
func getTmpPath(filePath string) string {
func (h *FileHandlers) getTmpPath(filePath string) string {
return path.Join(UploadDir, fmt.Sprintf("%x", sha1.Sum([]byte(filePath))))
}
@ -504,7 +505,7 @@ func (h *FileHandlers) DelUploading(c *gin.Context) {
userName := c.MustGet(singleuserhdr.UserParam).(string)
var err error
tmpFilePath := getTmpPath(filePath)
tmpFilePath := h.getTmpPath(filePath)
locker := h.NewAutoLocker(c, lockName(userName, tmpFilePath))
locker.Exec(func() {
err = h.deps.FS().Remove(tmpFilePath)

View file

@ -9,33 +9,33 @@ type FSConfig struct {
}
type UsersCfg struct {
EnableAuth bool `json:"enableAuth"`
DefaultAdmin string `json:"defaultAdmin" cfg:"env"`
DefaultAdminPwd string `json:"defaultAdminPwd" cfg:"env"`
CookieTTL int `json:"cookieTTL"`
CookieSecure bool `json:"cookieSecure"`
CookieHttpOnly bool `json:"cookieHttpOnly"`
EnableAuth bool `json:"enableAuth" yaml:"enableAuth"`
DefaultAdmin string `json:"defaultAdmin" yaml:"defaultAdmin" cfg:"env"`
DefaultAdminPwd string `json:"defaultAdminPwd" yaml:"defaultAdminPwd" cfg:"env"`
CookieTTL int `json:"cookieTTL" yaml:"cookieTTL"`
CookieSecure bool `json:"cookieSecure" yaml:"cookieSecure"`
CookieHttpOnly bool `json:"cookieHttpOnly" yaml:"cookieHttpOnly"`
}
type Secrets struct {
TokenSecret string `json:"tokenSecret" cfg:"env"`
TokenSecret string `json:"tokenSecret" yaml:"tokenSecret" cfg:"env"`
}
type ServerCfg struct {
Debug bool `json:"debug"`
Host string `json:"host"`
Port int `json:"port"`
ReadTimeout int `json:"readTimeout"`
WriteTimeout int `json:"writeTimeout"`
MaxHeaderBytes int `json:"maxHeaderBytes"`
PublicPath string `json:"publicPath"`
Debug bool `json:"debug" yaml:"debug"`
Host string `json:"host" yaml:"host"`
Port int `json:"port" yaml:"port"`
ReadTimeout int `json:"readTimeout" yaml:"readTimeout"`
WriteTimeout int `json:"writeTimeout" yaml:"writeTimeout"`
MaxHeaderBytes int `json:"maxHeaderBytes" yaml:"maxHeaderBytes"`
PublicPath string `json:"publicPath" yaml:"publicPath"`
}
type Config struct {
Fs *FSConfig `json:"fs"`
Secrets *Secrets `json:"secrets"`
Server *ServerCfg `json:"server"`
Users *UsersCfg `json:"users"`
Fs *FSConfig `json:"fs" yaml:"fs"`
Secrets *Secrets `json:"secrets" yaml:"secrets"`
Server *ServerCfg `json:"server" yaml:"server"`
Users *UsersCfg `json:"users" yaml:"users"`
}
func NewConfig() *Config {
@ -45,7 +45,7 @@ func NewConfig() *Config {
func DefaultConfig() (string, error) {
defaultCfg := &Config{
Fs: &FSConfig{
Root: ".",
Root: "root",
OpensLimit: 128,
OpenTTL: 60, // 1 min
},