MongoDB java 更新时间戳Timestamp
环境
mongodb:3.4
java:1.7
前言
最近,因为业务需要,需要将mongodb
数据同步sql
那边,而我公司的同步程序,需要用到mongodb
自带的时间戳字段。
格式如下:
Timestamp(1524117776, 3698)
由于历史原因,我公司的历史数据,是没有时间戳字段的,所以需要刷出来!
需要刷出类似如下的结构:
"_tm" : Timestamp(1524117948, 3817)
代码
由于就是刷数据,没什么好讲的,就直接上代码了。
完整的代码:
public static void main(String[] args) {
final MongoCollection<Document> useropRecord;
//连接数据库 start
MongoCredential credential = MongoCredential.createCredential("user", "user", "user.gogoal.com".toCharArray());
ServerAddress serverAddress;
serverAddress = new ServerAddress("192.168.11.22", 22);
List<ServerAddress> addrs = new ArrayList<ServerAddress>();
addrs.add(serverAddress);
List<MongoCredential> credentials = new ArrayList<MongoCredential>();
credentials.add(credential);
@SuppressWarnings("resource")
MongoClient mongoClient = new MongoClient(addrs, credentials);
System.out.println("Connect to database successfully");
//连接数据库 end
MongoDatabase database = mongoClient.getDatabase("user");
useropRecord = database.getCollection("userop_record");//埋点表
Document match = new Document();
match.append("_tm", null);
Date stringToDate = DateUtil.stringToDate("2018-04-01", "yyyy-MM-dd");
match.append("date", new Document("$gte", stringToDate));
useropRecord.find(match).forEach(new Block<Document>() {
int aa=3000;
@Override
public void apply(Document doc) {
Document project = new Document();
project.append("$set", new Document("_tm", new BSONTimestamp((int)(System.currentTimeMillis() / 1000), aa++)));
useropRecord.updateMany(new BasicDBObject("_id", doc.get("_id")), project);
if(aa >= 4000){
aa = 3000;
}
}
}
);
}
BSONTimestamp
上面的代码中重点就是:
new Document("_tm", new BSONTimestamp((int)(System.currentTimeMillis() / 1000), aa++))
其有两个参数,官方的说明:
time - the time in seconds since epoch
increment - an incrementing ordinal for operations within a given second
time
:就是从公记年开始(1970
),的秒数。
increment:这是一个自增的值。这个是自己随便定义的;比如我上面的程序就是从3000开始自增;其这么的原因就是:
上图中我们可以看到,在使用程序刷数据时,会出现,秒都一样的数据,假设没有自增的值的话,那么就会出现两个时间戳一模一样的数据,这样的话,时间戳的含义,就失去了意义!
上面的代码中,我做了如下判断:
if(aa >= 4000){
aa = 3000;
}
因为这个自增的值,只有在秒相同的情况下,来起到一个区分的作用,所以该自增的值,并不需要无限的增长。
BsonTimestamp
官方的驱动包里还提供了一个BsonTimestamp
对象。其和上面的BSONTimestamp
极其相似;
其参数:
seconds - the number of seconds since the epoch
increment - the increment.
其英文的解释和上面也是基本一样;
只不过上面的那个秒和Date
有关,而这个,是你随便输入的数字来表示秒。
源码比较
BSONTimestamp
public BSONTimestamp(int time, int increment)
{
this.time = new Date(time * 1000L);
inc = increment;
}
BsonTimestamp
public BsonTimestamp(int seconds, int inc)
{
this.seconds = seconds;
this.inc = inc;
}
可以看出,第一个,其源码里,又转成了时间,而第二个,只是一个int
型的数字。
由于我们的习惯是:时间戳对应的就是时间,所以一般使用BSONTimestamp
类型。
总结
在此之前,我还对mongodb
表示疑惑,为什么不直接使用时间来表示时间戳,而非要弄个Timestamp
类型来表示时间戳。
现在终于明白了!
虽然知识点理解起来并不难,但是这个设计的想法真的非常赞!
参考地址:
https://docs.mongodb.com/manual/reference/bson-types/#timestamps
http://api.mongodb.com/java/current/org/bson/types/BSONTimestamp.html#BSONTimestamp-int-int-
上一篇: 电子商务类站点终极资源大全
推荐阅读