Merge pull request #1813 from mattermost/PLT-1558
PLT-1558 adding session length to config file
Этот коммит содержится в:
@@ -523,6 +523,13 @@ func GetSession(token string) *model.Session {
|
|||||||
l4g.Error("Invalid session token=" + token + ", err=" + sessionResult.Err.DetailedError)
|
l4g.Error("Invalid session token=" + token + ", err=" + sessionResult.Err.DetailedError)
|
||||||
} else {
|
} else {
|
||||||
session = sessionResult.Data.(*model.Session)
|
session = sessionResult.Data.(*model.Session)
|
||||||
|
|
||||||
|
if session.IsExpired() {
|
||||||
|
return nil
|
||||||
|
} else {
|
||||||
|
AddSessionToCache(session)
|
||||||
|
return session
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -553,5 +560,5 @@ func FindMultiSessionForTeamId(r *http.Request, teamId string) (int64, *model.Se
|
|||||||
}
|
}
|
||||||
|
|
||||||
func AddSessionToCache(session *model.Session) {
|
func AddSessionToCache(session *model.Session) {
|
||||||
sessionCache.Add(session.Token, session)
|
sessionCache.AddWithExpiresInSecs(session.Token, session, int64(*utils.Cfg.ServiceSettings.SessionCacheInMinutes*60))
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -492,11 +492,11 @@ func Login(c *Context, w http.ResponseWriter, r *http.Request, user *model.User,
|
|||||||
|
|
||||||
session := &model.Session{UserId: user.Id, TeamId: user.TeamId, Roles: user.Roles, DeviceId: deviceId, IsOAuth: false}
|
session := &model.Session{UserId: user.Id, TeamId: user.TeamId, Roles: user.Roles, DeviceId: deviceId, IsOAuth: false}
|
||||||
|
|
||||||
maxAge := model.SESSION_TIME_WEB_IN_SECS
|
maxAge := *utils.Cfg.ServiceSettings.SessionLengthWebInDays * 60 * 60 * 24
|
||||||
|
|
||||||
if len(deviceId) > 0 {
|
if len(deviceId) > 0 {
|
||||||
session.SetExpireInDays(model.SESSION_TIME_MOBILE_IN_DAYS)
|
session.SetExpireInDays(*utils.Cfg.ServiceSettings.SessionLengthMobileInDays)
|
||||||
maxAge = model.SESSION_TIME_MOBILE_IN_SECS
|
maxAge = *utils.Cfg.ServiceSettings.SessionLengthMobileInDays * 60 * 60 * 24
|
||||||
|
|
||||||
// A special case where we logout of all other sessions with the same Id
|
// A special case where we logout of all other sessions with the same Id
|
||||||
if result := <-Srv.Store.Session().GetSessions(user.Id); result.Err != nil {
|
if result := <-Srv.Store.Session().GetSessions(user.Id); result.Err != nil {
|
||||||
@@ -518,7 +518,7 @@ func Login(c *Context, w http.ResponseWriter, r *http.Request, user *model.User,
|
|||||||
}
|
}
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
session.SetExpireInDays(model.SESSION_TIME_WEB_IN_DAYS)
|
session.SetExpireInDays(*utils.Cfg.ServiceSettings.SessionLengthWebInDays)
|
||||||
}
|
}
|
||||||
|
|
||||||
ua := user_agent.New(r.UserAgent())
|
ua := user_agent.New(r.UserAgent())
|
||||||
|
|||||||
@@ -11,7 +11,11 @@
|
|||||||
"EnablePostIconOverride": false,
|
"EnablePostIconOverride": false,
|
||||||
"EnableTesting": false,
|
"EnableTesting": false,
|
||||||
"EnableDeveloper": false,
|
"EnableDeveloper": false,
|
||||||
"EnableSecurityFixAlert": true
|
"EnableSecurityFixAlert": true,
|
||||||
|
"SessionLengthWebInDays" : 30,
|
||||||
|
"SessionLengthMobileInDays" : 30,
|
||||||
|
"SessionLengthSSOInDays" : 30,
|
||||||
|
"SessionCacheInMinutes" : 10
|
||||||
},
|
},
|
||||||
"TeamSettings": {
|
"TeamSettings": {
|
||||||
"SiteName": "Mattermost",
|
"SiteName": "Mattermost",
|
||||||
|
|||||||
@@ -11,7 +11,11 @@
|
|||||||
"EnablePostIconOverride": false,
|
"EnablePostIconOverride": false,
|
||||||
"EnableTesting": false,
|
"EnableTesting": false,
|
||||||
"EnableDeveloper": false,
|
"EnableDeveloper": false,
|
||||||
"EnableSecurityFixAlert": true
|
"EnableSecurityFixAlert": true,
|
||||||
|
"SessionLengthWebInDays" : 30,
|
||||||
|
"SessionLengthMobileInDays" : 30,
|
||||||
|
"SessionLengthSSOInDays" : 30,
|
||||||
|
"SessionCacheInMinutes" : 10
|
||||||
},
|
},
|
||||||
"TeamSettings": {
|
"TeamSettings": {
|
||||||
"SiteName": "Mattermost",
|
"SiteName": "Mattermost",
|
||||||
|
|||||||
@@ -11,7 +11,11 @@
|
|||||||
"EnablePostIconOverride": false,
|
"EnablePostIconOverride": false,
|
||||||
"EnableTesting": false,
|
"EnableTesting": false,
|
||||||
"EnableDeveloper": false,
|
"EnableDeveloper": false,
|
||||||
"EnableSecurityFixAlert": true
|
"EnableSecurityFixAlert": true,
|
||||||
|
"SessionLengthWebInDays" : 30,
|
||||||
|
"SessionLengthMobileInDays" : 30,
|
||||||
|
"SessionLengthSSOInDays" : 30,
|
||||||
|
"SessionCacheInMinutes" : 10
|
||||||
},
|
},
|
||||||
"TeamSettings": {
|
"TeamSettings": {
|
||||||
"SiteName": "Mattermost",
|
"SiteName": "Mattermost",
|
||||||
|
|||||||
@@ -114,7 +114,7 @@ func manualTest(c *api.Context, w http.ResponseWriter, r *http.Request) {
|
|||||||
Name: model.SESSION_COOKIE_TOKEN,
|
Name: model.SESSION_COOKIE_TOKEN,
|
||||||
Value: client.AuthToken,
|
Value: client.AuthToken,
|
||||||
Path: "/",
|
Path: "/",
|
||||||
MaxAge: model.SESSION_TIME_WEB_IN_SECS,
|
MaxAge: *utils.Cfg.ServiceSettings.SessionLengthWebInDays * 60 * 60 * 24,
|
||||||
HttpOnly: true,
|
HttpOnly: true,
|
||||||
}
|
}
|
||||||
http.SetCookie(w, sessionCookie)
|
http.SetCookie(w, sessionCookie)
|
||||||
|
|||||||
@@ -36,6 +36,10 @@ type ServiceSettings struct {
|
|||||||
EnableTesting bool
|
EnableTesting bool
|
||||||
EnableDeveloper *bool
|
EnableDeveloper *bool
|
||||||
EnableSecurityFixAlert *bool
|
EnableSecurityFixAlert *bool
|
||||||
|
SessionLengthWebInDays *int
|
||||||
|
SessionLengthMobileInDays *int
|
||||||
|
SessionLengthSSOInDays *int
|
||||||
|
SessionCacheInMinutes *int
|
||||||
}
|
}
|
||||||
|
|
||||||
type SSOSettings struct {
|
type SSOSettings struct {
|
||||||
@@ -306,6 +310,26 @@ func (o *Config) SetDefaults() {
|
|||||||
o.LdapSettings.Enable = new(bool)
|
o.LdapSettings.Enable = new(bool)
|
||||||
*o.LdapSettings.Enable = false
|
*o.LdapSettings.Enable = false
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if o.ServiceSettings.SessionLengthWebInDays == nil {
|
||||||
|
o.ServiceSettings.SessionLengthWebInDays = new(int)
|
||||||
|
*o.ServiceSettings.SessionLengthWebInDays = 30
|
||||||
|
}
|
||||||
|
|
||||||
|
if o.ServiceSettings.SessionLengthMobileInDays == nil {
|
||||||
|
o.ServiceSettings.SessionLengthMobileInDays = new(int)
|
||||||
|
*o.ServiceSettings.SessionLengthMobileInDays = 30
|
||||||
|
}
|
||||||
|
|
||||||
|
if o.ServiceSettings.SessionLengthSSOInDays == nil {
|
||||||
|
o.ServiceSettings.SessionLengthSSOInDays = new(int)
|
||||||
|
*o.ServiceSettings.SessionLengthSSOInDays = 30
|
||||||
|
}
|
||||||
|
|
||||||
|
if o.ServiceSettings.SessionCacheInMinutes == nil {
|
||||||
|
o.ServiceSettings.SessionCacheInMinutes = new(int)
|
||||||
|
*o.ServiceSettings.SessionCacheInMinutes = 10
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (o *Config) IsValid() *AppError {
|
func (o *Config) IsValid() *AppError {
|
||||||
|
|||||||
@@ -10,13 +10,6 @@ import (
|
|||||||
|
|
||||||
const (
|
const (
|
||||||
SESSION_COOKIE_TOKEN = "MMTOKEN"
|
SESSION_COOKIE_TOKEN = "MMTOKEN"
|
||||||
SESSION_TIME_WEB_IN_DAYS = 30
|
|
||||||
SESSION_TIME_WEB_IN_SECS = 60 * 60 * 24 * SESSION_TIME_WEB_IN_DAYS
|
|
||||||
SESSION_TIME_MOBILE_IN_DAYS = 30
|
|
||||||
SESSION_TIME_MOBILE_IN_SECS = 60 * 60 * 24 * SESSION_TIME_MOBILE_IN_DAYS
|
|
||||||
SESSION_TIME_OAUTH_IN_DAYS = 365
|
|
||||||
SESSION_TIME_OAUTH_IN_SECS = 60 * 60 * 24 * SESSION_TIME_OAUTH_IN_DAYS
|
|
||||||
SESSION_CACHE_IN_SECS = 60 * 10
|
|
||||||
SESSION_CACHE_SIZE = 10000
|
SESSION_CACHE_SIZE = 10000
|
||||||
SESSION_PROP_PLATFORM = "platform"
|
SESSION_PROP_PLATFORM = "platform"
|
||||||
SESSION_PROP_OS = "os"
|
SESSION_PROP_OS = "os"
|
||||||
@@ -89,8 +82,8 @@ func (me *Session) IsExpired() bool {
|
|||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
func (me *Session) SetExpireInDays(days int64) {
|
func (me *Session) SetExpireInDays(days int) {
|
||||||
me.ExpiresAt = GetMillis() + (1000 * 60 * 60 * 24 * days)
|
me.ExpiresAt = GetMillis() + (1000 * 60 * 60 * 24 * int64(days))
|
||||||
}
|
}
|
||||||
|
|
||||||
func (me *Session) AddProp(key string, value string) {
|
func (me *Session) AddProp(key string, value string) {
|
||||||
|
|||||||
@@ -4,6 +4,10 @@
|
|||||||
import * as Client from '../../utils/client.jsx';
|
import * as Client from '../../utils/client.jsx';
|
||||||
import * as AsyncClient from '../../utils/async_client.jsx';
|
import * as AsyncClient from '../../utils/async_client.jsx';
|
||||||
|
|
||||||
|
const DefaultSessionLength = 30;
|
||||||
|
const DefaultMaximumLoginAttempts = 10;
|
||||||
|
const DefaultSessionCacheInMinutes = 10;
|
||||||
|
|
||||||
export default class ServiceSettings extends React.Component {
|
export default class ServiceSettings extends React.Component {
|
||||||
constructor(props) {
|
constructor(props) {
|
||||||
super(props);
|
super(props);
|
||||||
@@ -45,13 +49,56 @@ export default class ServiceSettings extends React.Component {
|
|||||||
|
|
||||||
//config.ServiceSettings.EnableOAuthServiceProvider = ReactDOM.findDOMNode(this.refs.EnableOAuthServiceProvider).checked;
|
//config.ServiceSettings.EnableOAuthServiceProvider = ReactDOM.findDOMNode(this.refs.EnableOAuthServiceProvider).checked;
|
||||||
|
|
||||||
var MaximumLoginAttempts = 10;
|
var MaximumLoginAttempts = DefaultMaximumLoginAttempts;
|
||||||
if (!isNaN(parseInt(ReactDOM.findDOMNode(this.refs.MaximumLoginAttempts).value, 10))) {
|
if (!isNaN(parseInt(ReactDOM.findDOMNode(this.refs.MaximumLoginAttempts).value, 10))) {
|
||||||
MaximumLoginAttempts = parseInt(ReactDOM.findDOMNode(this.refs.MaximumLoginAttempts).value, 10);
|
MaximumLoginAttempts = parseInt(ReactDOM.findDOMNode(this.refs.MaximumLoginAttempts).value, 10);
|
||||||
}
|
}
|
||||||
|
if (MaximumLoginAttempts < 1) {
|
||||||
|
MaximumLoginAttempts = 1;
|
||||||
|
}
|
||||||
config.ServiceSettings.MaximumLoginAttempts = MaximumLoginAttempts;
|
config.ServiceSettings.MaximumLoginAttempts = MaximumLoginAttempts;
|
||||||
ReactDOM.findDOMNode(this.refs.MaximumLoginAttempts).value = MaximumLoginAttempts;
|
ReactDOM.findDOMNode(this.refs.MaximumLoginAttempts).value = MaximumLoginAttempts;
|
||||||
|
|
||||||
|
var SessionLengthWebInDays = DefaultSessionLength;
|
||||||
|
if (!isNaN(parseInt(ReactDOM.findDOMNode(this.refs.SessionLengthWebInDays).value, 10))) {
|
||||||
|
SessionLengthWebInDays = parseInt(ReactDOM.findDOMNode(this.refs.SessionLengthWebInDays).value, 10);
|
||||||
|
}
|
||||||
|
if (SessionLengthWebInDays < 1) {
|
||||||
|
SessionLengthWebInDays = 1;
|
||||||
|
}
|
||||||
|
config.ServiceSettings.SessionLengthWebInDays = SessionLengthWebInDays;
|
||||||
|
ReactDOM.findDOMNode(this.refs.SessionLengthWebInDays).value = SessionLengthWebInDays;
|
||||||
|
|
||||||
|
var SessionLengthMobileInDays = DefaultSessionLength;
|
||||||
|
if (!isNaN(parseInt(ReactDOM.findDOMNode(this.refs.SessionLengthMobileInDays).value, 10))) {
|
||||||
|
SessionLengthMobileInDays = parseInt(ReactDOM.findDOMNode(this.refs.SessionLengthMobileInDays).value, 10);
|
||||||
|
}
|
||||||
|
if (SessionLengthMobileInDays < 1) {
|
||||||
|
SessionLengthMobileInDays = 1;
|
||||||
|
}
|
||||||
|
config.ServiceSettings.SessionLengthMobileInDays = SessionLengthMobileInDays;
|
||||||
|
ReactDOM.findDOMNode(this.refs.SessionLengthMobileInDays).value = SessionLengthMobileInDays;
|
||||||
|
|
||||||
|
var SessionLengthSSOInDays = DefaultSessionLength;
|
||||||
|
if (!isNaN(parseInt(ReactDOM.findDOMNode(this.refs.SessionLengthSSOInDays).value, 10))) {
|
||||||
|
SessionLengthSSOInDays = parseInt(ReactDOM.findDOMNode(this.refs.SessionLengthSSOInDays).value, 10);
|
||||||
|
}
|
||||||
|
if (SessionLengthSSOInDays < 1) {
|
||||||
|
SessionLengthSSOInDays = 1;
|
||||||
|
}
|
||||||
|
config.ServiceSettings.SessionLengthSSOInDays = SessionLengthSSOInDays;
|
||||||
|
ReactDOM.findDOMNode(this.refs.SessionLengthSSOInDays).value = SessionLengthSSOInDays;
|
||||||
|
|
||||||
|
var SessionCacheInMinutes = DefaultSessionCacheInMinutes;
|
||||||
|
if (!isNaN(parseInt(ReactDOM.findDOMNode(this.refs.SessionCacheInMinutes).value, 10))) {
|
||||||
|
SessionCacheInMinutes = parseInt(ReactDOM.findDOMNode(this.refs.SessionCacheInMinutes).value, 10);
|
||||||
|
}
|
||||||
|
if (SessionCacheInMinutes < -1) {
|
||||||
|
SessionCacheInMinutes = -1;
|
||||||
|
}
|
||||||
|
config.ServiceSettings.SessionCacheInMinutes = SessionCacheInMinutes;
|
||||||
|
ReactDOM.findDOMNode(this.refs.SessionCacheInMinutes).value = SessionCacheInMinutes;
|
||||||
|
|
||||||
Client.saveConfig(
|
Client.saveConfig(
|
||||||
config,
|
config,
|
||||||
() => {
|
() => {
|
||||||
@@ -416,6 +463,90 @@ export default class ServiceSettings extends React.Component {
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div className='form-group'>
|
||||||
|
<label
|
||||||
|
className='control-label col-sm-4'
|
||||||
|
htmlFor='SessionLengthWebInDays'
|
||||||
|
>
|
||||||
|
{'Session Length for Web in Days:'}
|
||||||
|
</label>
|
||||||
|
<div className='col-sm-8'>
|
||||||
|
<input
|
||||||
|
type='text'
|
||||||
|
className='form-control'
|
||||||
|
id='SessionLengthWebInDays'
|
||||||
|
ref='SessionLengthWebInDays'
|
||||||
|
placeholder='Ex "30"'
|
||||||
|
defaultValue={this.props.config.ServiceSettings.SessionLengthWebInDays}
|
||||||
|
onChange={this.handleChange}
|
||||||
|
/>
|
||||||
|
<p className='help-text'>{'The web session will expire after the number of days specified and will require a user to login again.'}</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className='form-group'>
|
||||||
|
<label
|
||||||
|
className='control-label col-sm-4'
|
||||||
|
htmlFor='SessionLengthMobileInDays'
|
||||||
|
>
|
||||||
|
{'Session Length for Mobile Device in Days:'}
|
||||||
|
</label>
|
||||||
|
<div className='col-sm-8'>
|
||||||
|
<input
|
||||||
|
type='text'
|
||||||
|
className='form-control'
|
||||||
|
id='SessionLengthMobileInDays'
|
||||||
|
ref='SessionLengthMobileInDays'
|
||||||
|
placeholder='Ex "30"'
|
||||||
|
defaultValue={this.props.config.ServiceSettings.SessionLengthMobileInDays}
|
||||||
|
onChange={this.handleChange}
|
||||||
|
/>
|
||||||
|
<p className='help-text'>{'The native mobile session will expire after the number of days specified and will require a user to login again.'}</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className='form-group'>
|
||||||
|
<label
|
||||||
|
className='control-label col-sm-4'
|
||||||
|
htmlFor='SessionLengthSSOInDays'
|
||||||
|
>
|
||||||
|
{'Session Length for SSO in Days:'}
|
||||||
|
</label>
|
||||||
|
<div className='col-sm-8'>
|
||||||
|
<input
|
||||||
|
type='text'
|
||||||
|
className='form-control'
|
||||||
|
id='SessionLengthSSOInDays'
|
||||||
|
ref='SessionLengthSSOInDays'
|
||||||
|
placeholder='Ex "30"'
|
||||||
|
defaultValue={this.props.config.ServiceSettings.SessionLengthSSOInDays}
|
||||||
|
onChange={this.handleChange}
|
||||||
|
/>
|
||||||
|
<p className='help-text'>{'The SSO session will expire after the number of days specified and will require a user to login again.'}</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div className='form-group'>
|
||||||
|
<label
|
||||||
|
className='control-label col-sm-4'
|
||||||
|
htmlFor='SessionCacheInMinutes'
|
||||||
|
>
|
||||||
|
{'Session Cache in Minutes:'}
|
||||||
|
</label>
|
||||||
|
<div className='col-sm-8'>
|
||||||
|
<input
|
||||||
|
type='text'
|
||||||
|
className='form-control'
|
||||||
|
id='SessionCacheInMinutes'
|
||||||
|
ref='SessionCacheInMinutes'
|
||||||
|
placeholder='Ex "30"'
|
||||||
|
defaultValue={this.props.config.ServiceSettings.SessionCacheInMinutes}
|
||||||
|
onChange={this.handleChange}
|
||||||
|
/>
|
||||||
|
<p className='help-text'>{'The number of minutes to cache a session in memory.'}</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div className='form-group'>
|
<div className='form-group'>
|
||||||
<div className='col-sm-12'>
|
<div className='col-sm-12'>
|
||||||
{serverError}
|
{serverError}
|
||||||
|
|||||||
@@ -998,7 +998,7 @@ func getAccessToken(c *api.Context, w http.ResponseWriter, r *http.Request) {
|
|||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
accessRsp := &model.AccessResponse{AccessToken: session.Token, TokenType: model.ACCESS_TOKEN_TYPE, ExpiresIn: model.SESSION_TIME_OAUTH_IN_SECS}
|
accessRsp := &model.AccessResponse{AccessToken: session.Token, TokenType: model.ACCESS_TOKEN_TYPE, ExpiresIn: int32(*utils.Cfg.ServiceSettings.SessionLengthSSOInDays * 60 * 60 * 24)}
|
||||||
|
|
||||||
w.Header().Set("Content-Type", "application/json")
|
w.Header().Set("Content-Type", "application/json")
|
||||||
w.Header().Set("Cache-Control", "no-store")
|
w.Header().Set("Cache-Control", "no-store")
|
||||||
|
|||||||
Ссылка в новой задаче
Block a user