连接后 mongobee 在 Atlas 集群上读取 DBname.system.indexes 失败

Reading of DBname.system.indexes failed on Atlas cluster by mongobee after getting connected

我有一个 Jhipster Spring 启动项目。最近我从 mlabs 独立沙箱转移到 Atlas 集群沙箱 M0 免费层副本集。它甚至可以工作,我已经对它进行了一些数据库操作。但是现在由于某种原因出现了读取权限错误

Error creating bean with name 'mongobee' defined in class path resource [DatabaseConfiguration.class]: Invocation of init method failed; nested exception is com.mongodb.MongoQueryException: Query failed with error code 8000 and error message 'user is not allowed to do action [find] on [test.system.indexes]' on server ********-shard-00-01-mfwhq.mongodb.net:27017

你可以在这里看到完整的堆栈https://pastebin.com/kaxcr7VS

我到处搜索,我所能找到的只是 M0 层用户没有覆盖管理数据库的权限,而我没有这样做。

即使现在连接到 Mlabs DB 也能正常工作,但在 Atlas DB M0 层上有这个问题。

Mongo 数据库版本:3.4

Jars 及其版本 名称:'mongobee',版本:'0.10' 名称:'mongo-java-driver',版本:'3.4.2'

@Neil Lunn 我用来连接的 userId 是管理员的,连接读写通过 shell 或 Robo3T(mongo client)

进行

在与 MongoDB 支持团队讨论后,MongoDB 3.0 反对直接访问 system.indexes 集合,该集合以前用于列出数据库中的所有索引。应用程序应改用 db.<COLLECTION>.getIndexes()

MongoDB Atlas docs可以看出,他们可能会禁止调用system.个集合:

Optionally, for the read and readWrite role, you can also specify a collection. If you do not specify a collection for read and readWrite, the role applies to all collections (excluding some system. collections) in the database.

从堆栈跟踪可以看出,MongoBee 正在尝试进行此调用,所以现在是库问题,应该进行更新。

更新: 为了在 MongoBee 发布新版本之前解决问题:

  1. 获取 MongoBee git clone git@github.com:mongobee/mongobee.gitcd mongobee
  2. 的最新来源
  3. 获取拉取请求git fetch origin pull/87/head:mongobee-atlas
  4. 结帐git checkout mongobee-atlas
  5. 安装 MongoBee jar mvn clean install
  6. /target文件夹或本地/.m2
  7. 获取编译好的jar
  8. 使用 jar 作为项目的依赖项

今天早上遇到了这个问题。这是针对该问题的快速而肮脏的猴子补丁:

package com.github.mongobee.dao;

import com.github.mongobee.changeset.ChangeEntry;
import com.mongodb.BasicDBObject;
import com.mongodb.DB;
import com.mongodb.DBCollection;
import com.mongodb.DBObject;

import java.util.List;

import static com.github.mongobee.changeset.ChangeEntry.CHANGELOG_COLLECTION;

public class ChangeEntryIndexDao {

    public void createRequiredUniqueIndex(DBCollection collection) {
        collection.createIndex(new BasicDBObject()
                        .append(ChangeEntry.KEY_CHANGEID, 1)
                        .append(ChangeEntry.KEY_AUTHOR, 1),
                new BasicDBObject().append("unique", true));
    }

    public DBObject findRequiredChangeAndAuthorIndex(DB db) {
        DBCollection changelogCollection = db.getCollection(CHANGELOG_COLLECTION);
        List<DBObject> indexes = changelogCollection.getIndexInfo();
        if (indexes == null) return null;
        for (DBObject index : indexes) {
            BasicDBObject indexKeys = ((BasicDBObject) index.get("key"));
            if (indexKeys != null && (indexKeys.get(ChangeEntry.KEY_CHANGEID) != null && indexKeys.get(ChangeEntry.KEY_AUTHOR) != null)) {
                return index;
            }
        }
        return null;
    }

    public boolean isUnique(DBObject index) {
        Object unique = index.get("unique");
        if (unique != null && unique instanceof Boolean) {
            return (Boolean) unique;
        } else {
            return false;
        }
    }

    public void dropIndex(DBCollection collection, DBObject index) {
        collection.dropIndex(index.get("name").toString());
    }

}
Caused by: java.lang.NoSuchMethodError: com.github.mongobee.dao.ChangeEntryIndexDao.<init>(Ljava/lang/String;)V
    at com.github.mongobee.dao.ChangeEntryDao.<init>(ChangeEntryDao.java:34)
    at com.github.mongobee.Mongobee.<init>(Mongobee.java:87)
    at com.xxx.proj.config.DatabaseConfiguration.mongobee(DatabaseConfiguration.java:62)
    at com.xxx.proj.config.DatabaseConfiguration$$EnhancerBySpringCGLIB$ae465a5.CGLIB$mongobee(<generated>)
    at com.xxx.proj.config.DatabaseConfiguration$$EnhancerBySpringCGLIB$ae465a5$$FastClassBySpringCGLIB$$f202afb.invoke(<generated>)
    at org.springframework.cglib.proxy.MethodProxy.invokeSuper(MethodProxy.java:228)
    at org.springframework.context.annotation.ConfigurationClassEnhancer$BeanMethodInterceptor.intercept(ConfigurationClassEnhancer.java:358)
    at com.xxx.proj.config.DatabaseConfiguration$$EnhancerBySpringCGLIB$ae465a5.mongobee(<generated>)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:498)
    at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:162)
    ... 22 common frames omitted

jhipster 5 必须使用不同的版本,因为我在实现上述代码时得到了它。看起来它期待一个不同的版本。

system.indexes 的访问是 open issue in mongobee。该问题已在项目中修复,但该项目在修复发布之前就被放弃了。

由于这个项目被放弃,两个后继库已经从 mongobee 中分叉出来并解决了这个问题:Mongock and mongobeeJ.

将应用程序的依赖项从 mongobee 库切换到这些后继库之一将使您能够 运行 在 Atlas 上迁移 mongobee 数据库。

总结这些库:

  • Mongock - 2018 年从 mongobee 分叉出来。积极维护。与原始版本相比有了显着的改进,包括 built-in 对 Spring、Spring 引导的支持,以及 Mongo Java 驱动程序的第 3 版和第 4 版。
  • mongobeeJ - 2018 年从 mongobee 分叉出来。已经发布了五个更新版本。原始猫鼬的最小进化。 Mongo Java Driver 4 支持已于 2020 年 8 月实施。该项目已于 2020 年 8 月弃用,其创建者建议改用 Mongock 等库。