Cleanup related to context refactor (#9988)
Этот коммит содержится в:
коммит произвёл
GitHub
родитель
829f183bb0
Коммит
8429add371
@@ -24,6 +24,7 @@ import (
|
||||
"github.com/mattermost/mattermost-server/einterfaces"
|
||||
"github.com/mattermost/mattermost-server/mlog"
|
||||
"github.com/mattermost/mattermost-server/model"
|
||||
"github.com/mattermost/mattermost-server/utils/fileutils"
|
||||
"github.com/mattermost/mattermost-server/utils/jsonutils"
|
||||
)
|
||||
|
||||
@@ -33,13 +34,6 @@ const (
|
||||
)
|
||||
|
||||
var (
|
||||
commonBaseSearchPaths = []string{
|
||||
".",
|
||||
"..",
|
||||
"../..",
|
||||
"../../..",
|
||||
}
|
||||
|
||||
termsOfServiceEnabledAndEmpty = model.NewAppError(
|
||||
"Config.IsValid",
|
||||
"model.config.is_valid.support.custom_terms_of_service_text.app_error",
|
||||
@@ -49,87 +43,6 @@ var (
|
||||
)
|
||||
)
|
||||
|
||||
func FindPath(path string, baseSearchPaths []string, filter func(os.FileInfo) bool) string {
|
||||
if filepath.IsAbs(path) {
|
||||
if _, err := os.Stat(path); err == nil {
|
||||
return path
|
||||
}
|
||||
|
||||
return ""
|
||||
}
|
||||
|
||||
searchPaths := []string{}
|
||||
searchPaths = append(searchPaths, baseSearchPaths...)
|
||||
|
||||
// Additionally attempt to search relative to the location of the running binary.
|
||||
var binaryDir string
|
||||
if exe, err := os.Executable(); err == nil {
|
||||
if exe, err = filepath.EvalSymlinks(exe); err == nil {
|
||||
if exe, err = filepath.Abs(exe); err == nil {
|
||||
binaryDir = filepath.Dir(exe)
|
||||
}
|
||||
}
|
||||
}
|
||||
if binaryDir != "" {
|
||||
for _, baseSearchPath := range baseSearchPaths {
|
||||
searchPaths = append(
|
||||
searchPaths,
|
||||
filepath.Join(binaryDir, baseSearchPath),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
for _, parent := range searchPaths {
|
||||
found, err := filepath.Abs(filepath.Join(parent, path))
|
||||
if err != nil {
|
||||
continue
|
||||
} else if fileInfo, err := os.Stat(found); err == nil {
|
||||
if filter != nil {
|
||||
if filter(fileInfo) {
|
||||
return found
|
||||
}
|
||||
} else {
|
||||
return found
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return ""
|
||||
}
|
||||
|
||||
// FindConfigFile attempts to find an existing configuration file. fileName can be an absolute or
|
||||
// relative path or name such as "/opt/mattermost/config.json" or simply "config.json". An empty
|
||||
// string is returned if no configuration is found.
|
||||
func FindConfigFile(fileName string) (path string) {
|
||||
found := FindFile(filepath.Join("config", fileName))
|
||||
if found == "" {
|
||||
found = FindPath(fileName, []string{"."}, nil)
|
||||
}
|
||||
|
||||
return found
|
||||
}
|
||||
|
||||
// FindFile looks for the given file in nearby ancestors relative to the current working
|
||||
// directory as well as the directory of the executable.
|
||||
func FindFile(path string) string {
|
||||
return FindPath(path, commonBaseSearchPaths, func(fileInfo os.FileInfo) bool {
|
||||
return !fileInfo.IsDir()
|
||||
})
|
||||
}
|
||||
|
||||
// FindDir looks for the given directory in nearby ancestors relative to the current working
|
||||
// directory as well as the directory of the executable, falling back to `./` if not found.
|
||||
func FindDir(dir string) (string, bool) {
|
||||
found := FindPath(dir, commonBaseSearchPaths, func(fileInfo os.FileInfo) bool {
|
||||
return fileInfo.IsDir()
|
||||
})
|
||||
if found == "" {
|
||||
return "./", false
|
||||
}
|
||||
|
||||
return found, true
|
||||
}
|
||||
|
||||
func MloggerConfigFromLoggerConfig(s *model.LogSettings) *mlog.LoggerConfiguration {
|
||||
return &mlog.LoggerConfiguration{
|
||||
EnableConsole: s.EnableConsole,
|
||||
@@ -154,7 +67,7 @@ func EnableDebugLogForTest() {
|
||||
|
||||
func GetLogFileLocation(fileLocation string) string {
|
||||
if fileLocation == "" {
|
||||
fileLocation, _ = FindDir("logs")
|
||||
fileLocation, _ = fileutils.FindDir("logs")
|
||||
}
|
||||
|
||||
return filepath.Join(fileLocation, LOG_FILENAME)
|
||||
@@ -432,10 +345,10 @@ func ReadConfigFile(path string, allowEnvironmentOverrides bool) (*model.Config,
|
||||
// it will attempt to locate a default config file, and copy it to a file named fileName in the same
|
||||
// directory. In either case, the config file path is returned.
|
||||
func EnsureConfigFile(fileName string) (string, error) {
|
||||
if configFile := FindConfigFile(fileName); configFile != "" {
|
||||
if configFile := fileutils.FindConfigFile(fileName); configFile != "" {
|
||||
return configFile, nil
|
||||
}
|
||||
if defaultPath := FindConfigFile("default.json"); defaultPath != "" {
|
||||
if defaultPath := fileutils.FindConfigFile("default.json"); defaultPath != "" {
|
||||
destPath := filepath.Join(filepath.Dir(defaultPath), fileName)
|
||||
src, err := os.Open(defaultPath)
|
||||
if err != nil {
|
||||
|
||||
@@ -6,9 +6,7 @@ package utils
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
"io/ioutil"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
"testing"
|
||||
|
||||
@@ -112,293 +110,6 @@ func TestReadConfig_PluginSettings(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestTimezoneConfig(t *testing.T) {
|
||||
TranslationsPreInit()
|
||||
supportedTimezones := LoadTimezones("timezones.json")
|
||||
assert.Equal(t, len(supportedTimezones) > 0, true)
|
||||
|
||||
supportedTimezones2 := LoadTimezones("timezones_file_does_not_exists.json")
|
||||
assert.Equal(t, len(supportedTimezones2) > 0, true)
|
||||
}
|
||||
|
||||
func TestFindConfigFile(t *testing.T) {
|
||||
t.Run("config.json in current working directory, not inside config/", func(t *testing.T) {
|
||||
// Force a unique working directory
|
||||
cwd, err := ioutil.TempDir("", "")
|
||||
require.NoError(t, err)
|
||||
defer os.RemoveAll(cwd)
|
||||
|
||||
prevDir, err := os.Getwd()
|
||||
require.NoError(t, err)
|
||||
defer os.Chdir(prevDir)
|
||||
os.Chdir(cwd)
|
||||
|
||||
configJson, err := filepath.Abs("config.json")
|
||||
require.NoError(t, err)
|
||||
require.NoError(t, ioutil.WriteFile(configJson, []byte("{}"), 0600))
|
||||
|
||||
// Relative paths end up getting symlinks fully resolved.
|
||||
configJsonResolved, err := filepath.EvalSymlinks(configJson)
|
||||
require.NoError(t, err)
|
||||
|
||||
assert.Equal(t, configJsonResolved, FindConfigFile("config.json"))
|
||||
})
|
||||
|
||||
t.Run("config/config.json from various paths", func(t *testing.T) {
|
||||
// Create the following directory structure:
|
||||
// tmpDir1/
|
||||
// config/
|
||||
// config.json
|
||||
// tmpDir2/
|
||||
// tmpDir3/
|
||||
// tmpDir4/
|
||||
// tmpDir5/
|
||||
tmpDir1, err := ioutil.TempDir("", "")
|
||||
require.NoError(t, err)
|
||||
defer os.RemoveAll(tmpDir1)
|
||||
|
||||
err = os.Mkdir(filepath.Join(tmpDir1, "config"), 0700)
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir2, err := ioutil.TempDir(tmpDir1, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir3, err := ioutil.TempDir(tmpDir2, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir4, err := ioutil.TempDir(tmpDir3, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir5, err := ioutil.TempDir(tmpDir4, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
configJson := filepath.Join(tmpDir1, "config", "config.json")
|
||||
require.NoError(t, ioutil.WriteFile(configJson, []byte("{}"), 0600))
|
||||
|
||||
// Relative paths end up getting symlinks fully resolved, so use this below as necessary.
|
||||
configJsonResolved, err := filepath.EvalSymlinks(configJson)
|
||||
require.NoError(t, err)
|
||||
|
||||
testCases := []struct {
|
||||
Description string
|
||||
Cwd *string
|
||||
FileName string
|
||||
Expected string
|
||||
}{
|
||||
{
|
||||
"absolute path to config.json",
|
||||
nil,
|
||||
configJson,
|
||||
configJson,
|
||||
},
|
||||
{
|
||||
"absolute path to config.json from directory containing config.json",
|
||||
&tmpDir1,
|
||||
configJson,
|
||||
configJson,
|
||||
},
|
||||
{
|
||||
"relative path to config.json from directory containing config.json",
|
||||
&tmpDir1,
|
||||
"config.json",
|
||||
configJsonResolved,
|
||||
},
|
||||
{
|
||||
"subdirectory of directory containing config.json",
|
||||
&tmpDir2,
|
||||
"config.json",
|
||||
configJsonResolved,
|
||||
},
|
||||
{
|
||||
"twice-nested subdirectory of directory containing config.json",
|
||||
&tmpDir3,
|
||||
"config.json",
|
||||
configJsonResolved,
|
||||
},
|
||||
{
|
||||
"thrice-nested subdirectory of directory containing config.json",
|
||||
&tmpDir4,
|
||||
"config.json",
|
||||
configJsonResolved,
|
||||
},
|
||||
{
|
||||
"can't find from four nesting levels deep",
|
||||
&tmpDir5,
|
||||
"config.json",
|
||||
"",
|
||||
},
|
||||
}
|
||||
|
||||
for _, testCase := range testCases {
|
||||
t.Run(testCase.Description, func(t *testing.T) {
|
||||
if testCase.Cwd != nil {
|
||||
prevDir, err := os.Getwd()
|
||||
require.NoError(t, err)
|
||||
defer os.Chdir(prevDir)
|
||||
os.Chdir(*testCase.Cwd)
|
||||
}
|
||||
|
||||
assert.Equal(t, testCase.Expected, FindConfigFile(testCase.FileName))
|
||||
})
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("config/config.json relative to executable", func(t *testing.T) {
|
||||
osExecutable, err := os.Executable()
|
||||
require.NoError(t, err)
|
||||
osExecutableDir := filepath.Dir(osExecutable)
|
||||
|
||||
// Force a working directory different than the executable.
|
||||
cwd, err := ioutil.TempDir("", "")
|
||||
require.NoError(t, err)
|
||||
defer os.RemoveAll(cwd)
|
||||
|
||||
prevDir, err := os.Getwd()
|
||||
require.NoError(t, err)
|
||||
defer os.Chdir(prevDir)
|
||||
os.Chdir(cwd)
|
||||
|
||||
testCases := []struct {
|
||||
Description string
|
||||
RelativePath string
|
||||
}{
|
||||
{
|
||||
"config/config.json",
|
||||
".",
|
||||
},
|
||||
{
|
||||
"../config/config.json",
|
||||
"../",
|
||||
},
|
||||
}
|
||||
|
||||
for _, testCase := range testCases {
|
||||
t.Run(testCase.Description, func(t *testing.T) {
|
||||
// Install the config in config/config.json relative to the executable
|
||||
configJson := filepath.Join(osExecutableDir, testCase.RelativePath, "config", "config.json")
|
||||
require.NoError(t, os.Mkdir(filepath.Dir(configJson), 0700))
|
||||
require.NoError(t, ioutil.WriteFile(configJson, []byte("{}"), 0600))
|
||||
defer os.RemoveAll(filepath.Dir(configJson))
|
||||
|
||||
// Relative paths end up getting symlinks fully resolved.
|
||||
configJsonResolved, err := filepath.EvalSymlinks(configJson)
|
||||
require.NoError(t, err)
|
||||
|
||||
assert.Equal(t, configJsonResolved, FindConfigFile("config.json"))
|
||||
})
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
func TestFindFile(t *testing.T) {
|
||||
t.Run("files from various paths", func(t *testing.T) {
|
||||
// Create the following directory structure:
|
||||
// tmpDir1/
|
||||
// file1.json
|
||||
// file2.xml
|
||||
// other.txt
|
||||
// tmpDir2/
|
||||
// other.txt/ [directory]
|
||||
// tmpDir3/
|
||||
// tmpDir4/
|
||||
// tmpDir5/
|
||||
tmpDir1, err := ioutil.TempDir("", "")
|
||||
require.NoError(t, err)
|
||||
defer os.RemoveAll(tmpDir1)
|
||||
|
||||
tmpDir2, err := ioutil.TempDir(tmpDir1, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
err = os.Mkdir(filepath.Join(tmpDir2, "other.txt"), 0700)
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir3, err := ioutil.TempDir(tmpDir2, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir4, err := ioutil.TempDir(tmpDir3, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir5, err := ioutil.TempDir(tmpDir4, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
type testCase struct {
|
||||
Description string
|
||||
Cwd *string
|
||||
FileName string
|
||||
Expected string
|
||||
}
|
||||
|
||||
testCases := []testCase{}
|
||||
|
||||
for _, fileName := range []string{"file1.json", "file2.xml", "other.txt"} {
|
||||
filePath := filepath.Join(tmpDir1, fileName)
|
||||
require.NoError(t, ioutil.WriteFile(filePath, []byte("{}"), 0600))
|
||||
|
||||
// Relative paths end up getting symlinks fully resolved, so use this below as necessary.
|
||||
filePathResolved, err := filepath.EvalSymlinks(filePath)
|
||||
require.NoError(t, err)
|
||||
|
||||
testCases = append(testCases, []testCase{
|
||||
{
|
||||
fmt.Sprintf("absolute path to %s", fileName),
|
||||
nil,
|
||||
filePath,
|
||||
filePath,
|
||||
},
|
||||
{
|
||||
fmt.Sprintf("absolute path to %s from containing directory", fileName),
|
||||
&tmpDir1,
|
||||
filePath,
|
||||
filePath,
|
||||
},
|
||||
{
|
||||
fmt.Sprintf("relative path to %s from containing directory", fileName),
|
||||
&tmpDir1,
|
||||
fileName,
|
||||
filePathResolved,
|
||||
},
|
||||
{
|
||||
fmt.Sprintf("%s: subdirectory of containing directory", fileName),
|
||||
&tmpDir2,
|
||||
fileName,
|
||||
filePathResolved,
|
||||
},
|
||||
{
|
||||
fmt.Sprintf("%s: twice-nested subdirectory of containing directory", fileName),
|
||||
&tmpDir3,
|
||||
fileName,
|
||||
filePathResolved,
|
||||
},
|
||||
{
|
||||
fmt.Sprintf("%s: thrice-nested subdirectory of containing directory", fileName),
|
||||
&tmpDir4,
|
||||
fileName,
|
||||
filePathResolved,
|
||||
},
|
||||
{
|
||||
fmt.Sprintf("%s: can't find from four nesting levels deep", fileName),
|
||||
&tmpDir5,
|
||||
fileName,
|
||||
"",
|
||||
},
|
||||
}...)
|
||||
}
|
||||
|
||||
for _, testCase := range testCases {
|
||||
t.Run(testCase.Description, func(t *testing.T) {
|
||||
if testCase.Cwd != nil {
|
||||
prevDir, err := os.Getwd()
|
||||
require.NoError(t, err)
|
||||
defer os.Chdir(prevDir)
|
||||
os.Chdir(*testCase.Cwd)
|
||||
}
|
||||
|
||||
assert.Equal(t, testCase.Expected, FindFile(testCase.FileName))
|
||||
})
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
func TestConfigFromEnviroVars(t *testing.T) {
|
||||
TranslationsPreInit()
|
||||
|
||||
|
||||
99
utils/fileutils/fileutils.go
Обычный файл
99
utils/fileutils/fileutils.go
Обычный файл
@@ -0,0 +1,99 @@
|
||||
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
|
||||
// See License.txt for license information.
|
||||
|
||||
package fileutils
|
||||
|
||||
import (
|
||||
"os"
|
||||
"path/filepath"
|
||||
)
|
||||
|
||||
var (
|
||||
commonBaseSearchPaths = []string{
|
||||
".",
|
||||
"..",
|
||||
"../..",
|
||||
"../../..",
|
||||
}
|
||||
)
|
||||
|
||||
func FindPath(path string, baseSearchPaths []string, filter func(os.FileInfo) bool) string {
|
||||
if filepath.IsAbs(path) {
|
||||
if _, err := os.Stat(path); err == nil {
|
||||
return path
|
||||
}
|
||||
|
||||
return ""
|
||||
}
|
||||
|
||||
searchPaths := []string{}
|
||||
searchPaths = append(searchPaths, baseSearchPaths...)
|
||||
|
||||
// Additionally attempt to search relative to the location of the running binary.
|
||||
var binaryDir string
|
||||
if exe, err := os.Executable(); err == nil {
|
||||
if exe, err = filepath.EvalSymlinks(exe); err == nil {
|
||||
if exe, err = filepath.Abs(exe); err == nil {
|
||||
binaryDir = filepath.Dir(exe)
|
||||
}
|
||||
}
|
||||
}
|
||||
if binaryDir != "" {
|
||||
for _, baseSearchPath := range baseSearchPaths {
|
||||
searchPaths = append(
|
||||
searchPaths,
|
||||
filepath.Join(binaryDir, baseSearchPath),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
for _, parent := range searchPaths {
|
||||
found, err := filepath.Abs(filepath.Join(parent, path))
|
||||
if err != nil {
|
||||
continue
|
||||
} else if fileInfo, err := os.Stat(found); err == nil {
|
||||
if filter != nil {
|
||||
if filter(fileInfo) {
|
||||
return found
|
||||
}
|
||||
} else {
|
||||
return found
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return ""
|
||||
}
|
||||
|
||||
// FindFile looks for the given file in nearby ancestors relative to the current working
|
||||
// directory as well as the directory of the executable.
|
||||
func FindFile(path string) string {
|
||||
return FindPath(path, commonBaseSearchPaths, func(fileInfo os.FileInfo) bool {
|
||||
return !fileInfo.IsDir()
|
||||
})
|
||||
}
|
||||
|
||||
// fileutils.FindDir looks for the given directory in nearby ancestors relative to the current working
|
||||
// directory as well as the directory of the executable, falling back to `./` if not found.
|
||||
func FindDir(dir string) (string, bool) {
|
||||
found := FindPath(dir, commonBaseSearchPaths, func(fileInfo os.FileInfo) bool {
|
||||
return fileInfo.IsDir()
|
||||
})
|
||||
if found == "" {
|
||||
return "./", false
|
||||
}
|
||||
|
||||
return found, true
|
||||
}
|
||||
|
||||
// FindConfigFile attempts to find an existing configuration file. fileName can be an absolute or
|
||||
// relative path or name such as "/opt/mattermost/config.json" or simply "config.json". An empty
|
||||
// string is returned if no configuration is found.
|
||||
func FindConfigFile(fileName string) (path string) {
|
||||
found := FindFile(filepath.Join("config", fileName))
|
||||
if found == "" {
|
||||
found = FindPath(fileName, []string{"."}, nil)
|
||||
}
|
||||
|
||||
return found
|
||||
}
|
||||
293
utils/fileutils/fileutils_test.go
Обычный файл
293
utils/fileutils/fileutils_test.go
Обычный файл
@@ -0,0 +1,293 @@
|
||||
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
|
||||
// See License.txt for license information.
|
||||
|
||||
package fileutils
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"io/ioutil"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"testing"
|
||||
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
)
|
||||
|
||||
func TestFindConfigFile(t *testing.T) {
|
||||
t.Run("config.json in current working directory, not inside config/", func(t *testing.T) {
|
||||
// Force a unique working directory
|
||||
cwd, err := ioutil.TempDir("", "")
|
||||
require.NoError(t, err)
|
||||
defer os.RemoveAll(cwd)
|
||||
|
||||
prevDir, err := os.Getwd()
|
||||
require.NoError(t, err)
|
||||
defer os.Chdir(prevDir)
|
||||
os.Chdir(cwd)
|
||||
|
||||
configJson, err := filepath.Abs("config.json")
|
||||
require.NoError(t, err)
|
||||
require.NoError(t, ioutil.WriteFile(configJson, []byte("{}"), 0600))
|
||||
|
||||
// Relative paths end up getting symlinks fully resolved.
|
||||
configJsonResolved, err := filepath.EvalSymlinks(configJson)
|
||||
require.NoError(t, err)
|
||||
|
||||
assert.Equal(t, configJsonResolved, FindConfigFile("config.json"))
|
||||
})
|
||||
|
||||
t.Run("config/config.json from various paths", func(t *testing.T) {
|
||||
// Create the following directory structure:
|
||||
// tmpDir1/
|
||||
// config/
|
||||
// config.json
|
||||
// tmpDir2/
|
||||
// tmpDir3/
|
||||
// tmpDir4/
|
||||
// tmpDir5/
|
||||
tmpDir1, err := ioutil.TempDir("", "")
|
||||
require.NoError(t, err)
|
||||
defer os.RemoveAll(tmpDir1)
|
||||
|
||||
err = os.Mkdir(filepath.Join(tmpDir1, "config"), 0700)
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir2, err := ioutil.TempDir(tmpDir1, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir3, err := ioutil.TempDir(tmpDir2, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir4, err := ioutil.TempDir(tmpDir3, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir5, err := ioutil.TempDir(tmpDir4, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
configJson := filepath.Join(tmpDir1, "config", "config.json")
|
||||
require.NoError(t, ioutil.WriteFile(configJson, []byte("{}"), 0600))
|
||||
|
||||
// Relative paths end up getting symlinks fully resolved, so use this below as necessary.
|
||||
configJsonResolved, err := filepath.EvalSymlinks(configJson)
|
||||
require.NoError(t, err)
|
||||
|
||||
testCases := []struct {
|
||||
Description string
|
||||
Cwd *string
|
||||
FileName string
|
||||
Expected string
|
||||
}{
|
||||
{
|
||||
"absolute path to config.json",
|
||||
nil,
|
||||
configJson,
|
||||
configJson,
|
||||
},
|
||||
{
|
||||
"absolute path to config.json from directory containing config.json",
|
||||
&tmpDir1,
|
||||
configJson,
|
||||
configJson,
|
||||
},
|
||||
{
|
||||
"relative path to config.json from directory containing config.json",
|
||||
&tmpDir1,
|
||||
"config.json",
|
||||
configJsonResolved,
|
||||
},
|
||||
{
|
||||
"subdirectory of directory containing config.json",
|
||||
&tmpDir2,
|
||||
"config.json",
|
||||
configJsonResolved,
|
||||
},
|
||||
{
|
||||
"twice-nested subdirectory of directory containing config.json",
|
||||
&tmpDir3,
|
||||
"config.json",
|
||||
configJsonResolved,
|
||||
},
|
||||
{
|
||||
"thrice-nested subdirectory of directory containing config.json",
|
||||
&tmpDir4,
|
||||
"config.json",
|
||||
configJsonResolved,
|
||||
},
|
||||
{
|
||||
"can't find from four nesting levels deep",
|
||||
&tmpDir5,
|
||||
"config.json",
|
||||
"",
|
||||
},
|
||||
}
|
||||
|
||||
for _, testCase := range testCases {
|
||||
t.Run(testCase.Description, func(t *testing.T) {
|
||||
if testCase.Cwd != nil {
|
||||
prevDir, err := os.Getwd()
|
||||
require.NoError(t, err)
|
||||
defer os.Chdir(prevDir)
|
||||
os.Chdir(*testCase.Cwd)
|
||||
}
|
||||
|
||||
assert.Equal(t, testCase.Expected, FindConfigFile(testCase.FileName))
|
||||
})
|
||||
}
|
||||
})
|
||||
|
||||
t.Run("config/config.json relative to executable", func(t *testing.T) {
|
||||
osExecutable, err := os.Executable()
|
||||
require.NoError(t, err)
|
||||
osExecutableDir := filepath.Dir(osExecutable)
|
||||
|
||||
// Force a working directory different than the executable.
|
||||
cwd, err := ioutil.TempDir("", "")
|
||||
require.NoError(t, err)
|
||||
defer os.RemoveAll(cwd)
|
||||
|
||||
prevDir, err := os.Getwd()
|
||||
require.NoError(t, err)
|
||||
defer os.Chdir(prevDir)
|
||||
os.Chdir(cwd)
|
||||
|
||||
testCases := []struct {
|
||||
Description string
|
||||
RelativePath string
|
||||
}{
|
||||
{
|
||||
"config/config.json",
|
||||
".",
|
||||
},
|
||||
{
|
||||
"../config/config.json",
|
||||
"../",
|
||||
},
|
||||
}
|
||||
|
||||
for _, testCase := range testCases {
|
||||
t.Run(testCase.Description, func(t *testing.T) {
|
||||
// Install the config in config/config.json relative to the executable
|
||||
configJson := filepath.Join(osExecutableDir, testCase.RelativePath, "config", "config.json")
|
||||
require.NoError(t, os.Mkdir(filepath.Dir(configJson), 0700))
|
||||
require.NoError(t, ioutil.WriteFile(configJson, []byte("{}"), 0600))
|
||||
defer os.RemoveAll(filepath.Dir(configJson))
|
||||
|
||||
// Relative paths end up getting symlinks fully resolved.
|
||||
configJsonResolved, err := filepath.EvalSymlinks(configJson)
|
||||
require.NoError(t, err)
|
||||
|
||||
assert.Equal(t, configJsonResolved, FindConfigFile("config.json"))
|
||||
})
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
func TestFindFile(t *testing.T) {
|
||||
t.Run("files from various paths", func(t *testing.T) {
|
||||
// Create the following directory structure:
|
||||
// tmpDir1/
|
||||
// file1.json
|
||||
// file2.xml
|
||||
// other.txt
|
||||
// tmpDir2/
|
||||
// other.txt/ [directory]
|
||||
// tmpDir3/
|
||||
// tmpDir4/
|
||||
// tmpDir5/
|
||||
tmpDir1, err := ioutil.TempDir("", "")
|
||||
require.NoError(t, err)
|
||||
defer os.RemoveAll(tmpDir1)
|
||||
|
||||
tmpDir2, err := ioutil.TempDir(tmpDir1, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
err = os.Mkdir(filepath.Join(tmpDir2, "other.txt"), 0700)
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir3, err := ioutil.TempDir(tmpDir2, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir4, err := ioutil.TempDir(tmpDir3, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
tmpDir5, err := ioutil.TempDir(tmpDir4, "")
|
||||
require.NoError(t, err)
|
||||
|
||||
type testCase struct {
|
||||
Description string
|
||||
Cwd *string
|
||||
FileName string
|
||||
Expected string
|
||||
}
|
||||
|
||||
testCases := []testCase{}
|
||||
|
||||
for _, fileName := range []string{"file1.json", "file2.xml", "other.txt"} {
|
||||
filePath := filepath.Join(tmpDir1, fileName)
|
||||
require.NoError(t, ioutil.WriteFile(filePath, []byte("{}"), 0600))
|
||||
|
||||
// Relative paths end up getting symlinks fully resolved, so use this below as necessary.
|
||||
filePathResolved, err := filepath.EvalSymlinks(filePath)
|
||||
require.NoError(t, err)
|
||||
|
||||
testCases = append(testCases, []testCase{
|
||||
{
|
||||
fmt.Sprintf("absolute path to %s", fileName),
|
||||
nil,
|
||||
filePath,
|
||||
filePath,
|
||||
},
|
||||
{
|
||||
fmt.Sprintf("absolute path to %s from containing directory", fileName),
|
||||
&tmpDir1,
|
||||
filePath,
|
||||
filePath,
|
||||
},
|
||||
{
|
||||
fmt.Sprintf("relative path to %s from containing directory", fileName),
|
||||
&tmpDir1,
|
||||
fileName,
|
||||
filePathResolved,
|
||||
},
|
||||
{
|
||||
fmt.Sprintf("%s: subdirectory of containing directory", fileName),
|
||||
&tmpDir2,
|
||||
fileName,
|
||||
filePathResolved,
|
||||
},
|
||||
{
|
||||
fmt.Sprintf("%s: twice-nested subdirectory of containing directory", fileName),
|
||||
&tmpDir3,
|
||||
fileName,
|
||||
filePathResolved,
|
||||
},
|
||||
{
|
||||
fmt.Sprintf("%s: thrice-nested subdirectory of containing directory", fileName),
|
||||
&tmpDir4,
|
||||
fileName,
|
||||
filePathResolved,
|
||||
},
|
||||
{
|
||||
fmt.Sprintf("%s: can't find from four nesting levels deep", fileName),
|
||||
&tmpDir5,
|
||||
fileName,
|
||||
"",
|
||||
},
|
||||
}...)
|
||||
}
|
||||
|
||||
for _, testCase := range testCases {
|
||||
t.Run(testCase.Description, func(t *testing.T) {
|
||||
if testCase.Cwd != nil {
|
||||
prevDir, err := os.Getwd()
|
||||
require.NoError(t, err)
|
||||
defer os.Chdir(prevDir)
|
||||
os.Chdir(*testCase.Cwd)
|
||||
}
|
||||
|
||||
assert.Equal(t, testCase.Expected, FindFile(testCase.FileName))
|
||||
})
|
||||
}
|
||||
})
|
||||
}
|
||||
@@ -16,6 +16,7 @@ import (
|
||||
|
||||
"github.com/fsnotify/fsnotify"
|
||||
"github.com/mattermost/mattermost-server/mlog"
|
||||
"github.com/mattermost/mattermost-server/utils/fileutils"
|
||||
"github.com/nicksnyder/go-i18n/i18n"
|
||||
)
|
||||
|
||||
@@ -26,7 +27,7 @@ type HTMLTemplateWatcher struct {
|
||||
}
|
||||
|
||||
func NewHTMLTemplateWatcher(directory string) (*HTMLTemplateWatcher, error) {
|
||||
templatesDir, _ := FindDir(directory)
|
||||
templatesDir, _ := fileutils.FindDir(directory)
|
||||
mlog.Debug(fmt.Sprintf("Parsing server templates at %v", templatesDir))
|
||||
|
||||
ret := &HTMLTemplateWatcher{
|
||||
|
||||
@@ -12,6 +12,7 @@ import (
|
||||
|
||||
"github.com/mattermost/mattermost-server/mlog"
|
||||
"github.com/mattermost/mattermost-server/model"
|
||||
"github.com/mattermost/mattermost-server/utils/fileutils"
|
||||
"github.com/nicksnyder/go-i18n/i18n"
|
||||
)
|
||||
|
||||
@@ -39,7 +40,7 @@ func InitTranslations(localizationSettings model.LocalizationSettings) error {
|
||||
}
|
||||
|
||||
func InitTranslationsWithDir(dir string) error {
|
||||
i18nDirectory, found := FindDir(dir)
|
||||
i18nDirectory, found := fileutils.FindDir(dir)
|
||||
if !found {
|
||||
return fmt.Errorf("Unable to find i18n directory")
|
||||
}
|
||||
|
||||
@@ -19,6 +19,7 @@ import (
|
||||
|
||||
"github.com/mattermost/mattermost-server/mlog"
|
||||
"github.com/mattermost/mattermost-server/model"
|
||||
"github.com/mattermost/mattermost-server/utils/fileutils"
|
||||
)
|
||||
|
||||
var publicKey []byte = []byte(`-----BEGIN PUBLIC KEY-----
|
||||
@@ -114,7 +115,7 @@ func GetLicenseFileFromDisk(fileName string) []byte {
|
||||
|
||||
func GetLicenseFileLocation(fileLocation string) string {
|
||||
if fileLocation == "" {
|
||||
configDir, _ := FindDir("config")
|
||||
configDir, _ := fileutils.FindDir("config")
|
||||
return filepath.Join(configDir, "mattermost.mattermost-license")
|
||||
} else {
|
||||
return fileLocation
|
||||
|
||||
@@ -5,6 +5,8 @@ package utils
|
||||
|
||||
import (
|
||||
"testing"
|
||||
|
||||
"github.com/mattermost/mattermost-server/utils/fileutils"
|
||||
)
|
||||
|
||||
func TestValidateLicense(t *testing.T) {
|
||||
@@ -37,7 +39,7 @@ func TestGetLicenseFileFromDisk(t *testing.T) {
|
||||
t.Fatal("invalid bytes")
|
||||
}
|
||||
|
||||
fileBytes = GetLicenseFileFromDisk(FindConfigFile("config.json"))
|
||||
fileBytes = GetLicenseFileFromDisk(fileutils.FindConfigFile("config.json"))
|
||||
if len(fileBytes) == 0 { // a valid bytes but should be a fail license
|
||||
t.Fatal("invalid bytes")
|
||||
}
|
||||
|
||||
@@ -19,6 +19,7 @@ import (
|
||||
|
||||
"github.com/mattermost/mattermost-server/mlog"
|
||||
"github.com/mattermost/mattermost-server/model"
|
||||
"github.com/mattermost/mattermost-server/utils/fileutils"
|
||||
)
|
||||
|
||||
// UpdateAssetsSubpath rewrites assets in the /client directory to assume the application is hosted
|
||||
@@ -28,7 +29,7 @@ func UpdateAssetsSubpath(subpath string) error {
|
||||
subpath = "/"
|
||||
}
|
||||
|
||||
staticDir, found := FindDir(model.CLIENT_DIR)
|
||||
staticDir, found := fileutils.FindDir(model.CLIENT_DIR)
|
||||
if !found {
|
||||
return errors.New("failed to find client dir")
|
||||
}
|
||||
|
||||
@@ -9,11 +9,11 @@ import (
|
||||
"os"
|
||||
"path/filepath"
|
||||
|
||||
"github.com/mattermost/mattermost-server/utils"
|
||||
"github.com/mattermost/mattermost-server/utils/fileutils"
|
||||
)
|
||||
|
||||
func ReadTestFile(name string) ([]byte, error) {
|
||||
path, _ := utils.FindDir("tests")
|
||||
path, _ := fileutils.FindDir("tests")
|
||||
file, err := os.Open(filepath.Join(path, name))
|
||||
if err != nil {
|
||||
return nil, err
|
||||
|
||||
@@ -1,25 +0,0 @@
|
||||
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
|
||||
// See License.txt for license information.
|
||||
|
||||
package utils
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"io/ioutil"
|
||||
|
||||
"github.com/mattermost/mattermost-server/model"
|
||||
)
|
||||
|
||||
func LoadTimezones(fileName string) model.SupportedTimezones {
|
||||
var supportedTimezones model.SupportedTimezones
|
||||
|
||||
if timezoneFile := FindConfigFile(fileName); timezoneFile == "" {
|
||||
return model.DefaultSupportedTimezones
|
||||
} else if raw, err := ioutil.ReadFile(timezoneFile); err != nil {
|
||||
return model.DefaultSupportedTimezones
|
||||
} else if err := json.Unmarshal(raw, &supportedTimezones); err != nil {
|
||||
return model.DefaultSupportedTimezones
|
||||
} else {
|
||||
return supportedTimezones
|
||||
}
|
||||
}
|
||||
@@ -11,6 +11,7 @@ import (
|
||||
"strings"
|
||||
|
||||
"github.com/mattermost/mattermost-server/model"
|
||||
"github.com/mattermost/mattermost-server/utils/fileutils"
|
||||
)
|
||||
|
||||
func StringInSlice(a string, slice []string) bool {
|
||||
@@ -44,7 +45,7 @@ func FileExistsInConfigFolder(filename string) bool {
|
||||
return false
|
||||
}
|
||||
|
||||
if _, err := os.Stat(FindConfigFile(filename)); err == nil {
|
||||
if _, err := os.Stat(fileutils.FindConfigFile(filename)); err == nil {
|
||||
return true
|
||||
}
|
||||
return false
|
||||
|
||||
Ссылка в новой задаче
Block a user