Permalink
Browse files

SEVER-394 remove overwrite field name in place mode, as this can caus…

…e field ordering to differ between master and slave
  • Loading branch information...
1 parent 2895525 commit e74fae251d4b2d581c00e10163c01a4c0ee267bc @astaple astaple committed Sep 29, 2010
Showing with 35 additions and 39 deletions.
  1. +0 −4 db/jsobjmanipulator.h
  2. +2 −27 db/update.cpp
  3. +18 −1 dbtests/repltests.cpp
  4. +15 −7 jstests/rename4.js
@@ -103,10 +103,6 @@ namespace mongo {
}
}
}
-
- void rewriteFieldName( const char *name ) {
- strcpy( data() + 1, name );
- }
private:
char *data() { return nonConst( _element.rawdata() ); }
char *value() { return nonConst( _element.value() ); }
View
@@ -346,29 +346,6 @@ namespace mongo {
return !obj.getField( path ).eoo();
}
- bool nameRewritePossible( const char *a, const char *b ) {
- const char *ar = strrchr( a, '.' );
- const char *br = strrchr( b, '.' );
- if ( ar && br ) {
- if ( ( ar - a ) != ( br - b ) ) {
- return false;
- }
- if ( strncmp( a, b, ar - a ) != 0 ) {
- return false;
- }
- if ( strlen( ar ) != strlen( br ) ) {
- return false;
- }
- } else if ( !ar && !br ) {
- if ( strlen( a ) != strlen( b ) ) {
- return false;
- }
- } else {
- return false;
- }
- return true;
- }
-
auto_ptr<ModSetState> ModSet::prepare(const BSONObj &obj) const {
DEBUGUPDATE( "\t start prepare" );
ModSetState * mss = new ModSetState( obj );
@@ -400,7 +377,7 @@ namespace mongo {
int target = validRenamePath( obj, m.fieldName );
uassert( 13490, "$rename target field invalid", target != -1 );
ms.newVal = obj.getFieldDotted( m.renameFrom() );
- mss->amIInPlacePossible( target == 0 && nameRewritePossible( m.renameFrom(), m.fieldName ) );
+ mss->amIInPlacePossible( false );
} else {
ms.dontApply = true;
}
@@ -564,12 +541,10 @@ namespace mongo {
case Mod::PULL_ALL:
case Mod::ADDTOSET:
case Mod::RENAME_FROM:
+ case Mod::RENAME_TO:
// this should have been handled by prepare
break;
// [dm] the BSONElementManipulator statements below are for replication (correct?)
- case Mod::RENAME_TO:
- BSONElementManipulator( m.newVal ).rewriteFieldName( m.m->shortFieldName );
- break;
case Mod::INC:
m.m->IncrementMe( m.old );
m.fixedOpName = "$set";
View
@@ -972,7 +972,7 @@ namespace ReplTests {
}
};
- class RenameOverwrite : public Base {
+ class RenameReplace : public Base {
public:
void doIt() const {
client()->update( ns(), BSON( "_id" << 0 ), fromjson( "{$rename:{a:'b'}}" ) );
@@ -988,6 +988,22 @@ namespace ReplTests {
insert( fromjson( "{'_id':0,a:3,b:100}" ) );
}
};
+
+ class RenameOverwrite : public Base {
+ public:
+ void doIt() const {
+ client()->update( ns(), BSON( "_id" << 0 ), fromjson( "{$rename:{a:'b'}}" ) );
+ }
+ using ReplTests::Base::check;
+ void check() const {
+ ASSERT_EQUALS( 1, count() );
+ check( BSON( "_id" << 0 << "b" << 3 << "z" << 1 ) , one( fromjson( "{'_id':0}" ) ) );
+ }
+ void reset() const {
+ deleteAll( ns() );
+ insert( fromjson( "{'_id':0,z:1,a:3}" ) );
+ }
+ };
class NoRename : public Base {
public:
@@ -1190,6 +1206,7 @@ namespace ReplTests {
add< Idempotence::PopReverse >();
add< Idempotence::BitOp >();
add< Idempotence::Rename >();
+ add< Idempotence::RenameReplace >();
add< Idempotence::RenameOverwrite >();
add< Idempotence::NoRename >();
add< DeleteOpIsIdBased >();
View
@@ -85,29 +85,37 @@ v( {a:{b:1}}, {$rename:{'a.b':'d'}}, {a:{},d:1} );
v( {a:[5]}, {$rename:{a:'b'}}, {b:[5]} );
v( {aa:[5]}, {$rename:{aa:'b'}}, {b:[5]} );
v( {'0':1}, {$rename:{'0':'5'}}, {'5':1} );
-v( {a:1,b:2}, {$rename:{a:'c'},$set:{b:5}}, {c:1,b:5} );
+v( {a:1,b:2}, {$rename:{a:'c'},$set:{b:5}}, {b:5,c:1} );
v( {aa:1,b:2}, {$rename:{aa:'c'},$set:{b:5}}, {b:5,c:1} );
v( {a:1,b:2}, {$rename:{z:'c'},$set:{b:5}}, {a:1,b:5} );
v( {aa:1,b:2}, {$rename:{z:'c'},$set:{b:5}}, {aa:1,b:5} );
+// (formerly) rewriting single field
+v( {a:{z:1,b:1}}, {$rename:{'a.b':'a.c'}}, {a:{c:1,z:1}} );
+v( {a:{z:1,tomato:1}}, {$rename:{'a.tomato':'a.potato'}}, {a:{potato:1,z:1}} );
+v( {a:{z:1,b:1,c:1}}, {$rename:{'a.b':'a.c'}}, {a:{c:1,z:1}} );
+v( {a:{z:1,tomato:1,potato:1}}, {$rename:{'a.tomato':'a.potato'}}, {a:{potato:1,z:1}} );
+v( {a:{z:1,b:1}}, {$rename:{'a.b':'a.cc'}}, {a:{cc:1,z:1}} );
+v( {a:{z:1,b:1,c:1}}, {$rename:{'a.b':'aa.c'}}, {a:{c:1,z:1},aa:{c:1}} );
+
// invalid target, but missing source
v( {a:1,c:4}, {$rename:{b:'c.d'}}, {a:1,c:4} );
// check index
t.drop();
t.ensureIndex( {a:1} );
-function l( start, mod, expected ) {
+function l( start, mod, query, expected ) {
t.remove();
t.save( start );
t.update( {}, mod );
assert( !db.getLastError() );
- var got = t.find().hint( {a:1} ).next();
+ var got = t.find( query ).hint( {a:1} ).next();
delete got._id;
assert.eq( expected, got );
}
-l( {a:1}, {$rename:{a:'b'}}, {b:1} );
-l( {a:1}, {$rename:{a:'bb'}}, {bb:1} );
-l( {b:1}, {$rename:{b:'a'}}, {a:1} );
-l( {bb:1}, {$rename:{bb:'a'}}, {a:1} );
+l( {a:1}, {$rename:{a:'b'}}, {a:null}, {b:1} );
+l( {a:1}, {$rename:{a:'bb'}}, {a:null}, {bb:1} );
+l( {b:1}, {$rename:{b:'a'}}, {a:1}, {a:1} );
+l( {bb:1}, {$rename:{bb:'a'}}, {a:1}, {a:1} );

0 comments on commit e74fae2

Please sign in to comment.