How to connect to mongoDB via ssl using .crt file in Go

huangapple go评论81阅读模式
英文:

How to connect to mongoDB via ssl using .crt file in Go

问题

我正在尝试使用.crt文件连接到托管在Azure上的Mongo数据库。

我可以成功地从我的Linux机器终端使用以下命令连接:

mongo mongodb://username:password@prod-replicaset-0.com:27017,prod-replicaset-1.com:27017,prod-replicaset-2.com:27017/ --tls --tlsCAFile rootca.crt --tlsAllowInvalidCertificates

我还可以通过设置"Use SSL protocol"并将认证机制设置为"SCRAM-SHA-256"来从Mongo UI客户端(如Robo3T)连接。
[如果将认证机制设置为其他值,将导致身份验证失败]

但是,我无法在Go语言代码中连接到该数据库。

这是我正在使用的代码示例:

package main

import (
	"crypto/tls"
	"crypto/x509"
	"io/ioutil"
	"log"
	"net"

	"github.com/globalsign/mgo"
)

func InitMongo() error {

	rootCerts := x509.NewCertPool()
	ca, err := ioutil.ReadFile("./rootca.crt")
	if err != nil {
		log.Fatalf("failed to read file : %s", err.Error())
		return err
	}

	success := rootCerts.AppendCertsFromPEM(ca)
	if !success {
		log.Printf("rootcert failed")
	}

	connStr := "mongodb://username:password@prod-replicaset-0.com:27017,prod-replicaset-1.com:27017,prod-replicaset-2.com:27017/?ssl=true"

	dbDialInfo, err := mgo.ParseURL(connStr)
	if err != nil {
		log.Fatal("unable to parse url - " + err.Error())
	}

	dbDialInfo.DialServer = func(addr *mgo.ServerAddr) (net.Conn, error) {
		return tls.Dial("tcp", addr.String(), &tls.Config{
			RootCAs:            rootCerts,
			InsecureSkipVerify: true,
		})
	}

	// dbDialInfo.Mechanism = "SCRAM-SHA-256"

	_session, err := mgo.DialWithInfo(dbDialInfo)
	if err != nil {
		log.Fatalf("failed to creating db session : %s", err.Error())
		return err
	}

	log.Printf("Created session - %v", _session)

	return nil
}

当我运行此代码时,我收到错误消息:
failed to creating db session : "server returned error on SASL authentication step: Authentication failed."

如果在创建会话之前设置[dbDialInfo.Mechanism = "SCRAM-SHA-256"],我收到错误消息:
failed to creating db session : "SASL support not enabled during build (-tags sasl)"

请告诉我是什么原因导致了这个问题,我该如何连接到数据库。
目前我正在使用"github.com/globalsign/mgo",如果需要使用其他库,对我来说完全没问题。
我只想连接到数据库。

rootca.crt文件的内容如下:

-----BEGIN CERTIFICATE-----
MIIGLjCCBBagAwIBAgIUbxINX1qe6W+7kolWGp+MX8NbYj8wDQYJKoZIhvcNAQEL
<blah> <blah> <blah> <blah> <blah> <blah> <blah> <blah> <blah> <blah> 
jCZAGGHmbrR3zeIsOY8yKau0IXqRp5Wy6NQ0poOTcma9BfwNUVc4/ixsCkEVYbgW
eMs=
-----END CERTIFICATE-----

谢谢。

英文:

I am trying to connect to a mongo database hosted in azure using the .crt file.

I am successfully able to connect from my linux machine terminal using command:

mongo mongodb://username:password@prod-replicaset-0.com:27017,prod-replicaset-1.com:27017,prod-replicaset-2.com:27017/ --tls --tlsCAFile rootca.crt --tlsAllowInvalidCertificates

I am also able to connect from mongo UI client like robo3T by setting "Use SSL protocol" and using Auth Mechanism as "SCRAM-SHA-256".
[If I set Auth Mechanism to any other value, results in Authentication Failure]

But I am not able to connect to that database in Go lang code.

Here is a sample of code I am using:

package main

import (
	&quot;crypto/tls&quot;
	&quot;crypto/x509&quot;
	&quot;io/ioutil&quot;
	&quot;log&quot;
	&quot;net&quot;

	&quot;github.com/globalsign/mgo&quot;
)

func InitMongo() error {

	rootCerts := x509.NewCertPool()
	ca, err := ioutil.ReadFile(&quot;./rootca.crt&quot;)
	if err != nil {
		log.Fatalf(&quot;failed to read file : %s&quot;, err.Error())
		return err
	}

	success := rootCerts.AppendCertsFromPEM(ca)
	if !success {
		log.Printf(&quot;rootcert failed&quot;)
	}

	connStr := &quot;mongodb://username:password@prod-replicaset-0.com:27017,prod-replicaset-1.com:27017,prod-replicaset-2.com:27017/?ssl=true&quot;

	dbDialInfo, err := mgo.ParseURL(connStr)
	if err != nil {
		log.Fatal(&quot;unable to parse url - &quot; + err.Error())
	}

	dbDialInfo.DialServer = func(addr *mgo.ServerAddr) (net.Conn, error) {
		return tls.Dial(&quot;tcp&quot;, addr.String(), &amp;tls.Config{
			RootCAs:            rootCerts,
			InsecureSkipVerify: true,
		})
	}

	// dbDialInfo.Mechanism = &quot;SCRAM-SHA-256&quot;

	_session, err := mgo.DialWithInfo(dbDialInfo)
	if err != nil {
		log.Fatalf(&quot;failed to creating db session : %s&quot;, err.Error())
		return err
	}

	log.Printf(&quot;Created session - %v&quot;, _session)

	return nil
}

