forked from tronprotocol/java-tron
-
Notifications
You must be signed in to change notification settings - Fork 2
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
481141a
commit 4156b73
Showing
2 changed files
with
136 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,135 @@ | ||
package org.tron.plugins; | ||
|
||
import java.io.File; | ||
import java.io.IOException; | ||
import java.nio.file.Path; | ||
import java.util.Arrays; | ||
import java.util.concurrent.Callable; | ||
import lombok.extern.slf4j.Slf4j; | ||
import org.rocksdb.RocksDBException; | ||
import org.tron.plugins.utils.ByteArray; | ||
import org.tron.plugins.utils.DBUtils; | ||
import org.tron.plugins.utils.db.DBInterface; | ||
import org.tron.plugins.utils.db.DBIterator; | ||
import org.tron.plugins.utils.db.DbTool; | ||
import picocli.CommandLine; | ||
|
||
@Slf4j(topic = "compare") | ||
@CommandLine.Command(name = "compare", | ||
description = "compare data between two path for db.", | ||
exitCodeListHeading = "Exit Codes:%n", | ||
exitCodeList = { | ||
"0:Successful", | ||
"n:compare diff find,please check toolkit.log"}) | ||
public class DbCompare implements Callable<Integer> { | ||
|
||
@CommandLine.Spec | ||
static CommandLine.Model.CommandSpec spec; | ||
@CommandLine.Parameters(index = "0", | ||
description = " ful input path for base") | ||
private File base; | ||
@CommandLine.Parameters(index = "1", | ||
description = "ful input path for compare") | ||
private File compare; | ||
@CommandLine.Option(names = {"-h", "--help"}, help = true, description = "display a help message") | ||
private boolean help; | ||
|
||
@Override | ||
public Integer call() throws Exception { | ||
if (help) { | ||
spec.commandLine().usage(System.out); | ||
return 0; | ||
} | ||
if (!base.exists()) { | ||
logger.info(" {} does not exist.", base); | ||
spec.commandLine().getErr().println(spec.commandLine().getColorScheme() | ||
.errorText(String.format("%s does not exist.", base))); | ||
return 404; | ||
} | ||
if (!compare.exists()) { | ||
logger.info(" {} does not exist.", compare); | ||
spec.commandLine().getErr().println(spec.commandLine().getColorScheme() | ||
.errorText(String.format("%s does not exist.", compare))); | ||
return 404; | ||
} | ||
|
||
Comparison service = new DbComparison(base.toPath(), compare.toPath()); | ||
return service.doCompare() ? 0 : 1; | ||
|
||
} | ||
|
||
interface Comparison { | ||
boolean doCompare() throws Exception; | ||
} | ||
|
||
static class DbComparison implements Comparison { | ||
|
||
private final Path basePath; | ||
private final Path dstPath; | ||
private final String name; | ||
|
||
public DbComparison(Path srcDir, Path dstDir) { | ||
this.basePath = srcDir.getParent(); | ||
this.dstPath = dstDir.getParent(); | ||
this.name = srcDir.getFileName().toString(); | ||
} | ||
|
||
@Override | ||
public boolean doCompare() throws Exception { | ||
return compare(); | ||
} | ||
|
||
|
||
|
||
private boolean compare() throws RocksDBException, IOException { | ||
try ( | ||
DBInterface base = DbTool.getDB(this.basePath, this.name); | ||
DBIterator baseIterator = base.iterator(); | ||
DBInterface dst = DbTool.getDB(this.dstPath, this.name); | ||
DBIterator dstIterator = dst.iterator()) { | ||
|
||
// check | ||
logger.info("compare {} start", this.name); | ||
spec.commandLine().getOut().println("compare " + this.name + " start"); | ||
baseIterator.seekToFirst(); | ||
dstIterator.seekToFirst(); | ||
for (; baseIterator.hasNext() && dstIterator.hasNext(); | ||
baseIterator.next(), dstIterator.next()) { | ||
byte[] baseValue = baseIterator.getValue(); | ||
byte[] baseKey = baseIterator.getKey(); | ||
byte[] key = dstIterator.getKey(); | ||
byte[] value = dstIterator.getValue(); | ||
if (!Arrays.equals(baseKey, key) || !Arrays.equals(baseValue, value)) { | ||
spec.commandLine().getOut().format("%s\t%s\t%s\t%s\t%s.", name, | ||
ByteArray.toHexString(baseKey), ByteArray.toHexString(key), | ||
ByteArray.toHexString(baseValue), ByteArray.toHexString(value)).println(); | ||
logger.info("{}\t{}\t{}\t{}\t{}", name, | ||
ByteArray.toHexString(baseKey), ByteArray.toHexString(key), | ||
ByteArray.toHexString(baseValue), ByteArray.toHexString(value)); | ||
} | ||
} | ||
for (; baseIterator.hasNext(); baseIterator.next()) { | ||
byte[] key = baseIterator.getKey(); | ||
byte[] value = baseIterator.getValue(); | ||
String dbName = DBUtils.simpleDecode(key); | ||
spec.commandLine().getOut().format("b\t%s\t%s\t%s.", dbName, | ||
ByteArray.toHexString(key), ByteArray.toHexString(value)).println(); | ||
logger.info("b\t{}\t{}\t{}", dbName, | ||
ByteArray.toHexString(key), ByteArray.toHexString(value)); | ||
} | ||
for (; dstIterator.hasNext(); dstIterator.next()) { | ||
byte[] key = dstIterator.getKey(); | ||
byte[] value = dstIterator.getValue(); | ||
String dbName = DBUtils.simpleDecode(key); | ||
spec.commandLine().getOut().format("d\t%s\t%s\t%s.", dbName, | ||
ByteArray.toHexString(key), ByteArray.toHexString(value)).println(); | ||
logger.info("d\t{}\t{}\t{}", dbName, | ||
ByteArray.toHexString(key), ByteArray.toHexString(value)); | ||
} | ||
} | ||
logger.info("compare {} end", this.name); | ||
spec.commandLine().getOut().println("compare " + this.name + " end"); | ||
return true; | ||
} | ||
} | ||
} |