For now, chown the server directory when the server starts
This commit is contained in:
parent
e95c22a526
commit
7a52e3a9c2
|
@ -53,7 +53,7 @@ func NewDockerEnvironment(opts ...func(*DockerEnvironment)) (*DockerEnvironment,
|
|||
}
|
||||
|
||||
env := &DockerEnvironment{
|
||||
User: 1000,
|
||||
User: 1000,
|
||||
Client: cli,
|
||||
}
|
||||
|
||||
|
@ -131,6 +131,14 @@ func (d *DockerEnvironment) Start() error {
|
|||
opts := types.ContainerStartOptions{}
|
||||
|
||||
d.Server.Emit(StatusEvent, ProcessStartingState)
|
||||
|
||||
// Reset the permissions on files for the server before actually trying
|
||||
// to start it.
|
||||
if err := d.Server.Filesystem.Chown("/"); err != nil {
|
||||
d.Server.Emit(StatusEvent, ProcessOfflineState)
|
||||
return err
|
||||
}
|
||||
|
||||
if err := d.Client.ContainerStart(context.Background(), d.Server.Uuid, opts); err != nil {
|
||||
d.Server.Emit(StatusEvent, ProcessOfflineState)
|
||||
return err
|
||||
|
@ -179,7 +187,7 @@ func (d *DockerEnvironment) Attach() error {
|
|||
|
||||
var err error
|
||||
d.stream, err = d.Client.ContainerAttach(ctx, d.Server.Uuid, types.ContainerAttachOptions{
|
||||
Stdin: true,
|
||||
Stdin: true,
|
||||
Stdout: true,
|
||||
Stderr: true,
|
||||
Stream: true,
|
||||
|
@ -416,7 +424,7 @@ func (d *DockerEnvironment) Readlog(len int64) ([]string, error) {
|
|||
}
|
||||
|
||||
type dockerLogLine struct {
|
||||
Log string `json:"log"`
|
||||
Log string `json:"log"`
|
||||
}
|
||||
|
||||
// Docker stores the logs for server output in a JSON format. This function will iterate over the JSON
|
||||
|
@ -513,4 +521,4 @@ func (d *DockerEnvironment) exposedPorts() nat.PortSet {
|
|||
}
|
||||
|
||||
return out
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,6 +6,7 @@ import (
|
|||
"errors"
|
||||
"fmt"
|
||||
"github.com/gabriel-vasile/mimetype"
|
||||
"github.com/pterodactyl/wings/config"
|
||||
"go.uber.org/zap"
|
||||
"io"
|
||||
"io/ioutil"
|
||||
|
@ -23,17 +24,15 @@ import (
|
|||
var InvalidPathResolution = errors.New("invalid path resolution")
|
||||
|
||||
type Filesystem struct {
|
||||
// The root directory where all of the server data is contained. By default
|
||||
// this is going to be /srv/daemon-data but can vary depending on the system.
|
||||
Root string
|
||||
|
||||
// The server object associated with this Filesystem.
|
||||
Server *Server
|
||||
|
||||
Configuration *config.SystemConfiguration
|
||||
}
|
||||
|
||||
// Returns the root path that contains all of a server's data.
|
||||
func (fs *Filesystem) Path() string {
|
||||
return filepath.Join(fs.Root, fs.Server.Uuid)
|
||||
return filepath.Join(fs.Configuration.Data, fs.Server.Uuid)
|
||||
}
|
||||
|
||||
// Normalizes a directory being passed in to ensure the user is not able to escape
|
||||
|
@ -47,7 +46,10 @@ func (fs *Filesystem) SafePath(p string) (string, error) {
|
|||
|
||||
// Calling filpath.Clean on the joined directory will resolve it to the absolute path,
|
||||
// removing any ../ type of resolution arguments, and leaving us with a direct path link.
|
||||
r := filepath.Clean(filepath.Join(fs.Path(), p))
|
||||
//
|
||||
// This will also trim the existing root path off the beginning of the path passed to
|
||||
// the function since that can get a bit messy.
|
||||
r := filepath.Clean(filepath.Join(fs.Path(), strings.TrimPrefix(p, fs.Path())))
|
||||
|
||||
// At the same time, evaluate the symlink status and determine where this file or folder
|
||||
// is truly pointing to.
|
||||
|
@ -278,6 +280,57 @@ func (fs *Filesystem) Rename(from string, to string) error {
|
|||
return os.Rename(cleanedFrom, cleanedTo)
|
||||
}
|
||||
|
||||
// Recursively iterates over a directory and sets the permissions on all of the
|
||||
// underlying files.
|
||||
func (fs *Filesystem) Chown(path string) error {
|
||||
cleaned, err := fs.SafePath(path)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if s, err := os.Stat(cleaned); err != nil {
|
||||
return err
|
||||
} else if !s.IsDir() {
|
||||
return os.Chown(cleaned, fs.Configuration.User.Uid, fs.Configuration.User.Gid)
|
||||
}
|
||||
|
||||
return fs.chownDirectory(cleaned)
|
||||
}
|
||||
|
||||
// Iterate over all of the files and directories. If it is a file just go ahead and perform
|
||||
// the chown operation. Otherwise dig deeper into the directory until we've run out of
|
||||
// directories to dig into.
|
||||
func (fs *Filesystem) chownDirectory(path string) error {
|
||||
var wg sync.WaitGroup
|
||||
|
||||
cleaned, err := fs.SafePath(path)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
files, err := ioutil.ReadDir(cleaned)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
for _, f := range files {
|
||||
if f.IsDir() {
|
||||
wg.Add(1)
|
||||
|
||||
go func(p string) {
|
||||
defer wg.Done()
|
||||
fs.chownDirectory(p)
|
||||
}(filepath.Join(cleaned, f.Name()))
|
||||
} else {
|
||||
os.Chown(filepath.Join(cleaned, f.Name()), fs.Configuration.User.Uid, fs.Configuration.User.Gid)
|
||||
}
|
||||
}
|
||||
|
||||
wg.Wait()
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// Copies a given file to the same location and appends a suffix to the file to indicate that
|
||||
// it has been copied.
|
||||
//
|
||||
|
|
|
@ -200,7 +200,7 @@ func FromConfiguration(data []byte, cfg *config.SystemConfiguration) (*Server, e
|
|||
s.Environment = env
|
||||
s.Cache = cache.New(time.Minute*10, time.Minute*15)
|
||||
s.Filesystem = &Filesystem{
|
||||
Root: cfg.Data,
|
||||
Configuration: cfg,
|
||||
Server: s,
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue
Block a user