web-dev-qa-db-ja.com

mongodbドキュメントの部分文字列を置換する方法

次の形式のコレクションに多くのmongodbドキュメントがあります。

{
....
"URL":"www.abc.com/helloWorldt/..."
.....
}

helloWorldthelloWorldに置き換えて取得したい:

{
....
"URL":"www.abc.com/helloWorld/..."
.....
}

コレクション内のすべてのドキュメントでこれを実現するにはどうすればよいですか?

54
user1071979
db.media.find({mediaContainer:"ContainerS3"}).forEach(function(e,i) {
    e.url=e.url.replace("//a.n.com","//b.n.com");
    db.media.save(e);
});
98
Naveed

現在、フィールドの値を使用して更新することはできません。そのため、ドキュメントを反復処理し、関数を使用して各ドキュメントを更新する必要があります。ここでそれを行う方法の例があります。 MongoDB:同じドキュメントのデータを使用してドキュメントを更新する

8
Louisa

nodejs。 npmからのmongodbパッケージ の使用

db.collection('ABC').find({url: /helloWorldt/}).toArray((err, docs) => {
  docs.forEach(doc => {
    let URL = doc.URL.replace('helloWorldt', 'helloWorld');
    db.collection('ABC').updateOne({_id: doc._id}, {URL});
  });
});
5
Lukas

[〜#〜] all [〜#〜]文書内の部分文字列の出現を置き換えるには、次を使用します。

db.media.find({mediaContainer:"ContainerS3"}).forEach(function(e,i) {
var find = "//a.n.com";
var re = new RegExp(find, 'g');
e.url=e.url.replace(re,"//b.n.com");
db.media.save(e);
});
5

_Mongo 4.2_を開始すると、 db.collection.update() は集約パイプラインを受け入れ、最終的に別のフィールドに基づいてフィールドの更新を許可できます。

_// { URL: "www.abc.com/helloWorldt/..." }
// { URL: "www.abc.com/HelloWo/..." }
db.collection.update(
  { URL: { $regex: "/helloWorldt/" } },
  [{
    $set: { URL: {
      $concat: [
        { $arrayElemAt: [ { $split: [ "$URL", "/helloWorldt/" ] }, 0 ] },
        "/helloWorld/",
        { $arrayElemAt: [ { $split: [ "$URL", "/helloWorldt/" ] }, 1 ] }
      ]
    }}
  }],
  { multi: true }
)
// { URL: "www.abc.com/helloWorld/..." }
// { URL: "www.abc.com/HelloWo/..." }
_

適切な文字列_$replace_演算子がまだないため、これは少し冗長です。

  • 最初の部分_{ URL: { $regex: "/helloWorldt/" } }_は、更新するドキュメント(hello worldのスペルが間違っているドキュメント)をフィルタリングする一致クエリです。

  • 2番目の部分_[{ $set: { URL: ... } }]_は、更新集計パイプラインです(集計パイプラインの使用を示す角括弧に注意してください)。 _$set_ は、この場合、フィールドを作成/置換する新しい集計演算子です。新しい値は、_$concat_と_$split_の混合を使用して、適切な文字列_$replace_演算子がないために奇妙に計算されます。 URLが独自の値(_$URL_)に基づいて直接変更される方法に注意してください。

  • _{ multi: true }_を忘れないでください。そうしないと、最初に一致したドキュメントのみが更新されます。

3
Xavier Guihot

選択した回答(@Naveedの回答)へのコメントの書式設定が乱れているため、これを回答として追加します。すべてのクレジットはNaveedに送られます。

-------------------------------------------------- --------------------

ただすごい。私の場合は-配列であるフィールドがあるので、余分なループを追加する必要がありました。

私のクエリは次のとおりです。

db.getCollection("profile").find({"photos": {$ne: "" }}).forEach(function(e,i) {
    e.photos.forEach(function(url, j) {
        url = url.replace("http://a.com", "https://dev.a.com");
        e.photos[j] = url;
    });
    db.getCollection("profile").save(e);
    eval(printjson(e));
})
3
Himel Nag Rana

今、あなたはそれをすることができます!

Mongoスクリプトを使用して、オンザフライでデータを操作できます。わたしにはできる!

このスクリプトを使用して、住所データを修正します。

現在の住所の例:「No.12、FIFTH AVENUE」。

最後の冗長なコンマ、予想される新しいアドレス「 "No.12、FIFTH AVENUE"」を削除したい。

var cursor = db.myCollection.find().limit(100);

while (cursor.hasNext()) {
  var currentDocument = cursor.next();

  var address = currentDocument['address'];
  var lastPosition = address.length - 1;

  var lastChar = address.charAt(lastPosition);

  if (lastChar == ",") {

    var newAddress = address.slice(0, lastPosition);


    currentDocument['address'] = newAddress;

    db.localbizs.update({_id: currentDocument._id}, currentDocument);

  }
}

お役に立てれば!

1
Dac Nguyen

ここの回答の例を使用して、置換スクリプトを実行するときに「更新済みの既存レコード0」を取得する場合に備えて、クライアントが変更を保存/書き込みできるプライマリMongoDBノードに接続されているかどうかを確認してください。

0

Mongodump、bsondumpおよびmongoimportを使用します。

時々、mongodbコレクションは、ネストされた配列/オブジェクトなどでループを構築するのが比較的難しい場合に、少し複雑になることがあります。私の回避策はちょっと生ですが、コレクションの複雑さに関係なく、ほとんどのシナリオで動作します。

1。mongodumpを使用して.bsonにコレクションをエクスポート

mongodump --db=<db_name> --collection=<products> --out=data/

2。bsondumpを使用して.bsonを.json形式に変換

bsondump --outFile products.json data/<db_name>/products.bson

。jsonファイルの文字列をsed(Linuxターミナルの場合)または他のツールで置き換えます

sed -i 's/oldstring/newstring/g' products.json

4。インポートする前にコレクションを削除する--dropタグを付けたmongoimportで.jsonコレクションをインポートして戻します

mongoimport --db=<db_name>  --drop --collection products <products.json

または、mongoimportとmongodumpの両方の接続に--uriを使用できます

mongodump --uri "mongodb://mongoadmin:[email protected]:27017,10.148.0.8:27017,10.148.0.9:27017/my-dbs?replicaSet=rs0&authSource=admin" --collection=products --out=data/
0
Ry Van