Skip to content
Projects
Groups
Snippets
Help
Loading...
Sign in
Toggle navigation
K
koko
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
ops
koko
Commits
8b06c4a1
Commit
8b06c4a1
authored
May 09, 2019
by
ibuler
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
[Update] 修改 认证
parent
93d1b3f1
Expand all
Show whitespace changes
Inline
Side-by-side
Showing
9 changed files
with
57 additions
and
78 deletions
+57
-78
server.go
pkg/auth/server.go
+39
-33
client.go
pkg/common/client.go
+2
-2
session.go
pkg/handler/session.go
+0
-0
terminal.go
pkg/model/terminal.go
+1
-1
users.go
pkg/model/users.go
+2
-3
accesskey.go
pkg/service/accesskey.go
+5
-5
perms.go
pkg/service/perms.go
+2
-2
users.go
pkg/service/users.go
+5
-31
handler.go
pkg/webssh/handler.go
+1
-1
No files found.
pkg/auth/server.go
View file @
8b06c4a1
package
auth
import
(
"cocogo/pkg/cctx"
"cocogo/pkg/i18n"
"strings"
"github.com/gliderlabs/ssh"
gossh
"golang.org/x/crypto/ssh"
"cocogo/pkg/cctx"
"cocogo/pkg/common"
"cocogo/pkg/i18n"
"cocogo/pkg/logger"
"cocogo/pkg/service"
)
...
...
@@ -16,34 +16,34 @@ import (
var
mfaInstruction
=
i18n
.
T
(
"Please enter 6 digits."
)
var
mfaQuestion
=
i18n
.
T
(
"[MFA auth]: "
)
var
contentKeyMFASeed
=
"MFASeed"
const
(
actionAccepted
=
"Accepted"
actionFailed
=
"Failed"
actionPartialAccepted
=
"Partial accepted"
)
func
checkAuth
(
ctx
ssh
.
Context
,
password
,
publicKey
string
)
(
res
ssh
.
AuthResult
)
{
username
:=
ctx
.
User
()
remoteAddr
:=
strings
.
Split
(
ctx
.
RemoteAddr
()
.
String
(),
":"
)[
0
]
resp
,
err
:=
service
.
Authenticate
(
username
,
password
,
publicKey
,
remoteAddr
,
"T"
)
authMethod
:=
"publickey"
action
:=
"Accepted"
action
:=
actionAccepted
res
=
ssh
.
AuthFailed
if
password
!=
""
{
authMethod
=
"password"
}
if
err
!=
nil
{
action
=
"Failed"
remoteAddr
:=
strings
.
Split
(
ctx
.
RemoteAddr
()
.
String
(),
":"
)[
0
]
}
else
if
resp
.
Seed
!=
""
&&
resp
.
Token
==
""
{
ctx
.
SetValue
(
contentKeyMFASeed
,
resp
.
Seed
)
res
=
ssh
.
AuthPartiallySuccessful
}
else
{
re
s
=
ssh
.
AuthSuccessful
resp
,
err
:=
service
.
Authenticate
(
username
,
password
,
publicKey
,
remoteAddr
,
"T"
)
if
err
!=
nil
{
action
=
actionFailed
logger
.
Infof
(
"%s %s for %s from %s"
,
action
,
authMethod
,
username
,
remoteAddr
)
re
turn
}
if
resp
!=
nil
{
switch
resp
.
User
.
IsMFA
{
switch
resp
.
User
.
OTPLevel
{
case
0
:
res
=
ssh
.
AuthSuccessful
case
1
:
res
=
ssh
.
AuthPartiallySuccessful
case
2
:
case
1
,
2
:
action
=
actionPartialAccepted
res
=
ssh
.
AuthPartiallySuccessful
default
:
}
...
...
@@ -51,14 +51,12 @@ func checkAuth(ctx ssh.Context, password, publicKey string) (res ssh.AuthResult)
ctx
.
SetValue
(
cctx
.
ContextKeySeed
,
resp
.
Seed
)
ctx
.
SetValue
(
cctx
.
ContextKeyToken
,
resp
.
Token
)
}
logger
.
Infof
(
"%s %s for %s from %s"
,
action
,
authMethod
,
username
,
remoteAddr
)
return
res
}
func
CheckUserPassword
(
ctx
ssh
.
Context
,
password
string
)
ssh
.
AuthResult
{
res
:=
checkAuth
(
ctx
,
password
,
""
)
return
res
return
checkAuth
(
ctx
,
password
,
""
)
}
func
CheckUserPublicKey
(
ctx
ssh
.
Context
,
key
ssh
.
PublicKey
)
ssh
.
AuthResult
{
...
...
@@ -67,32 +65,40 @@ func CheckUserPublicKey(ctx ssh.Context, key ssh.PublicKey) ssh.AuthResult {
return
checkAuth
(
ctx
,
""
,
publicKey
)
}
func
CheckMFA
(
ctx
ssh
.
Context
,
challenger
gossh
.
KeyboardInteractiveChallenge
)
ssh
.
AuthResult
{
func
CheckMFA
(
ctx
ssh
.
Context
,
challenger
gossh
.
KeyboardInteractiveChallenge
)
(
res
ssh
.
AuthResult
)
{
username
:=
ctx
.
User
()
answers
,
err
:=
challenger
(
username
,
mfaInstruction
,
[]
string
{
mfaQuestion
},
[]
bool
{
true
})
if
err
!=
nil
{
return
ssh
.
AuthFailed
remoteAddr
:=
strings
.
Split
(
ctx
.
RemoteAddr
()
.
String
(),
":"
)[
0
]
res
=
ssh
.
AuthFailed
defer
func
()
{
authMethod
:=
"MFA"
if
res
==
ssh
.
AuthSuccessful
{
action
:=
actionAccepted
logger
.
Infof
(
"%s %s for %s from %s"
,
action
,
authMethod
,
username
,
remoteAddr
)
}
else
{
action
:=
actionFailed
logger
.
Errorf
(
"%s %s for %s from %s"
,
action
,
authMethod
,
username
,
remoteAddr
)
}
if
len
(
answers
)
!=
1
{
return
ssh
.
AuthFailed
}()
answers
,
err
:=
challenger
(
username
,
mfaInstruction
,
[]
string
{
mfaQuestion
},
[]
bool
{
true
})
if
err
!=
nil
||
len
(
answers
)
!=
1
{
return
}
mfaCode
:=
answers
[
0
]
seed
,
ok
:=
ctx
.
Value
(
c
ontentKeyMFA
Seed
)
.
(
string
)
seed
,
ok
:=
ctx
.
Value
(
c
ctx
.
ContextKey
Seed
)
.
(
string
)
if
!
ok
{
logger
.
Error
(
"Mfa Auth failed, may be user password or publickey auth failed"
)
return
ssh
.
AuthFailed
return
}
resp
,
err
:=
service
.
CheckUserOTP
(
seed
,
mfaCode
)
if
err
!=
nil
{
logger
.
Error
(
"Mfa Auth failed: "
,
err
)
return
ssh
.
AuthFailed
return
}
if
resp
.
Token
!=
""
{
return
ssh
.
AuthSuccessful
res
=
ssh
.
AuthSuccessful
return
}
return
ssh
.
AuthFailed
return
}
func
CheckUserNeedMFA
(
ctx
ssh
.
Context
)
(
methods
[]
string
)
{
...
...
pkg/common/client.go
View file @
8b06c4a1
...
...
@@ -85,7 +85,7 @@ func (c *Client) parseUrlQuery(url string, params []map[string]string) string {
return
url
}
func
(
c
*
Client
)
P
arseUrl
(
url
string
,
params
[]
map
[
string
]
string
)
string
{
func
(
c
*
Client
)
p
arseUrl
(
url
string
,
params
[]
map
[
string
]
string
)
string
{
url
=
c
.
parseUrlQuery
(
url
,
params
)
if
c
.
BaseHost
!=
""
{
url
=
strings
.
TrimRight
(
c
.
BaseHost
,
"/"
)
+
url
...
...
@@ -126,7 +126,7 @@ func (c *Client) SetReqHeaders(req *http.Request) {
}
func
(
c
*
Client
)
NewRequest
(
method
,
url
string
,
body
interface
{},
params
[]
map
[
string
]
string
)
(
req
*
http
.
Request
,
err
error
)
{
url
=
c
.
P
arseUrl
(
url
,
params
)
url
=
c
.
p
arseUrl
(
url
,
params
)
reader
,
err
:=
c
.
marshalData
(
body
)
if
err
!=
nil
{
return
...
...
pkg/handler/session.go
View file @
8b06c4a1
This diff is collapsed.
Click to expand it.
pkg/model/terminal.go
View file @
8b06c4a1
...
...
@@ -7,7 +7,7 @@ type Terminal struct {
Id
string
`json:"id"`
Name
string
`json:"name"`
AccessKey
struct
{
I
d
string
`json:"id"`
I
D
string
`json:"id"`
Secret
string
`json:"secret"`
}
`json:"access_key"`
}
`json:"service_account"`
...
...
pkg/model/users.go
View file @
8b06c4a1
...
...
@@ -25,15 +25,14 @@ type AuthResponse struct {
}
type
User
struct
{
I
d
string
`json:"id"`
I
D
string
`json:"id"`
Name
string
`json:"name"`
Username
string
`json:"username"`
Email
string
`json:"email"`
OTPLevel
int
`json:"otp_level"`
Role
string
`json:"role"`
IsValid
bool
`json:"is_valid"`
IsActive
bool
`json:"is_active"`
IsMFA
int
`json:"otp_level"`
OTPLevel
int
`json:"otp_level"`
}
type
TokenUser
struct
{
...
...
pkg/service/accesskey.go
View file @
8b06c4a1
...
...
@@ -20,7 +20,7 @@ var (
)
type
AccessKey
struct
{
I
d
string
I
D
string
Secret
string
Path
string
Value
string
...
...
@@ -29,7 +29,7 @@ type AccessKey struct {
func
(
ak
AccessKey
)
Sign
()
(
string
,
string
)
{
date
:=
common
.
HTTPGMTDate
()
signature
:=
common
.
MakeSignature
(
ak
.
Secret
,
date
)
return
date
,
fmt
.
Sprintf
(
"Sign %s:%s"
,
ak
.
I
d
,
signature
)
return
date
,
fmt
.
Sprintf
(
"Sign %s:%s"
,
ak
.
I
D
,
signature
)
}
func
(
ak
*
AccessKey
)
LoadAccessKeyFromStr
(
key
string
)
error
{
...
...
@@ -40,7 +40,7 @@ func (ak *AccessKey) LoadAccessKeyFromStr(key string) error {
if
len
(
keySlice
)
!=
2
{
return
AccessKeyInvalid
}
ak
.
I
d
=
keySlice
[
0
]
ak
.
I
D
=
keySlice
[
0
]
ak
.
Secret
=
keySlice
[
1
]
return
nil
}
...
...
@@ -74,7 +74,7 @@ func (ak *AccessKey) SaveToFile() error {
if
err
!=
nil
{
return
err
}
_
,
err
=
f
.
WriteString
(
fmt
.
Sprintf
(
"%s:%s"
,
ak
.
I
d
,
ak
.
Secret
))
_
,
err
=
f
.
WriteString
(
fmt
.
Sprintf
(
"%s:%s"
,
ak
.
I
D
,
ak
.
Secret
))
if
err
!=
nil
{
logger
.
Error
(
err
)
}
...
...
@@ -92,7 +92,7 @@ func (ak *AccessKey) Register(times int) error {
logger
.
Error
(
msg
)
os
.
Exit
(
1
)
}
ak
.
I
d
=
res
.
ServiceAccount
.
AccessKey
.
Id
ak
.
I
D
=
res
.
ServiceAccount
.
AccessKey
.
ID
ak
.
Secret
=
res
.
ServiceAccount
.
AccessKey
.
Secret
return
nil
}
...
...
pkg/service/perms.go
View file @
8b06c4a1
...
...
@@ -7,12 +7,12 @@ import (
"cocogo/pkg/model"
)
func
GetUserAssets
(
userI
d
,
cachePolicy
string
)
(
assets
model
.
AssetList
)
{
func
GetUserAssets
(
userI
D
,
cachePolicy
string
)
(
assets
model
.
AssetList
)
{
if
cachePolicy
==
""
{
cachePolicy
=
"0"
}
payload
:=
map
[
string
]
string
{
"cache_policy"
:
cachePolicy
}
Url
:=
fmt
.
Sprintf
(
UserAssetsURL
,
userI
d
)
Url
:=
fmt
.
Sprintf
(
UserAssetsURL
,
userI
D
)
err
:=
authClient
.
Get
(
Url
,
&
assets
,
payload
)
if
err
!=
nil
{
logger
.
Error
(
"GetUserAssets---err"
)
...
...
pkg/service/users.go
View file @
8b06c4a1
...
...
@@ -23,8 +23,7 @@ func Authenticate(username, password, publicKey, remoteAddr, loginType string) (
"remote_addr"
:
remoteAddr
,
"login_type"
:
loginType
,
}
Url
:=
client
.
ParseUrl
(
UserAuthURL
,
nil
)
err
=
client
.
Post
(
Url
,
data
,
&
resp
)
err
=
client
.
Post
(
UserAuthURL
,
data
,
&
resp
)
if
err
!=
nil
{
logger
.
Error
(
err
)
...
...
@@ -32,33 +31,8 @@ func Authenticate(username, password, publicKey, remoteAddr, loginType string) (
return
}
func
AuthenticateMFA
(
seed
,
code
,
loginType
string
)
(
resp
*
model
.
AuthResponse
,
err
error
)
{
/*
data = {
'seed': seed,
'otp_code': otp_code,
'login_type': login_type,
}
*/
data
:=
map
[
string
]
string
{
"seed"
:
seed
,
"otp_code"
:
code
,
"login_type"
:
loginType
,
}
Url
:=
client
.
ParseUrl
(
AuthMFAURL
,
nil
)
err
=
client
.
Post
(
Url
,
data
,
resp
)
if
err
!=
nil
{
logger
.
Error
(
err
)
}
return
}
func
GetUserProfile
(
userId
string
)
(
user
*
model
.
User
)
{
Url
:=
fmt
.
Sprintf
(
UserDetailURL
,
userId
)
func
GetUserProfile
(
userID
string
)
(
user
*
model
.
User
)
{
Url
:=
fmt
.
Sprintf
(
UserDetailURL
,
userID
)
err
:=
authClient
.
Get
(
Url
,
user
)
if
err
!=
nil
{
logger
.
Error
(
err
)
...
...
@@ -98,9 +72,9 @@ func CheckUserOTP(seed, code string) (resp *AuthResp, err error) {
return
}
func
CheckUserCookie
(
sessionI
d
,
csrfToken
string
)
(
user
*
model
.
User
)
{
func
CheckUserCookie
(
sessionI
D
,
csrfToken
string
)
(
user
*
model
.
User
)
{
client
.
SetCookie
(
"csrftoken"
,
csrfToken
)
client
.
SetCookie
(
"sessionid"
,
sessionI
d
)
client
.
SetCookie
(
"sessionid"
,
sessionI
D
)
err
:=
client
.
Get
(
UserProfileURL
,
&
user
)
if
err
!=
nil
{
logger
.
Error
(
err
)
...
...
pkg/webssh/handler.go
View file @
8b06c4a1
...
...
@@ -28,7 +28,7 @@ func AuthDecorator(handler http.HandlerFunc) http.HandlerFunc {
}
}
user
:=
service
.
CheckUserCookie
(
sessionid
,
csrfToken
)
if
user
.
I
d
==
""
{
if
user
.
I
D
==
""
{
// Todo: 构建login的url
http
.
Redirect
(
responseWriter
,
request
,
""
,
http
.
StatusFound
)
return
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment