import java.util.ArrayList;
|
import java.util.Arrays;
|
import java.util.HashMap;
|
import java.util.List;
|
import java.util.Map;
|
import java.util.Random;
|
import java.util.concurrent.TimeUnit;
|
import java.util.concurrent.atomic.AtomicInteger;
|
|
import org.bson.Document;
|
|
import com.mongodb.ConnectionString;
|
import com.mongodb.ReadPreference;
|
import com.mongodb.async.SingleResultCallback;
|
import com.mongodb.async.client.MongoClient;
|
import com.mongodb.async.client.MongoClientSettings;
|
import com.mongodb.async.client.MongoClients;
|
import com.mongodb.async.client.MongoCollection;
|
import com.mongodb.async.client.MongoDatabase;
|
import com.mongodb.connection.ClusterSettings;
|
import com.mongodb.connection.ConnectionPoolSettings;
|
import com.mongodb.connection.SocketSettings;
|
|
/**
|
* MongoDB Demo
|
*
|
* params: ip connections batch
|
*
|
* @author daimin
|
* @version $Id: MongoBenchMark.java, v 0.1 Aug 30, 2016 2:12:54 PM daimin Exp $
|
*/
|
public class MongoBenchMark {
|
|
static String server = "10.189.224.12";
|
|
static int port = 9018;
|
|
static int connections = 100;
|
|
static AtomicInteger good = new AtomicInteger(0);
|
static AtomicInteger bad = new AtomicInteger(0);
|
|
static int batch = 500;
|
|
static int queue = 5000;
|
|
static Map<String, Integer> map = new HashMap<String, Integer>();
|
|
static AtomicInteger scan = new AtomicInteger(0);
|
|
public static void main(String[] args) {
|
if (args != null && args.length >= 1) {
|
server = args[0];
|
System.err.println("mongo: " + server);
|
}
|
if (args != null && args.length >= 2) {
|
connections = Integer.parseInt(args[1]);
|
System.err.println("connections: " + connections);
|
}
|
if (args != null && args.length >= 3) {
|
batch = Integer.parseInt(args[2]);
|
System.err.println("batch: " + batch);
|
}
|
MongoClient client = buildMongoClient(server, port);
|
MongoDatabase db = client.getDatabase("bench");
|
startRoutine(db);
|
}
|
|
static void startRoutine(MongoDatabase db) {
|
List<MongoCollection<Document>> cs = new ArrayList<MongoCollection<Document>>(10);
|
for (int i = 0; i < 10; i++) {
|
cs.add(db.getCollection("raw" + i));
|
}
|
for (int i = 0;; i++) {
|
int all = i * batch * 10;
|
int _good = good.get();
|
int _bad = bad.get();
|
int loss = all - _good - _bad;
|
System.err.println("start round " + i + ", expect: " + all + ", count: " + _good + "/"
|
+ _bad + " queue: " + loss);
|
try {
|
String mapstr = null;
|
synchronized (map) {
|
mapstr = map.toString();
|
map.clear();
|
}
|
long pre = System.currentTimeMillis();
|
for (int j = 0; j < 10; j++) {
|
doRoundSave(i, cs.get(j));
|
doRoundScan(i, cs.get(j));
|
}
|
System.err.println("cost: " + (System.currentTimeMillis() - pre) + ", scan size: "
|
+ scan.getAndSet(0));
|
System.err.println("errors: " + mapstr);
|
} catch (Throwable t) {
|
t.printStackTrace();
|
}
|
try {
|
Thread.sleep(5000);
|
} catch (Throwable t) {
|
t.printStackTrace();
|
}
|
}
|
}
|
|
static void doRoundScan(final int round, MongoCollection<Document> c) {
|
int b = getRandom(batch - 200);
|
for (int i = b; i < b + 100; i++) {
|
int hour = getRandom(10);
|
long end = System.currentTimeMillis() - hour * hour;
|
long start = end - 5 * minute;
|
final String startRow = i + "_" + start;
|
final String endRow = i + "_" + end;
|
c.find(
|
new Document("_id", new Document().append("$gt", startRow).append("$lt", endRow)))
|
.into(new ArrayList<Document>(), new SingleResultCallback<ArrayList<Document>>() {
|
@Override
|
public void onResult(ArrayList<Document> result, Throwable t) {
|
scan.addAndGet(result.size());
|
}
|
});
|
;
|
}
|
}
|
|
static List<Double> vs = Arrays.asList(new Double[] { 1.1, 2.2, 3.3, 4.4 });
|
|
static void doRoundSave(final int round, MongoCollection<Document> c) {
|
final long time = System.currentTimeMillis();
|
for (int i = 0; i < batch; i++) {
|
final String k = i + "";
|
final String key = k + "_" + time;
|
c.insertOne(new Document("_id", key).append("k", k).append("v", vs).append("t", time),
|
new SingleResultCallback<Void>() {
|
@Override
|
public void onResult(Void result, Throwable t) {
|
if (t == null) {
|
good.incrementAndGet();
|
} else {
|
bad.incrementAndGet();
|
String key = t.getClass().getName() + "@" + round;
|
synchronized (map) {
|
Integer old = map.get(key);
|
if (old == null) {
|
old = 0;
|
}
|
map.put(key, old + 1);
|
}
|
}
|
}
|
});
|
}
|
}
|
|
static MongoClient buildMongoClient(String server, int port) {
|
String mongoString = "mongodb://" + server + ":" + port;
|
ConnectionString connectionString = new ConnectionString(mongoString);
|
ClusterSettings clusterSettings = ClusterSettings.builder()
|
.applyConnectionString(connectionString).maxWaitQueueSize(queue).build();
|
ConnectionPoolSettings poolSettings = ConnectionPoolSettings.builder().maxSize(connections)
|
.minSize(connections).maxWaitQueueSize(queue).maxWaitTime(minute, TimeUnit.MILLISECONDS)
|
.maxConnectionLifeTime(0, TimeUnit.MILLISECONDS)
|
.maxConnectionIdleTime(0, TimeUnit.MILLISECONDS).build();
|
SocketSettings socketSettings = SocketSettings.builder().keepAlive(true).build();
|
MongoClientSettings settings = MongoClientSettings.builder()
|
.clusterSettings(clusterSettings).readPreference(ReadPreference.secondaryPreferred())
|
.connectionPoolSettings(poolSettings).socketSettings(socketSettings)
|
.streamFactoryFactory(NettyStreamFactoryFactory.builder().build()).build();
|
return MongoClients.create(settings);
|
}
|
|
private static Random seed = new Random();
|
|
private static int getRandom(int max) {
|
return (seed.nextInt() % max + max) % max;
|
}
|
|
static long minute = 60 * 1000;
|
static long hour = minute * 60;
|
}
|