[release] v0.7.6
This commit is contained in:
parent
bfe587b1ed
commit
10abffbf26
|
@ -1,4 +1,7 @@
|
||||||
## Version 0.7.1 -> 0.7.5
|
## Version 0.7.1 -> 0.7.6
|
||||||
|
- Add more special characters to be used for password validation
|
||||||
|
- Add configurable default data path for binds
|
||||||
|
- Remove Redirects from home page
|
||||||
- Fix compat with non-HTTP protocol like WebDAV (for Nextcloud for example)
|
- Fix compat with non-HTTP protocol like WebDAV (for Nextcloud for example)
|
||||||
- Fix regression with DNS wildcards certificates
|
- Fix regression with DNS wildcards certificates
|
||||||
- Fix issue with the installer when changing both the labels and the volumes
|
- Fix issue with the installer when changing both the labels and the volumes
|
||||||
|
|
|
@ -73,8 +73,8 @@ const AuthRegister = ({nickname, isRegister, isInviteLink, regkey}) => {
|
||||||
.max(255)
|
.max(255)
|
||||||
.required('Password is required')
|
.required('Password is required')
|
||||||
.matches(
|
.matches(
|
||||||
/^(?=.*[a-z])(?=.*[A-Z])(?=.*[0-9])(?=.*[!@#$%^&*])(?=.{9,})/,
|
/^(?=.*[a-z])(?=.*[A-Z])(?=.*[0-9])(?=.*[~!@#$%\^&\*\(\)_\+=\-\{\[\}\]:;"'<,>\.\?\/])(?=.{9,})/,
|
||||||
'Must Contain 9 Characters, One Uppercase, One Lowercase, One Number and one special case Character'
|
'Must Contain 9 Characters, One Uppercase, One Lowercase, One Number and one special case Character (~!@#$%^&*()_+=-{[}]:;"\'<>.?/)'
|
||||||
),
|
),
|
||||||
})}
|
})}
|
||||||
onSubmit={async (values, { setErrors, setStatus, setSubmitting }) => {
|
onSubmit={async (values, { setErrors, setStatus, setSubmitting }) => {
|
||||||
|
|
|
@ -80,6 +80,9 @@ const ConfigManagement = () => {
|
||||||
Email_Password: config.EmailConfig.Password,
|
Email_Password: config.EmailConfig.Password,
|
||||||
Email_From: config.EmailConfig.From,
|
Email_From: config.EmailConfig.From,
|
||||||
Email_UseTLS : config.EmailConfig.UseTLS,
|
Email_UseTLS : config.EmailConfig.UseTLS,
|
||||||
|
|
||||||
|
SkipPruneNetwork: config.DockerConfig.SkipPruneNetwork,
|
||||||
|
DefaultDataPath: config.DockerConfig.DefaultDataPath
|
||||||
}}
|
}}
|
||||||
validationSchema={Yup.object().shape({
|
validationSchema={Yup.object().shape({
|
||||||
Hostname: Yup.string().max(255).required('Hostname is required'),
|
Hostname: Yup.string().max(255).required('Hostname is required'),
|
||||||
|
@ -116,6 +119,11 @@ const ConfigManagement = () => {
|
||||||
Password: values.Email_Password,
|
Password: values.Email_Password,
|
||||||
From: values.Email_From,
|
From: values.Email_From,
|
||||||
UseTLS: values.Email_UseTLS,
|
UseTLS: values.Email_UseTLS,
|
||||||
|
},
|
||||||
|
DockerConfig: {
|
||||||
|
...config.DockerConfig,
|
||||||
|
SkipPruneNetwork: values.SkipPruneNetwork,
|
||||||
|
DefaultDataPath: values.DefaultDataPath
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -353,6 +361,23 @@ const ConfigManagement = () => {
|
||||||
</Stack>
|
</Stack>
|
||||||
</MainCard>
|
</MainCard>
|
||||||
|
|
||||||
|
<MainCard title="Docker">
|
||||||
|
<Stack spacing={2}>
|
||||||
|
<CosmosCheckbox
|
||||||
|
label="Skip Prune Network"
|
||||||
|
name="SkipPruneNetwork"
|
||||||
|
formik={formik}
|
||||||
|
/>
|
||||||
|
|
||||||
|
<CosmosInputText
|
||||||
|
label="Default data path for installs"
|
||||||
|
name="DefaultDataPath"
|
||||||
|
formik={formik}
|
||||||
|
/>
|
||||||
|
</Stack>
|
||||||
|
</MainCard>
|
||||||
|
|
||||||
|
|
||||||
<MainCard title="Security">
|
<MainCard title="Security">
|
||||||
<Grid container spacing={3}>
|
<Grid container spacing={3}>
|
||||||
|
|
||||||
|
|
|
@ -167,7 +167,7 @@ const HomePage = () => {
|
||||||
|
|
||||||
<Grid2 container spacing={2} style={{ zIndex: 2 }}>
|
<Grid2 container spacing={2} style={{ zIndex: 2 }}>
|
||||||
{config && serveApps && routes.map((route) => {
|
{config && serveApps && routes.map((route) => {
|
||||||
let skip = false;
|
let skip = route.Mode == "REDIRECT";
|
||||||
if(route.Mode == "SERVAPP") {
|
if(route.Mode == "SERVAPP") {
|
||||||
const containerName = route.Target.split(':')[1].slice(2);
|
const containerName = route.Target.split(':')[1].slice(2);
|
||||||
const container = serveApps.find((c) => c.Names.includes('/' + containerName));
|
const container = serveApps.find((c) => c.Names.includes('/' + containerName));
|
||||||
|
|
|
@ -455,7 +455,7 @@ const NewInstall = () => {
|
||||||
// nickname cant be admin or root
|
// nickname cant be admin or root
|
||||||
nickname: Yup.string().required('Nickname is required').min(3).max(32)
|
nickname: Yup.string().required('Nickname is required').min(3).max(32)
|
||||||
.matches(/^(?!admin|root).*$/, 'Nickname cannot be admin or root'),
|
.matches(/^(?!admin|root).*$/, 'Nickname cannot be admin or root'),
|
||||||
password: Yup.string().required('Password is required').min(8).max(128).matches(/^(?=.*[a-z])(?=.*[A-Z])(?=.*[0-9])(?=.*[!@#$%^&*])(?=.{9,})/, 'Password must contain 9 characters: at least 1 lowercase, 1 uppercase, 1 number, and 1 special character'),
|
password: Yup.string().required('Password is required').min(8).max(128).matches(/^(?=.*[a-z])(?=.*[A-Z])(?=.*[0-9])(?=.*[~!@#$%\^&\*\(\)_\+=\-\{\[\}\]:;"'<,>\.\?\/])(?=.{9,})/, 'Password must contain 9 characters: at least 1 lowercase, 1 uppercase, 1 number, and 1 special character'),
|
||||||
email: Yup.string().email('Must be a valid email').max(255),
|
email: Yup.string().email('Must be a valid email').max(255),
|
||||||
confirmPassword: Yup.string().oneOf([Yup.ref('password'), null], 'Passwords must match'),
|
confirmPassword: Yup.string().oneOf([Yup.ref('password'), null], 'Passwords must match'),
|
||||||
})}
|
})}
|
||||||
|
|
|
@ -93,6 +93,17 @@ const DockerComposeImport = ({ refresh, dockerComposeInit, installerInit, defaul
|
||||||
const [overrides, setOverrides] = useState({});
|
const [overrides, setOverrides] = useState({});
|
||||||
const [context, setContext] = useState({});
|
const [context, setContext] = useState({});
|
||||||
const [installer, setInstaller] = useState(installerInit);
|
const [installer, setInstaller] = useState(installerInit);
|
||||||
|
const [config, setConfig] = useState({});
|
||||||
|
|
||||||
|
function refreshConfig() {
|
||||||
|
API.config.get().then((res) => {
|
||||||
|
setConfig(res.data);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
React.useEffect(() => {
|
||||||
|
refreshConfig();
|
||||||
|
}, []);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (!openModal) {
|
if (!openModal) {
|
||||||
|
@ -325,12 +336,14 @@ const DockerComposeImport = ({ refresh, dockerComposeInit, installerInit, defaul
|
||||||
Hostnames: hostnames,
|
Hostnames: hostnames,
|
||||||
Context: context,
|
Context: context,
|
||||||
Passwords: [
|
Passwords: [
|
||||||
randomString(32),
|
randomString(24),
|
||||||
randomString(32),
|
randomString(24),
|
||||||
randomString(32)
|
randomString(24),
|
||||||
|
randomString(24)
|
||||||
],
|
],
|
||||||
CPU_ARCH: API.CPU_ARCH,
|
CPU_ARCH: API.CPU_ARCH,
|
||||||
CPU_AVX: API.CPU_AVX,
|
CPU_AVX: API.CPU_AVX,
|
||||||
|
DefaultDataPath: (config && config.DockerConfig && config.DockerConfig.DefaultDataPath) || "/usr",
|
||||||
});
|
});
|
||||||
|
|
||||||
const jsoned = JSON.parse(rendered);
|
const jsoned = JSON.parse(rendered);
|
||||||
|
@ -441,7 +454,7 @@ const DockerComposeImport = ({ refresh, dockerComposeInit, installerInit, defaul
|
||||||
setYmlError(e.message);
|
setYmlError(e.message);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}, [openModal, dockerCompose, serviceName, hostnames, overrides, installer]);
|
}, [openModal, dockerCompose, serviceName, hostnames, overrides, installer, config]);
|
||||||
|
|
||||||
const openModalFunc = () => {
|
const openModalFunc = () => {
|
||||||
setOpenModal(true);
|
setOpenModal(true);
|
||||||
|
|
|
@ -5,7 +5,7 @@ const hasNumber = (number) => new RegExp(/[0-9]/).test(number);
|
||||||
const hasMixed = (number) => new RegExp(/[a-z]/).test(number) && new RegExp(/[A-Z]/).test(number);
|
const hasMixed = (number) => new RegExp(/[a-z]/).test(number) && new RegExp(/[A-Z]/).test(number);
|
||||||
|
|
||||||
// has special chars
|
// has special chars
|
||||||
const hasSpecial = (number) => new RegExp(/[!#@$%^&*)(+=._-]/).test(number);
|
const hasSpecial = (number) => new RegExp(/[~!@#$%\^&\*\(\)_\+=\-\{\[\}\]:;"'<,>\.\?\/]/).test(number);
|
||||||
|
|
||||||
// set color based on password strength
|
// set color based on password strength
|
||||||
export const strengthColor = (count) => {
|
export const strengthColor = (count) => {
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
{
|
{
|
||||||
"name": "cosmos-server",
|
"name": "cosmos-server",
|
||||||
"version": "0.7.5",
|
"version": "0.7.6",
|
||||||
"description": "",
|
"description": "",
|
||||||
"main": "test-server.js",
|
"main": "test-server.js",
|
||||||
"bugs": {
|
"bugs": {
|
||||||
|
|
|
@ -39,7 +39,7 @@ type NewInstallJSON struct {
|
||||||
|
|
||||||
type AdminJSON struct {
|
type AdminJSON struct {
|
||||||
Nickname string `validate:"required,min=3,max=32,alphanum"`
|
Nickname string `validate:"required,min=3,max=32,alphanum"`
|
||||||
Password string `validate:"required,min=9,max=128,containsany=!@#$%^&*()_+,containsany=ABCDEFGHIJKLMNOPQRSTUVWXYZ,containsany=abcdefghijklmnopqrstuvwxyz,containsany=0123456789"`
|
Password string `validate:"required,min=9,max=128,containsany=~!@#$%^&*()_+=-{[}]:;"'<>.?/,containsany=ABCDEFGHIJKLMNOPQRSTUVWXYZ,containsany=abcdefghijklmnopqrstuvwxyz,containsany=0123456789"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewInstallRoute(w http.ResponseWriter, req *http.Request) {
|
func NewInstallRoute(w http.ResponseWriter, req *http.Request) {
|
||||||
|
|
|
@ -14,7 +14,7 @@ import (
|
||||||
|
|
||||||
type LoginRequestJSON struct {
|
type LoginRequestJSON struct {
|
||||||
Nickname string `validate:"required,min=3,max=32,alphanum"`
|
Nickname string `validate:"required,min=3,max=32,alphanum"`
|
||||||
Password string `validate:"required,min=8,max=128,containsany=!@#$%^&*()_+,containsany=ABCDEFGHIJKLMNOPQRSTUVWXYZ,containsany=abcdefghijklmnopqrstuvwxyz,containsany=0123456789"`
|
Password string `validate:"required,min=8,max=128,containsany=~!@#$%^&*()_+=-{[}]:;"'<>.?/,containsany=ABCDEFGHIJKLMNOPQRSTUVWXYZ,containsany=abcdefghijklmnopqrstuvwxyz,containsany=0123456789"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func UserLogin(w http.ResponseWriter, req *http.Request) {
|
func UserLogin(w http.ResponseWriter, req *http.Request) {
|
||||||
|
|
|
@ -13,7 +13,7 @@ import (
|
||||||
|
|
||||||
type RegisterRequestJSON struct {
|
type RegisterRequestJSON struct {
|
||||||
Nickname string `validate:"required,min=3,max=32,alphanum"`
|
Nickname string `validate:"required,min=3,max=32,alphanum"`
|
||||||
Password string `validate:"required,min=9,max=128,containsany=!@#$%^&*()_+,containsany=ABCDEFGHIJKLMNOPQRSTUVWXYZ,containsany=abcdefghijklmnopqrstuvwxyz,containsany=0123456789"`
|
Password string `validate:"required,min=9,max=128,containsany=~!@#$%^&*()_+=-{[}]:;"'<>.?/,containsany=ABCDEFGHIJKLMNOPQRSTUVWXYZ,containsany=abcdefghijklmnopqrstuvwxyz,containsany=0123456789"`
|
||||||
RegisterKey string `validate:"required,min=1,max=512,alphanum"`
|
RegisterKey string `validate:"required,min=1,max=512,alphanum"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -126,6 +126,7 @@ type SmartShieldPolicy struct {
|
||||||
|
|
||||||
type DockerConfig struct {
|
type DockerConfig struct {
|
||||||
SkipPruneNetwork bool
|
SkipPruneNetwork bool
|
||||||
|
DefaultDataPath string
|
||||||
}
|
}
|
||||||
|
|
||||||
type ProxyConfig struct {
|
type ProxyConfig struct {
|
||||||
|
|
|
@ -78,6 +78,9 @@ var DefaultConfig = Config{
|
||||||
Routes: []ProxyRouteConfig{},
|
Routes: []ProxyRouteConfig{},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
DockerConfig: DockerConfig{
|
||||||
|
DefaultDataPath: "/usr",
|
||||||
|
},
|
||||||
MarketConfig: MarketConfig{
|
MarketConfig: MarketConfig{
|
||||||
Sources: []MarketSource{
|
Sources: []MarketSource{
|
||||||
},
|
},
|
||||||
|
@ -216,9 +219,9 @@ func LoadBaseMainConfig(config Config) {
|
||||||
MainConfig.ServerCountry = os.Getenv("COSMOS_SERVER_COUNTRY")
|
MainConfig.ServerCountry = os.Getenv("COSMOS_SERVER_COUNTRY")
|
||||||
}
|
}
|
||||||
|
|
||||||
// if BaseMainConfig.NewInstall {
|
if MainConfig.DockerConfig.DefaultDataPath == "" {
|
||||||
// MainConfig.HTTPConfig.HTTPSCertificateMode = "DISABLED"
|
MainConfig.DockerConfig.DefaultDataPath = "/usr"
|
||||||
// }
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func GetMainConfig() Config {
|
func GetMainConfig() Config {
|
||||||
|
|
Loading…
Reference in a new issue