2019-02-07 00:02:57 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							 
							
							
								package  auth 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								import  ( 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									"context" 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									"crypto/sha256" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									"encoding/hex" 
							 
						 
					
						
							
								
									
										
										
										
											2020-11-25 14:55:22 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									"net" 
							 
						 
					
						
							
								
									
										
										
										
											2019-05-31 18:22:22 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									"strings" 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									"time" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									"github.com/grafana/grafana/pkg/infra/serverlock" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-05-13 14:45:54 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									"github.com/grafana/grafana/pkg/infra/log" 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-06 23:45:48 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							 
							
							
									"github.com/grafana/grafana/pkg/models" 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									"github.com/grafana/grafana/pkg/services/sqlstore" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									"github.com/grafana/grafana/pkg/setting" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									"github.com/grafana/grafana/pkg/util" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-12-11 18:44:44 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								const  ServiceName  =  "UserAuthTokenService" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								var  getTime  =  time . Now 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								const  urgentRotateTime  =  1  *  time . Minute 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-08-25 21:11:22 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  ProvideUserAuthTokenService ( sqlStore  * sqlstore . SQLStore ,  serverLockService  * serverlock . ServerLockService , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									cfg  * setting . Cfg )  * UserAuthTokenService  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									s  :=  & UserAuthTokenService { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										SQLStore :           sqlStore , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										ServerLockService :  serverLockService , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										Cfg :                cfg , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										log :                log . New ( "auth" ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									return  s 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-08-25 21:11:22 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								type  UserAuthTokenService  struct  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									SQLStore           * sqlstore . SQLStore 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									ServerLockService  * serverlock . ServerLockService 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									Cfg                * setting . Cfg 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									log                log . Logger 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  ( s  * UserAuthTokenService )  ActiveTokenCount ( ctx  context . Context )  ( int64 ,  error )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									var  count  int64 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									var  err  error 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									err  =  s . SQLStore . WithDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										var  model  userAuthToken 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-17 00:44:02 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										count ,  err  =  dbSession . Where ( ` created_at > ? AND rotated_at > ? AND revoked_at = 0 ` , 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
											s . createdAfterParam ( ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											s . rotatedAfterParam ( ) ) . 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											Count ( & model ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-12 04:12:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									return  count ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 00:55:53 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  ( s  * UserAuthTokenService )  CreateToken ( ctx  context . Context ,  user  * models . User ,  clientIP  net . IP ,  userAgent  string )  ( * models . UserToken ,  error )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									token ,  err  :=  util . RandomHex ( 16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  nil ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									hashedToken  :=  hashToken ( token ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									now  :=  getTime ( ) . Unix ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2020-11-25 14:55:22 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									clientIPStr  :=  clientIP . String ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  len ( clientIP )  ==  0  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										clientIPStr  =  "" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									userAuthToken  :=  userAuthToken { 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 00:55:53 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										UserId :         user . Id , 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										AuthToken :      hashedToken , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										PrevAuthToken :  hashedToken , 
							 
						 
					
						
							
								
									
										
										
										
											2020-11-25 14:55:22 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										ClientIp :       clientIPStr , 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										UserAgent :      userAgent , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										RotatedAt :      now , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										CreatedAt :      now , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										UpdatedAt :      now , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										SeenAt :         0 , 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-17 00:44:02 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										RevokedAt :      0 , 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										AuthTokenSeen :  false , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									err  =  s . SQLStore . WithDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										_ ,  err  =  dbSession . Insert ( & userAuthToken ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  nil ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									userAuthToken . UnhashedToken  =  token 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									s . log . Debug ( "user auth token created" ,  "tokenId" ,  userAuthToken . Id ,  "userId" ,  userAuthToken . UserId ,  "clientIP" ,  userAuthToken . ClientIp ,  "userAgent" ,  userAuthToken . UserAgent ,  "authToken" ,  userAuthToken . AuthToken ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-02-06 23:45:48 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							 
							
							
									var  userToken  models . UserToken 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-06 23:21:16 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							 
							
							
									err  =  userAuthToken . toUserToken ( & userToken ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									return  & userToken ,  err 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  ( s  * UserAuthTokenService )  LookupToken ( ctx  context . Context ,  unhashedToken  string )  ( * models . UserToken ,  error )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									hashedToken  :=  hashToken ( unhashedToken ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									var  model  userAuthToken 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									var  exists  bool 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									var  err  error 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									err  =  s . SQLStore . WithDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 00:55:53 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										exists ,  err  =  dbSession . Where ( "(auth_token = ? OR prev_auth_token = ?)" , 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
											hashedToken , 
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 00:55:53 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
											hashedToken ) . 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
											Get ( & model ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  nil ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  ! exists  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-07 00:02:57 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							 
							
							
										return  nil ,  models . ErrUserTokenNotFound 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-03-17 00:44:02 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									if  model . RevokedAt  >  0  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  nil ,  & models . TokenRevokedError { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											UserID :   model . UserId , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											TokenID :  model . Id , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-01-20 00:55:53 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									if  model . CreatedAt  <=  s . createdAfterParam ( )  ||  model . RotatedAt  <=  s . rotatedAfterParam ( )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  nil ,  & models . TokenExpiredError { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											UserID :   model . UserId , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											TokenID :  model . Id , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									if  model . AuthToken  !=  hashedToken  &&  model . PrevAuthToken  ==  hashedToken  &&  model . AuthTokenSeen  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										modelCopy  :=  model 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										modelCopy . AuthTokenSeen  =  false 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										expireBefore  :=  getTime ( ) . Add ( - urgentRotateTime ) . Unix ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										var  affectedRows  int64 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										err  =  s . SQLStore . WithTransactionalDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											affectedRows ,  err  =  dbSession . Where ( "id = ? AND prev_auth_token = ? AND rotated_at < ?" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
												modelCopy . Id , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
												modelCopy . PrevAuthToken , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
												expireBefore ) . 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
												AllCols ( ) . Update ( & modelCopy ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  nil ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										if  affectedRows  ==  0  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											s . log . Debug ( "prev seen token unchanged" ,  "tokenId" ,  model . Id ,  "userId" ,  model . UserId ,  "clientIP" ,  model . ClientIp ,  "userAgent" ,  model . UserAgent ,  "authToken" ,  model . AuthToken ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											s . log . Debug ( "prev seen token" ,  "tokenId" ,  model . Id ,  "userId" ,  model . UserId ,  "clientIP" ,  model . ClientIp ,  "userAgent" ,  model . UserAgent ,  "authToken" ,  model . AuthToken ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  ! model . AuthTokenSeen  &&  model . AuthToken  ==  hashedToken  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										modelCopy  :=  model 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										modelCopy . AuthTokenSeen  =  true 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										modelCopy . SeenAt  =  getTime ( ) . Unix ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										var  affectedRows  int64 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										err  =  s . SQLStore . WithTransactionalDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											affectedRows ,  err  =  dbSession . Where ( "id = ? AND auth_token = ?" , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
												modelCopy . Id , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
												modelCopy . AuthToken ) . 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
												AllCols ( ) . Update ( & modelCopy ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  nil ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										if  affectedRows  ==  1  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											model  =  modelCopy 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										if  affectedRows  ==  0  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											s . log . Debug ( "seen wrong token" ,  "tokenId" ,  model . Id ,  "userId" ,  model . UserId ,  "clientIP" ,  model . ClientIp ,  "userAgent" ,  model . UserAgent ,  "authToken" ,  model . AuthToken ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											s . log . Debug ( "seen token" ,  "tokenId" ,  model . Id ,  "userId" ,  model . UserId ,  "clientIP" ,  model . ClientIp ,  "userAgent" ,  model . UserAgent ,  "authToken" ,  model . AuthToken ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									model . UnhashedToken  =  unhashedToken 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-06 23:21:16 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-02-06 23:45:48 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							 
							
							
									var  userToken  models . UserToken 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-06 23:21:16 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							 
							
							
									err  =  model . toUserToken ( & userToken ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									return  & userToken ,  err 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-10-09 14:58:45 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  ( s  * UserAuthTokenService )  TryRotateToken ( ctx  context . Context ,  token  * models . UserToken , 
							 
						 
					
						
							
								
									
										
										
										
											2020-11-25 14:55:22 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									clientIP  net . IP ,  userAgent  string )  ( bool ,  error )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									if  token  ==  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  false ,  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-10-22 20:08:18 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									model ,  err  :=  userAuthTokenFromUserToken ( token ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  false ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									now  :=  getTime ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-16 16:27:07 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									var  needsRotation  bool 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									rotatedAt  :=  time . Unix ( model . RotatedAt ,  0 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  model . AuthTokenSeen  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-06 04:12:30 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							 
							
							
										needsRotation  =  rotatedAt . Before ( now . Add ( - time . Duration ( s . Cfg . TokenRotationIntervalMinutes )  *  time . Minute ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										needsRotation  =  rotatedAt . Before ( now . Add ( - urgentRotateTime ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  ! needsRotation  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  false ,  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									s . log . Debug ( "token needs rotation" ,  "tokenId" ,  model . Id ,  "authTokenSeen" ,  model . AuthTokenSeen ,  "rotatedAt" ,  rotatedAt ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2020-11-25 14:55:22 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									clientIPStr  :=  clientIP . String ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  len ( clientIP )  ==  0  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										clientIPStr  =  "" 
							 
						 
					
						
							
								
									
										
										
										
											2019-10-09 14:58:45 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									newToken ,  err  :=  util . RandomHex ( 16 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  false ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									hashedToken  :=  hashToken ( newToken ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									// very important that auth_token_seen is set after the prev_auth_token = case when ... for mysql to function correctly
 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									sql  :=  ` 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										UPDATE  user_auth_token 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										SET 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											seen_at  =  0 , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											user_agent  =  ? , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											client_ip  =  ? , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											prev_auth_token  =  case  when  auth_token_seen  =  ?  then  auth_token  else  prev_auth_token  end , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											auth_token  =  ? , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											auth_token_seen  =  ? , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											rotated_at  =  ? 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										WHERE  id  =  ?  AND  ( auth_token_seen  =  ?  OR  rotated_at  <  ? ) ` 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									var  affected  int64 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									err  =  s . SQLStore . WithTransactionalDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-11-25 14:55:22 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										res ,  err  :=  dbSession . Exec ( sql ,  userAgent ,  clientIPStr ,  s . SQLStore . Dialect . BooleanStr ( true ) ,  hashedToken , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											s . SQLStore . Dialect . BooleanStr ( false ) ,  now . Unix ( ) ,  model . Id ,  s . SQLStore . Dialect . BooleanStr ( true ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											now . Add ( - 30 * time . Second ) . Unix ( ) ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										affected ,  err  =  res . RowsAffected ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  false ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									s . log . Debug ( "auth token rotated" ,  "affected" ,  affected ,  "auth_token_id" ,  model . Id ,  "userId" ,  model . UserId ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  affected  >  0  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										model . UnhashedToken  =  newToken 
							 
						 
					
						
							
								
									
										
										
										
											2019-10-22 20:08:18 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										if  err  :=  model . toUserToken ( token ) ;  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  false ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										return  true ,  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									return  false ,  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-03-17 00:44:02 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  ( s  * UserAuthTokenService )  RevokeToken ( ctx  context . Context ,  token  * models . UserToken ,  soft  bool )  error  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									if  token  ==  nil  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-07 00:02:57 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							 
							
							
										return  models . ErrUserTokenNotFound 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-10-22 20:08:18 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									model ,  err  :=  userAuthTokenFromUserToken ( token ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									var  rowsAffected  int64 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-17 00:44:02 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  soft  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										model . RevokedAt  =  getTime ( ) . Unix ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										err  =  s . SQLStore . WithDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											rowsAffected ,  err  =  dbSession . ID ( model . Id ) . Update ( model ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									}  else  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										err  =  s . SQLStore . WithDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											rowsAffected ,  err  =  dbSession . Delete ( model ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									if  rowsAffected  ==  0  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										s . log . Debug ( "user auth token not found/revoked" ,  "tokenId" ,  model . Id ,  "userId" ,  model . UserId ,  "clientIP" ,  model . ClientIp ,  "userAgent" ,  model . UserAgent ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-07 00:02:57 +08:00 
										
									 
								 
							 
							
								
							 
							
								 
							 
							
							
										return  models . ErrUserTokenNotFound 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-03-17 00:44:02 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									s . log . Debug ( "user auth token revoked" ,  "tokenId" ,  model . Id ,  "userId" ,  model . UserId ,  "clientIP" ,  model . ClientIp ,  "userAgent" ,  model . UserAgent ,  "soft" ,  soft ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									return  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  ( s  * UserAuthTokenService )  RevokeAllUserTokens ( ctx  context . Context ,  userId  int64 )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									return  s . SQLStore . WithDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										sql  :=  ` DELETE from user_auth_token WHERE user_id = ? ` 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										res ,  err  :=  dbSession . Exec ( sql ,  userId ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2019-03-08 22:15:17 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										affected ,  err  :=  res . RowsAffected ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
									
										
										
										
											2019-03-08 22:15:17 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										s . log . Debug ( "all user tokens for user revoked" ,  "userId" ,  userId ,  "count" ,  affected ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-03-08 22:15:17 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-03-08 22:15:17 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-05-31 18:22:22 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  ( s  * UserAuthTokenService )  BatchRevokeAllUserTokens ( ctx  context . Context ,  userIds  [ ] int64 )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									return  s . SQLStore . WithTransactionalDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										if  len ( userIds )  ==  0  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										user_id_params  :=  strings . Repeat ( ",?" ,  len ( userIds ) - 1 ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										sql  :=  "DELETE from user_auth_token WHERE user_id IN (?"  +  user_id_params  +  ")" 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										params  :=  [ ] interface { } { sql } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										for  _ ,  v  :=  range  userIds  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											params  =  append ( params ,  v ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										res ,  err  :=  dbSession . Exec ( params ... ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										affected ,  err  :=  res . RowsAffected ( ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										s . log . Debug ( "all user tokens for given users revoked" ,  "usersCount" ,  len ( userIds ) ,  "count" ,  affected ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  ( s  * UserAuthTokenService )  GetUserToken ( ctx  context . Context ,  userId ,  userTokenId  int64 )  ( * models . UserToken ,  error )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-03-08 22:15:17 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									var  result  models . UserToken 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									err  :=  s . SQLStore . WithDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										var  token  userAuthToken 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										exists ,  err  :=  dbSession . Where ( "id = ? AND user_id = ?" ,  userTokenId ,  userId ) . Get ( & token ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										if  ! exists  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  models . ErrUserTokenNotFound 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-10-22 20:08:18 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										return  token . toUserToken ( & result ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									} ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-03-08 22:15:17 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									return  & result ,  err 
							 
						 
					
						
							
								
									
										
										
										
											2019-03-08 22:15:17 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  ( s  * UserAuthTokenService )  GetUserTokens ( ctx  context . Context ,  userId  int64 )  ( [ ] * models . UserToken ,  error )  { 
							 
						 
					
						
							
								
									
										
										
										
											2019-03-08 22:15:17 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									result  :=  [ ] * models . UserToken { } 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									err  :=  s . SQLStore . WithDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										var  tokens  [ ] * userAuthToken 
							 
						 
					
						
							
								
									
										
										
										
											2021-03-17 00:44:02 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
										err  :=  dbSession . Where ( "user_id = ? AND created_at > ? AND rotated_at > ? AND revoked_at = 0" , 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
											userId , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											s . createdAfterParam ( ) , 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											s . rotatedAfterParam ( ) ) . 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											Find ( & tokens ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										for  _ ,  token  :=  range  tokens  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											var  userToken  models . UserToken 
							 
						 
					
						
							
								
									
										
										
										
											2019-10-22 20:08:18 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
											if  err  :=  token . toUserToken ( & userToken ) ;  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
												return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											} 
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
											result  =  append ( result ,  & userToken ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-03-08 22:15:17 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-04-30 20:42:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									return  result ,  err 
							 
						 
					
						
							
								
									
										
										
										
											2019-03-08 22:15:17 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2021-03-17 00:44:02 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  ( s  * UserAuthTokenService )  GetUserRevokedTokens ( ctx  context . Context ,  userId  int64 )  ( [ ] * models . UserToken ,  error )  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									result  :=  [ ] * models . UserToken { } 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									err  :=  s . SQLStore . WithDbSession ( ctx ,  func ( dbSession  * sqlstore . DBSession )  error  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										var  tokens  [ ] * userAuthToken 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										err  :=  dbSession . Where ( "user_id = ? AND revoked_at > 0" ,  userId ) . Find ( & tokens ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										if  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										for  _ ,  token  :=  range  tokens  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											var  userToken  models . UserToken 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											if  err  :=  token . toUserToken ( & userToken ) ;  err  !=  nil  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
												return  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
											result  =  append ( result ,  & userToken ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
										return  nil 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									} ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									return  result ,  err 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-02-12 04:12:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  ( s  * UserAuthTokenService )  createdAfterParam ( )  int64  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-09-14 21:57:38 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									return  getTime ( ) . Add ( - s . Cfg . LoginMaxLifetime ) . Unix ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-12 04:12:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								func  ( s  * UserAuthTokenService )  rotatedAfterParam ( )  int64  { 
							 
						 
					
						
							
								
									
										
										
										
											2020-09-14 21:57:38 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
									return  getTime ( ) . Add ( - s . Cfg . LoginMaxInactiveLifetime ) . Unix ( ) 
							 
						 
					
						
							
								
									
										
										
										
											2019-02-12 04:12:01 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								} 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								
							 
						 
					
						
							
								
									
										
										
										
											2019-02-02 19:11:30 +08:00 
										
									 
								 
							 
							
								
									
										 
									 
								
							 
							
								 
							 
							
							
								func  hashToken ( token  string )  string  { 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									hashBytes  :=  sha256 . Sum256 ( [ ] byte ( token  +  setting . SecretKey ) ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
									return  hex . EncodeToString ( hashBytes [ : ] ) 
							 
						 
					
						
							
								
							 
							
								
							 
							
								 
							 
							
							
								}