When I run this code, I get error:
failed to creating db session : "server returned error on SASL authentication step: Authentication failed."

If I set [dbDialInfo.Mechanism = "SCRAM-SHA-256"] before creating session, I get error:
failed to creating db session : "SASL support not enabled during build (-tags sasl)"

Please let me know what is causing this issue, how can I connect to the database.
Currently I am using "github.com/globalsign/mgo", if it required to use any other library, that's totally fine for me.
I just want to get connected to the db.

rootca.crt file looks something like:

-----BEGIN CERTIFICATE-----
MIIGLjCCBBagAwIBAgIUbxINX1qe6W+7kolWGp+MX8NbYj8wDQYJKoZIhvcNAQEL
&lt;blah&gt; &lt;blah&gt; &lt;blah&gt; &lt;blah&gt; &lt;blah&gt; &lt;blah&gt; &lt;blah&gt; &lt;blah&gt; &lt;blah&gt; 
jCZAGGHmbrR3zeIsOY8yKau0IXqRp5Wy6NQ0poOTcma9BfwNUVc4/ixsCkEVYbgW
eMs=
-----END CERTIFICATE-----

Thank you.

答案1

得分: 0

经过大量研究,我无法找到使用globalsign库连接到mongodb的方法,使用.crt文件。

但是,我成功地使用mongo-driver库实现了这一点。
这里的连接字符串可以采用以下格式:

mongodb://user:password@replicaset-0.com:27017,replicaset-1.com:27017,replicaset-2.com:27017/?ssl=true&amp;tlsCAFile=./ca.crt&amp;tlsCertificateKeyFile=./ca.pem&amp;authSource=admin&amp;replicaSet=replicaset

示例代码:

import (
	"context"
	"log"
	"os"

	// "github.com/globalsign/mgo"
	mgo "go.mongodb.org/mongo-driver/mongo"

	mongoOptions "go.mongodb.org/mongo-driver/mongo/options"
)

func InitMongo() error {

	connStr := os.Getenv("MONGODB_CONN_STR")
	dbName := os.Getenv("MONGODB_DATABASE")

	clientOpts := mongoOptions.Client().ApplyURI(connStr)
	if err := clientOpts.Validate(); err != nil {
		log.Print("无法解析URL")
		log.Fatal(err)
	}
	client, err := mgo.Connect(context.TODO(), clientOpts)
	if err != nil {
		log.Print("无法连接到数据库")
		log.Fatal(err)
	}
	if err := client.Ping(context.TODO(), nil); err != nil {
		log.Print("数据库ping失败")
		log.Fatal(err)
	}

	//client.Database(dbName)

	return nil
}
英文:

After researching a lot, I was not able to find a way to connect to mongodb using .crt file using globalsign library.

However I was successfully able to do this using mongo-driver library.
here connection string can be of format:

mongodb://user:password@replicaset-0.com:27017,replicaset-1.com:27017,replicaset-2.com:27017/?ssl=true&amp;tlsCAFile=./ca.crt&amp;tlsCertificateKeyFile=./ca.pem&amp;authSource=admin&amp;replicaSet=replicaset

Sample code:

import (
	&quot;context&quot;
	&quot;log&quot;
	&quot;os&quot;

	// &quot;github.com/globalsign/mgo&quot;
	mgo &quot;go.mongodb.org/mongo-driver/mongo&quot;

	mongoOptions &quot;go.mongodb.org/mongo-driver/mongo/options&quot;
)
func InitMongo() (error) {
	
	connStr := os.Getenv(&quot;MONGODB_CONN_STR&quot;)
	dbName := os.Getenv(&quot;MONGODB_DATABASE&quot;)

	clientOpts := mongoOptions.Client().ApplyURI(connStr)
	if err := clientOpts.Validate(); err != nil {
		log.Print(&quot;unable to parse url&quot;)
		log.Fatal(err)
	}
	client, err := mgo.Connect(context.TODO(), clientOpts)
	if err != nil {
		log.Print(&quot;unable to connect into database&quot;)
		log.Fatal(err)
	}
	if err := client.Ping(context.TODO(), nil); err != nil {
		log.Print(&quot;database ping failed&quot;)
		log.Fatal(err)
	}

	//client.Database(dbName)

	return nil
}

huangapple
  • 本文由 发表于 2021年9月23日 19:17:38
  • 转载请务必保留本文链接:https://go.coder-hub.com/69298986.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定