1.问题描述
公司的 mongodb 使用非认证模式;不需要用户名密码连接;给客服部署时也使用非认证模式;然后客户那边通过漏洞扫描提示:【Mongodb未授权访问谢洞[原理扫描]】根据教程添加上用户名密码后,Navicat连接工具可以连接,但Java后台报错如图:
代码如下:
org.springframework.web.util.NestedServletException: Request processing failed; nested exception is org.springframework.data.mongodb.CannotGetMongoDbConnectionException: Failed to authenticate to database [aaa], username = [bbbb], password = [cc****ccc]
at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:948)
at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:827)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:620)
at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:812)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:727)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:303)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208)
at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:330)
at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.invoke(FilterSecurityInterceptor.java:118)
at org.springframework.security.web.access.intercept.FilterSecurityInterceptor.doFilter(FilterSecurityInterceptor.java:84)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.haze.base.web.filter.PermissionFilter.invoke(PermissionFilter.java:39)
at org.haze.base.web.filter.PermissionFilter.doFilter(PermissionFilter.java:24)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:113)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.session.SessionManagementFilter.doFilter(SessionManagementFilter.java:103)
at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:342)
at org.springframework.security.web.authentication.AnonymousAuthenticationFilter.doFilter(AnonymousAuthenticationFilter.java:113)
网上多处查找一天,有说 驱动不兼容问题 、 版本对应问题、 配置问题 ;首先我不说方法不对,或许他们遇到的问题可以解决,反正没有解决我的问题。
2.开发环境
- mongodbVersion:3.6.9
- javaversion:8 (编译级别7)
- springFramwork:3.2.5.RELEASE
- spring-data-mongodb:1.3.4.RELEASE
- mongo-java-driver:2.10.1
3.资料搜索
经过一天头疼的搜索尝试,在windows本地搭建搭建mongo服务模拟复现,在mongo控制台看见这么一个日志提示:
SASL SCRAM-SHA-1 authentication failed for nls-cloud on admin from client 172.0.0.1:14500 ; UserNotFound: Could not find user nls-cloud@admin
再结合之前看到的 MongoDB 3.X SCRAM-SHA-1认证
突然茅塞顿开,可能是认证机制不同导致;
结合这篇文章:mongodb3.03以上开启认证,解决程序认证连接报错以及第三方客户端无法认证问题:https://blog.csdn.net/ll657418802/article/details/50846313
终于是解决了;什么版本冲突、配置修改统统回滚;
4.解决过程
1.首先以非认证方式重启mongo服务;
> mongod --dbpath /usr/data/MongoDB/data
2.连接后切换到admin
> mongo
MongoDB shell version v3.6.23
connecting to: mongodb://127.0.0.1:27017/?gssapiServiceName=mongodb
Implicit session: session { "id" : UUID("ac4c4aae-49a6-4adf-aab5-9d2237a2bc02") }
MongoDB server version: 3.6.23
>use admin
switched to db admin
3.查看当前认证方式
>db.system.version.findOne({"_id" : "authSchema"})
{ "_id" : "authSchema", "currentVersion" : 5 }
说明:
5:SCRAM-SHA-1
3:MONGODB-CR
3.0之后新增SCRAM-SHA-1 但是Java驱动默认为MONGODB-CR 需要改为 3
4.修改之前需要先删除所有用户 (包括admin 和 自己的数据库 )
> db.dropAllUser()
> use mydatabase
switched to db mydatabase
> db.dropAllUser()
5.回到admin (*一定要切换到admin)修改认证方式
> use admin
switched to db admin
> var schema = db.system.version.findOne({"_id" : "authSchema"})
> schema.currentVersion = 3
3
> db.system.version.save(schema)
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })
返回 nModified:1 才算此修改成功
6.(建议重启服务后)重新创建用户
-- 在admin创建超级管理账户
> use admin
switched to db admin
> db.updateUser("root", {
roles: [
{
role: "root",
db: "admin"
},
{
role: "userAdminAnyDatabase",
db: "admin"
}
]
})
Successfully added user: {
"user" : "root",
"roles" : [
{
"role" : "root",
"db" : "admin"
},
{
"role" : "userAdminAnyDatabase",
"db" : "admin"
}
]
}
-- 切换到自己的数据库创建读写账户
>use mydatabase
switched to db mydatabase
>db.createUser(
{
user: "myuser",
pwd: "mypassword",
roles: [ { role: "readWrite", db: "mydatabase" } ]
}
)
Successfully added user: {
"user" : "myuser",
"roles" : [
{
"role" : "readWrite",
"db" : "mydatabase"
}
]
}
7.最后以认证方式重启服务器就可以了
mongod --dbpath /usr/data/MongoDB/data --uauth
命令添加 --auth
conf配置文件 添加或修改
auth=true