해당 오류 로그 관련해서 아무리 구글링을 해봐도,

'corruption이 발생했다' 외의 다른 정확한 원인이나 원인을 찾아내는 정보를 알 수 없었음.

그냥 빨리 조치를 취하는 수 밖에 없을 것 같다.

조치순서는 아래와 같다.



1. 서버들의 로그를 뒤져서 해당 오류가 발생한 서버를 빨리 찾을 것.


2. 오류가 발생한 서버의 local에 mongo로 접속하여 shutdown 시킴. (rolling upgrade 하듯이)

// 인증

shard_00X:PRIMARY> use admin

shard_00X:PRIMARY> db.auth('ROOT','비밀번호')

// stepdown

shard_00X:PRIMARY> rs.stepDown()

// stepdown이 실패할 경우 그냥 shell로 나가서 kill로 죽여 강제로 failover가 일어나도록 하는 수 밖에 없음


// stepdown이 성공했을 경우 정상적으로 shutdown

shard_00X:SECONDARY> use admin

shard_00X:SECONDARY> db.shutdownServer()



일단 여기까지 해서 failover가 되면 기능은 정상동작 한다.



3. replSet에 포함시키지 않고 standalone으로 해당 서버를 올린 후 oplog 정리

// 인증

mongo> use admin

mongo> db.auth('ROOT','비밀번호')

mongo> use local

// local.oplog.rs에 뭔가를 할 수 있는 상황인지 체크

mongo> db.oplog.rs.findOne()

 

// 뭔가 가능하다면 마지막 oplog를 남겨서 어떻게든 유실을 최소화 해보자

// 에러가 발생할 경우 바로 oplog.rs.drop() 으로...

mongo> db.temp.drop()

mongo> db.temp.save( db.oplog.rs.find({}, {ts:1, h:1}).sort({$natural: -1}).limit(1).next() )


// 기존 oplog 삭제 후 재생성. 재생성시 oplog 사이즈는 기존 사이즈로 맞출 것. 예제는 10G

mongo> db.oplog.rs.drop()

mongo> db.runCommand( {create: 'oplog.rs', capped: true, size: (10 * 1024 * 1024 * 1024)} )


// 데이터가 살아있었다면 복구

mongo> db.oplog.rs.save( db.temp.findOne() )

mongo> db.temp.drop()

 

// shutdown

mongo> use admin

mongo> db.shutdownServer()


4. oplog를 정리한 서버를 다시 replSet에 포함시켜 재시작



존나 찝찝하지만 일단 모든 서버가 정상동작함.







.




Posted by bloodguy
,