У меня есть набор данных из 100 миллионов твитов, хранящихся в Mongo, неоптимизированных и неиндексированных.
Мне нужно скопировать все твиты за последний месяц на другой сервер, как лучше всего это сделать?
Моя идея заключалась в том, чтобы использовать сценарий Ruby для извлечения и копирования соответствующих твитов в новую базу данных на сервере, а затем запустить команду mongo copyDatabase, чтобы скопировать их. Хотя это занимает ужасно много времени, есть другой способ сделать это?
require 'mongo_mapper'
MongoMapper.database = 'twitter'
require './models'
tweets = TwitterTweet.where(:created_at => {"$gt" => 1.month.ago}).all; # about 15 million
MongoMapper.database = 'monthly'
# copy the tweets over to the new db
tweets.each do |tweet|
tweet.save!
end;
Во-первых, вы упоминаете, что он не проиндексирован / не оптимизирован - есть ли хотя бы индекс на created_at
? Если нет, значит, вы выполняете чрезвычайно неэффективный запрос (сканирование таблицы), и это не будет очень быстро.
В общем, вероятно, самый простой способ сделать это - просто сделать существующий сервер основным, а затем создать дополнительный (см. Основные концепции набора реплик). В наборе реплик, когда вы добавляете новый вторичный, он синхронизируется с первичным, клонируя все существующие данные и затем применяя любые последующие изменения через oplog. Когда вы будете счастливы, что у вас есть все необходимые данные (и если вы не хотите сохранять набор реплик), просто перезапустите mongod
s без --replSet
аргумент (и на другом порту обычно хорошая идея), и у вас будет полная копия на новом хосте.
Более ручной подход заключался бы в отключении текущего mongod
(или fsyncLock()
чтобы гарантировать отсутствие изменений), а затем скопируйте файлы базы данных вручную на новый хост - они будут в вашем dbpath
и будет выглядеть так:
<databasename>.ns
<databasename>.0
<databasename>.1
<databasename>.2
etc.
Они содержат всю информацию о другом mongod
потребуется, поэтому, как только вы скопируете их на новый хост и запустите экземпляр MongoDB, вы сможете просто use <databasename>
и будь готов идти.
В любом случае, для любых неиспользуемых / нежелательных частей, просто отбросьте их, как только вы запустите новый хост, а затем запустите ремонт если вы хотите освободить место на диске.
Наконец, если вы действительно хотите просто взять часть записей, вы можете mongodump соответствующую коллекцию с фильтром запросов, а затем используйте mongorestore импортировать на новый хост. Я не думаю, что это будет намного быстрее, чем рубин, который вы предлагаете выше, особенно если вам его не хватает. created_at
индекс.