switched from curl to kerl

This commit is contained in:
adrianziser 2017-08-12 15:56:06 +02:00
parent 6241a01446
commit f3a32d4bdc
16 changed files with 366 additions and 58 deletions

View File

@ -4,7 +4,7 @@
<groupId>org.iota</groupId>
<artifactId>jota</artifactId>
<name>JOTA</name>
<version>0.9.0-RC1</version>
<version>0.9.2</version>
<description>JOTA library is a simple Java wrapper around IOTA Node's JSON-REST HTTP interface.</description>
<licenses>
<license>
@ -41,7 +41,7 @@
<artifactId>maven-surefire-plugin</artifactId>
<version>2.12.4</version>
<configuration>
<skipTests>true</skipTests>
<skipTests>${skipTests}</skipTests>
</configuration>
</plugin>
</plugins>
@ -53,7 +53,6 @@
<plugins>
<plugin>
<artifactId>maven-source-plugin</artifactId>
<version>3.0.1</version>
<executions>
<execution>
<id>attach-sources</id>
@ -72,11 +71,6 @@
<goals>
<goal>jar</goal>
</goals>
<configuration>
<show>private</show>
<nohelp>true</nohelp>
<additionalparam>-Xdoclint:none</additionalparam>
</configuration>
</execution>
</executions>
<configuration>
@ -121,6 +115,7 @@
</dependency>
</dependencies>
<properties>
<skipTests>true</skipTests>
<java-version>1.7</java-version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>

View File

@ -4,7 +4,7 @@
<modelVersion>4.0.0</modelVersion>
<groupId>org.iota</groupId>
<artifactId>jota</artifactId>
<version>0.9.1</version>
<version>0.9.2</version>
<name>JOTA</name>
<description>JOTA library is a simple Java wrapper around IOTA Node's JSON-REST HTTP interface.</description>
@ -24,6 +24,13 @@
<dependencies>
<!-- https://mvnrepository.com/artifact/org.bouncycastle/bcprov-jdk15on -->
<dependency>
<groupId>org.bouncycastle</groupId>
<artifactId>bcprov-jdk15on</artifactId>
<version>1.57</version>
</dependency>
<!-- https://mvnrepository.com/artifact/com.squareup.retrofit2/retrofit -->
<dependency>
<groupId>com.squareup.retrofit2</groupId>

View File

@ -1,10 +1,11 @@
package jota;
import com.google.gson.Gson;
import jota.dto.response.*;
import jota.error.*;
import jota.model.*;
import jota.pow.ICurl;
import jota.pow.JCurl;
import jota.pow.SpongeFactory;
import jota.utils.*;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
@ -252,6 +253,7 @@ public class IotaAPI extends IotaAPICore {
final GetTransactionsToApproveResponse txs = getTransactionsToApprove(depth);
// attach to tangle - do pow
System.out.println(new Gson().toJson(txs));
final GetAttachToTangleResponse res = attachToTangle(txs.getTrunkTransaction(), txs.getBranchTransaction(), minWeightMagnitude, trytes);
try {
@ -641,7 +643,7 @@ public class IotaAPI extends IotaAPICore {
long totalSum = 0;
String bundleHash = bundle.getTransactions().get(0).getBundle();
ICurl curl = new JCurl();
ICurl curl = SpongeFactory.create(SpongeFactory.Mode.KERL);
curl.reset();
List<Signature> signaturesToValidate = new ArrayList<>();
@ -1108,7 +1110,7 @@ public class IotaAPI extends IotaAPICore {
}
public static class Builder extends IotaAPICore.Builder<Builder> {
private ICurl customCurl = new JCurl();
private ICurl customCurl = SpongeFactory.create(SpongeFactory.Mode.KERL);
public Builder withCustomCurl(ICurl curl) {
customCurl = curl;

View File

@ -1,7 +1,7 @@
package jota.model;
import jota.pow.ICurl;
import jota.pow.JCurl;
import jota.pow.SpongeFactory;
import jota.utils.Converter;
import org.apache.commons.lang3.StringUtils;
@ -90,7 +90,7 @@ public class Bundle implements Comparable<Bundle> {
*/
public void finalize(ICurl customCurl) {
ICurl curl = customCurl == null ? new JCurl() : customCurl;
ICurl curl = customCurl == null ? SpongeFactory.create(SpongeFactory.Mode.KERL) : customCurl;
curl.reset();
for (int i = 0; i < this.getTransactions().size(); i++) {

View File

@ -1,7 +1,7 @@
package jota.model;
import jota.pow.ICurl;
import jota.pow.JCurl;
import jota.pow.SpongeFactory;
import jota.utils.Converter;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.builder.ToStringBuilder;
@ -18,8 +18,9 @@ import java.util.Arrays;
*/
public class Transaction {
private static final Logger log = LoggerFactory.getLogger(Transaction.class);
private ICurl customCurl;
private static final transient Logger log = LoggerFactory.getLogger(Transaction.class);
private transient ICurl customCurl;
private String hash;
private String signatureFragments;
@ -391,7 +392,7 @@ public class Transaction {
int[] transactionTrits = Converter.trits(trytes);
int[] hash = new int[243];
final ICurl curl = customCurl == null ? new JCurl() : customCurl; // we need a fluent JCurl.
final ICurl curl = customCurl == null ? SpongeFactory.create(SpongeFactory.Mode.KERL) : customCurl; // we need a fluent JCurl.
// generate the correct transaction hash
curl.reset();

View File

@ -1,5 +1,10 @@
package jota.pow;
import jota.utils.Converter;
import jota.utils.Pair;
import java.util.Arrays;
/**
* (c) 2016 Come-from-Beyond
* <p>
@ -14,10 +19,30 @@ public class JCurl implements ICurl {
private static final int STATE_LENGTH = 3 * HASH_LENGTH;
private static final int NUMBER_OF_ROUNDS = 27;
private static final int[] TRUTH_TABLE = {1, 0, -1, 1, -1, 0, -1, 1, 0};
private static final int[] TRUTH_TABLE = {1, 0, -1, 2, 1, -1, 0, 2, -1, 1, 0};
private final long[] stateLow;
private final long[] stateHigh;
private final int[] scratchpad = new int[STATE_LENGTH];
private int[] state;
private boolean pair;
private int[] state = new int[STATE_LENGTH];
public JCurl() {
this(false);
}
public JCurl(boolean pair) {
this.pair = pair;
if (pair) {
stateHigh = new long[STATE_LENGTH];
stateLow = new long[STATE_LENGTH];
state = null;
set();
} else {
state = new int[STATE_LENGTH];
stateHigh = null;
stateLow = null;
}
}
/**
* Absorbs the specified trits.
*
@ -54,14 +79,21 @@ public class JCurl implements ICurl {
*/
public JCurl transform() {
final int[] scratchpad = new int[STATE_LENGTH];
int scratchpadIndex = 0;
int prev_scratchpadIndex = 0;
for (int round = 0; round < NUMBER_OF_ROUNDS; round++) {
System.arraycopy(state, 0, scratchpad, 0, STATE_LENGTH);
for (int stateIndex = 0; stateIndex < STATE_LENGTH; stateIndex++) {
state[stateIndex] = TRUTH_TABLE[scratchpad[scratchpadIndex] + scratchpad[scratchpadIndex += (scratchpadIndex < 365 ? 364 : -365)] * 3 + 4];
prev_scratchpadIndex = scratchpadIndex;
if (scratchpadIndex < 365) {
scratchpadIndex += 364;
} else {
scratchpadIndex += -365;
}
state[stateIndex] = TRUTH_TABLE[scratchpad[prev_scratchpadIndex] + (scratchpad[scratchpadIndex] << 2) + 5];
}
}
return this;
}
@ -124,6 +156,52 @@ public class JCurl implements ICurl {
this.state = state;
}
private void set() {
Arrays.fill(stateLow, Converter.HIGH_LONG_BITS);
Arrays.fill(stateHigh, Converter.HIGH_LONG_BITS);
}
private void pairTransform() {
final long[] curlScratchpadLow = new long[STATE_LENGTH];
final long[] curlScratchpadHigh = new long[STATE_LENGTH];
int curlScratchpadIndex = 0;
for (int round = 27; round-- > 0; ) {
System.arraycopy(stateLow, 0, curlScratchpadLow, 0, STATE_LENGTH);
System.arraycopy(stateHigh, 0, curlScratchpadHigh, 0, STATE_LENGTH);
for (int curlStateIndex = 0; curlStateIndex < STATE_LENGTH; curlStateIndex++) {
final long alpha = curlScratchpadLow[curlScratchpadIndex];
final long beta = curlScratchpadHigh[curlScratchpadIndex];
final long gamma = curlScratchpadHigh[curlScratchpadIndex += (curlScratchpadIndex < 365 ? 364 : -365)];
final long delta = (alpha | (~gamma)) & (curlScratchpadLow[curlScratchpadIndex] ^ beta);
stateLow[curlStateIndex] = ~delta;
stateHigh[curlStateIndex] = (alpha ^ gamma) | delta;
}
}
}
public void absorb(final Pair<long[], long[]> pair, int offset, int length) {
int o = offset, l = length, i = 0;
do {
System.arraycopy(pair.low, o, stateLow, 0, l < HASH_LENGTH ? l : HASH_LENGTH);
System.arraycopy(pair.hi, o, stateHigh, 0, l < HASH_LENGTH ? l : HASH_LENGTH);
pairTransform();
o += HASH_LENGTH;
} while ((l -= HASH_LENGTH) > 0);
}
public Pair<long[], long[]> squeeze(Pair<long[], long[]> pair, int offset, int length) {
int o = offset, l = length, i = 0;
long[] low = pair.low;
long[] hi = pair.hi;
do {
System.arraycopy(stateLow, 0, low, o, l < HASH_LENGTH ? l : HASH_LENGTH);
System.arraycopy(stateHigh, 0, hi, o, l < HASH_LENGTH ? l : HASH_LENGTH);
pairTransform();
o += HASH_LENGTH;
} while ((l -= HASH_LENGTH) > 0);
return new Pair<>(low, hi);
}
/**
* Clones this instance.
*
@ -131,6 +209,6 @@ public class JCurl implements ICurl {
*/
@Override
public ICurl clone() {
return new JCurl();
return new JCurl(pair);
}
}

View File

@ -0,0 +1,169 @@
package jota.pow;
import org.bouncycastle.jcajce.provider.digest.Keccak;
import java.math.BigInteger;
import java.util.Arrays;
public class Kerl extends JCurl {
private static final int HASH_LENGTH = 243;
private static final int BIT_HASH_LENGTH = 384;
private static final int BYTE_HASH_LENGTH = BIT_HASH_LENGTH / 8;
private static final int RADIX = 3;
private static final int MAX_TRIT_VALUE = (RADIX - 1) / 2, MIN_TRIT_VALUE = -MAX_TRIT_VALUE;
private final Keccak.Digest384 keccak;
private byte[] byte_state;
private int[] trit_state;
public Kerl() {
super();
this.keccak = new Keccak.Digest384();
this.byte_state = new byte[BYTE_HASH_LENGTH];
this.trit_state = new int[HASH_LENGTH];
}
public static BigInteger convertTritsToBigint(final int[] trits, final int offset, final int size) {
BigInteger value = BigInteger.ZERO;
for (int i = size; i-- > 0; ) {
value = value.multiply(BigInteger.valueOf(RADIX)).add(BigInteger.valueOf(trits[offset + i]));
}
return value;
}
private static BigInteger convertBytesToBigInt(final byte[] bytes, final int offset, final int size) {
return new BigInteger(Arrays.copyOfRange(bytes, offset, offset + size));
}
private static int[] convertBigintToTrits(final BigInteger value, int size) {
int[] destination = new int[size];
BigInteger absoluteValue = value.compareTo(BigInteger.ZERO) < 0 ? value.negate() : value;
for (int i = 0; i < size; i++) {
BigInteger[] divRemainder = absoluteValue.divideAndRemainder(BigInteger.valueOf(RADIX));
int remainder = divRemainder[1].intValue();
absoluteValue = divRemainder[0];
if (remainder > MAX_TRIT_VALUE) {
remainder = MIN_TRIT_VALUE;
absoluteValue = absoluteValue.add(BigInteger.ONE);
}
destination[i] = remainder;
}
if (value.compareTo(BigInteger.ZERO) < 0) {
for (int i = 0; i < size; i++) {
destination[i] = -destination[i];
}
}
return destination;
}
private static byte[] convertBigintToBytes(final BigInteger value, int size) {
final byte[] result = new byte[BYTE_HASH_LENGTH];
final byte[] bytes = value.toByteArray();
int i = 0;
while (i + bytes.length < BYTE_HASH_LENGTH) {
result[i++] = (byte) (bytes[0] < 0 ? -1 : 0);
}
for (int j = bytes.length; j-- > 0; ) {
result[i++] = bytes[bytes.length - 1 - j];
}
return result;
}
@Override
public Kerl reset() {
this.keccak.reset();
return this;
}
@Override
public Kerl absorb(final int[] trits, int offset, int length) {
if (length % 243 != 0) throw new RuntimeException("Illegal length: " + length);
do {
//copy trits[offset:offset+length]
System.arraycopy(trits, offset, trit_state, 0, HASH_LENGTH);
//convert to bits
trit_state[HASH_LENGTH - 1] = 0;
byte[] bytes = convertBigintToBytes(convertTritsToBigint(trit_state, 0, HASH_LENGTH), BYTE_HASH_LENGTH);
//run keccak
keccak.update(bytes);
offset += HASH_LENGTH;
} while ((length -= HASH_LENGTH) > 0);
return this;
}
@Override
public int[] squeeze(final int[] trits, int offset, int length) {
if (length % 243 != 0) throw new RuntimeException("Illegal length: " + length);
do {
byte_state = this.keccak.digest();
//convert to trits
trit_state = convertBigintToTrits(convertBytesToBigInt(byte_state, 0, BYTE_HASH_LENGTH), HASH_LENGTH);
//copy with offset
trit_state[HASH_LENGTH - 1] = 0;
System.arraycopy(trit_state, 0, trits, offset, HASH_LENGTH);
//calculate hash again
for (int i = byte_state.length; i-- > 0; ) {
byte_state[i] = (byte) (byte_state[i] ^ 0xFF);
}
keccak.update(byte_state);
offset += HASH_LENGTH;
} while ((length -= HASH_LENGTH) > 0);
return trits;
}
/**
* Squeezes the specified trits.
*
* @param trits The trits.
* @return The squeezes trits.
*/
public int[] squeeze(final int[] trits) {
return squeeze(trits, 0, trits.length);
}
/**
* Clones this instance.
*
* @return A new instance.
*/
@Override
public Kerl clone() {
return new Kerl();
}
}

View File

@ -0,0 +1,25 @@
package jota.pow;
/**
* Created by paul on 7/27/17.
*/
public abstract class SpongeFactory {
public static ICurl create(Mode mode) {
switch (mode) {
case CURL:
return new JCurl();
case KERL:
return new Kerl();
case BCURLT:
return new JCurl(true);
default:
return null;
}
}
public enum Mode {
CURL,
KERL,
BCURLT
}
}

View File

@ -1,7 +1,9 @@
package jota.utils;
import jota.error.InvalidAddressException;
import jota.pow.ICurl;
import jota.pow.JCurl;
import jota.pow.SpongeFactory;
/**
* This class defines utility methods to add/remove the checksum to/from an address.
@ -53,7 +55,7 @@ public class Checksum {
**/
public static boolean isValidChecksum(String addressWithChecksum) throws InvalidAddressException {
String addressWithoutChecksum = removeChecksum(addressWithChecksum);
String addressWithRecalculateChecksum = addressWithChecksum += calculateChecksum(addressWithoutChecksum);
String addressWithRecalculateChecksum = addressWithoutChecksum += calculateChecksum(addressWithoutChecksum);
return addressWithRecalculateChecksum.equals(addressWithChecksum);
}
@ -82,10 +84,13 @@ public class Checksum {
}
private static String calculateChecksum(String address) {
JCurl curl = new JCurl();
ICurl curl = SpongeFactory.create(SpongeFactory.Mode.KERL);
curl.reset();
curl.setState(Converter.copyTrits(address, curl.getState()));
curl.transform();
return Converter.trytes(curl.getState()).substring(0, 9);
curl.absorb(Converter.trits(address));
int[] checksumTrits = new int[JCurl.HASH_LENGTH];
curl.squeeze(checksumTrits);
String checksum = Converter.trytes(checksumTrits);
String checksumPrt = checksum.substring(72, 81);
return checksumPrt;
}
}

View File

@ -31,6 +31,9 @@ public class Converter {
private static final int[][] BYTE_TO_TRITS_MAPPINGS = new int[243][];
private static final int[][] TRYTE_TO_TRITS_MAPPINGS = new int[27][];
public static final int HIGH_INTEGER_BITS = 0xFFFFFFFF;
public static final long HIGH_LONG_BITS = 0xFFFFFFFFFFFFFFFFL;
static {
final int[] trits = new int[NUMBER_OF_TRITS_IN_A_BYTE];

View File

@ -2,7 +2,7 @@ package jota.utils;
import jota.model.Bundle;
import jota.pow.ICurl;
import jota.pow.JCurl;
import jota.pow.SpongeFactory;
import java.util.Arrays;
@ -27,7 +27,7 @@ public class Multisig {
* Initializes a new instance of the Multisig class.
*/
public Multisig() {
this(new JCurl());
this(SpongeFactory.create(SpongeFactory.Mode.KERL));
}
/**

View File

@ -0,0 +1,14 @@
package jota.utils;
/**
* Created by paul on 4/15/17.
*/
public class Pair<S, T> {
public S low;
public T hi;
public Pair(S k, T v) {
low = k;
hi = v;
}
}

View File

@ -3,7 +3,7 @@ package jota.utils;
import jota.model.Bundle;
import jota.model.Transaction;
import jota.pow.ICurl;
import jota.pow.JCurl;
import jota.pow.SpongeFactory;
import java.util.ArrayList;
import java.util.Arrays;
@ -27,7 +27,7 @@ public class Signing {
* @param curl
*/
public Signing(ICurl curl) {
this.curl = curl == null ? new JCurl() : curl;
this.curl = curl == null ? SpongeFactory.create(SpongeFactory.Mode.KERL) : curl;
}
/**
@ -146,7 +146,7 @@ public class Signing {
for (int j = normalizedBundleFragment[i] + 13; j-- > 0; ) {
ICurl jCurl = new JCurl();
ICurl jCurl = SpongeFactory.create(SpongeFactory.Mode.KERL);
jCurl.reset();
jCurl.absorb(buffer);
jCurl.squeeze(buffer);

View File

@ -11,21 +11,23 @@ import static org.junit.Assert.assertEquals;
*/
public class ChecksumTest {
private static final String TEST_ADDRESS_WITHOUT_CHECKSUM = "RVORZ9SIIP9RCYMREUIXXVPQIPHVCNPQ9HZWYKFWYWZRE9JQKG9REPKIASHUUECPSQO9JT9XNMVKWYGVA";
private static final String TEST_ADDRESS_WITH_CHECKSUM = "RVORZ9SIIP9RCYMREUIXXVPQIPHVCNPQ9HZWYKFWYWZRE9JQKG9REPKIASHUUECPSQO9JT9XNMVKWYGVAFOXM9MUBX";
private static final String TEST_ADDRESS_WITHOUT_CHECKSUM = "EUHMAFIYBYZOXAVQQYRQ9RCNMTYX9KNEZFWXYMQIYPSRZRVDOLXDPUEARYPTWSZCAXJLXRYUUQKSHIJYZ";
private static final String TEST_ADDRESS_WITHOUT_CHECKSUM2 = "P9UDUZMN9DEXCRQEKLJYSBSBZFCHOBPJSDKMLCCVJDOVOFDWMNBZRIRRZJGINOUMPJBMYYZEGRTIDUABD";
private static final String TEST_ADDRESS_WITH_CHECKSUM = "EUHMAFIYBYZOXAVQQYRQ9RCNMTYX9KNEZFWXYMQIYPSRZRVDOLXDPUEARYPTWSZCAXJLXRYUUQKSHIJYZICCXCXUHX";
private static final String TEST_ADDRESS_WITH_CHECKSUM2 = "P9UDUZMN9DEXCRQEKLJYSBSBZFCHOBPJSDKMLCCVJDOVOFDWMNBZRIRRZJGINOUMPJBMYYZEGRTIDUABDODCNSCYJD";
@Test
public void shouldAddChecksum() throws InvalidAddressException {
assertEquals(Checksum.addChecksum(TEST_ADDRESS_WITHOUT_CHECKSUM), TEST_ADDRESS_WITH_CHECKSUM);
assertEquals(Checksum.addChecksum(TEST_ADDRESS_WITHOUT_CHECKSUM2), TEST_ADDRESS_WITH_CHECKSUM2);
}
@Test
public void shouldRemoveChecksum() throws InvalidAddressException {
assertEquals(Checksum.removeChecksum(TEST_ADDRESS_WITH_CHECKSUM), TEST_ADDRESS_WITHOUT_CHECKSUM);
assertEquals(Checksum.removeChecksum(TEST_ADDRESS_WITH_CHECKSUM2), TEST_ADDRESS_WITHOUT_CHECKSUM2);
}
@Test
public void shouldIsValidChecksum() throws InvalidAddressException {
assertEquals(Checksum.isValidChecksum(TEST_ADDRESS_WITH_CHECKSUM), true);
assertEquals(Checksum.isValidChecksum(TEST_ADDRESS_WITH_CHECKSUM2), true);
}
}

View File

@ -14,6 +14,7 @@ import org.junit.Before;
import org.junit.Ignore;
import org.junit.Test;
import java.lang.reflect.Modifier;
import java.util.ArrayList;
import java.util.List;
@ -26,21 +27,22 @@ import static org.junit.Assert.assertThat;
*/
public class IotaAPITest {
private static final String TEST_SEED1 = "AAA999999999999999999999999999999999999999999999999999999999999999999999999999999";
private static final String TEST_SEED1 = "IHDEENZYITYVYSPKAURUZAQKGVJEREFDJMYTANNXXGPZ9GJWTEOJJ9IPMXOGZNQLSNMFDSQOTZAEETUEA";
private static final String TEST_SEED2 = "IHDEENZYITYVYSPKAURUZAQKGVJEREFDJMYTANNXXGPZ9GJWTEOJJ9IPMXOGZNQLSNMFDSQOTZAEETUEA";
private static final String TEST_ADDRESS_WITHOUT_CHECKSUM_SECURITY_LEVEL_1 = "NINSZRAKWBERQBBN9KGIRNXQDNENLBUBAYRZPUXFJSWRWVADEOGGOWMLQWSHA9NEOLASWRGOQJXAVRMFY";
private static final String TEST_ADDRESS_WITHOUT_CHECKSUM_SECURITY_LEVEL_2 = "PNGMCSNRCTRHCHPXYTPKEJYPCOWKOMRXZFHH9N9VDIKMNVAZCMIYRHVJIAZARZTUETJVFDMBEBIQE9QTH";
private static final String TEST_ADDRESS_WITHOUT_CHECKSUM_SECURITY_LEVEL_3 = "NOHBJKARAS9DZBFTRVIFY99STSQPSGTHMGMDYXLYIYKFYZISJUOGYWMZXDB9XEXFSSP9GYAIEHUQHLQ9C";
private static final String TEST_HASH = "CKZ9TYPLUWH9FUSYJMPIZBVHWFZXTZMVOJLC9KOICSTBBQWXYTOTMCVPSPMYNDONTXHRULRFAWD999999";
private static final String TEST_ADDRESS_WITHOUT_CHECKSUM_SECURITY_LEVEL_1 = "MALAZGDVZIAQQRTNYJDSZMY9VE9LAHQKTVCUOAGZUCX9IBUMODFFTMGUIUAXGLWZQ9CYRSLYBM9QBIBYA";
private static final String TEST_ADDRESS_WITHOUT_CHECKSUM_SECURITY_LEVEL_2 = "LXQHWNY9CQOHPNMKFJFIJHGEPAENAOVFRDIBF99PPHDTWJDCGHLYETXT9NPUVSNKT9XDTDYNJKJCPQMZC";
private static final String TEST_ADDRESS_WITHOUT_CHECKSUM_SECURITY_LEVEL_2_2 = "LXQHWNY9CQOHPNMKFJFIJHGEPAENAOVFRDIBF99PPHDTWJDCGHLYETXT9NPUVSNKT9XDTDYNJKJCPQMZCCOZVXMTXC";
private static final String TEST_ADDRESS_WITHOUT_CHECKSUM_SECURITY_LEVEL_3 = "ASCZZOBQDMNHLELQKWJBMRETMHBTF9V9TNKYDIFW9PDXPUHPVVGHMSWPVMNJHSJF99QFCMNTPCPGS9DT9";
private static final String TEST_HASH = "AKOEBGNW9BVIDWLXIYFIVQMEOTELGKMKWDCMEVRBPSYQZC9UIRYNKHPEQRGQKTBYVQCIQMWMZFXA99999";
private static final String TEST_INVALID_TRYTES = "BYSWEAUTWXHXZ9YBZISEK9LUHWGMHXCGEVNZHRLUWQFCUSDXZHOFHWHL9MQPVJXXZLIXPXPXF9KYEREFSKCPKYIIKPZVLHUTDFQKKVVBBN9ATTLPCNPJDWDEVIYYLGPZGCWXOBDXMLJC9VO9QXTTBLAXTTBFUAROYEGQIVB9MJWJKXJMCUPTWAUGFZBTZCSJVRBGMYXTVBDDS9MYUJCPZ9YDWWQNIPUAIJXXSNLKUBSCOIJPCLEFPOXFJREXQCUVUMKSDOVQGGHRNILCO9GNCLWFM9APMNMWYASHXQAYBEXF9QRIHIBHYEJOYHRQJAOKAQ9AJJFQ9WEIWIJOTZATIBOXQLBMIJU9PCGBLVDDVFP9CFFSXTDUXMEGOOFXWRTLFGV9XXMYWEMGQEEEDBTIJ9OJOXFAPFQXCDAXOUDMLVYRMRLUDBETOLRJQAEDDLNVIRQJUBZBO9CCFDHIX9MSQCWYAXJVWHCUPTRSXJDESISQPRKZAFKFRULCGVRSBLVFOPEYLEE99JD9SEBALQINPDAZHFAB9RNBH9AZWIJOTLBZVIEJIAYGMC9AZGNFWGRSWAXTYSXVROVNKCOQQIWGPNQZKHUNODGYADPYLZZZUQRTJRTODOUKAOITNOMWNGHJBBA99QUMBHRENGBHTH9KHUAOXBVIVDVYYZMSEYSJWIOGGXZVRGN999EEGQMCOYVJQRIRROMPCQBLDYIGQO9AMORPYFSSUGACOJXGAQSPDY9YWRRPESNXXBDQ9OZOXVIOMLGTSWAMKMTDRSPGJKGBXQIVNRJRFRYEZ9VJDLHIKPSKMYC9YEGHFDS9SGVDHRIXBEMLFIINOHVPXIFAZCJKBHVMQZEVWCOSNWQRDYWVAIBLSCBGESJUIBWZECPUCAYAWMTQKRMCHONIPKJYYTEGZCJYCT9ABRWTJLRQXKMWY9GWZMHYZNWPXULNZAPVQLPMYQZCYNEPOCGOHBJUZLZDPIXVHLDMQYJUUBEDXXPXFLNRGIPWBRNQQZJSGSJTTYHIGGFAWJVXWL9THTPWOOHTNQWCNYOYZXALHAZXVMIZE9WMQUDCHDJMIBWKTYH9AC9AFOT9DPCADCV9ZWUTE9QNOMSZPTZDJLJZCJGHXUNBJFUBJWQUEZDMHXGBPTNSPZBR9TGSKVOHMOQSWPGFLSWNESFKSAZY9HHERAXALZCABFYPOVLAHMIHVDBGKUMDXC9WHHTIRYHZVWNXSVQUWCR9M9RAGMFEZZKZ9XEOQGOSLFQCHHOKLDSA9QCMDGCGMRYJZLBVIFOLBIJPROKMHOYTBTJIWUZWJMCTKCJKKTR9LCVYPVJI9AHGI9JOWMIWZAGMLDFJA9WU9QAMEFGABIBEZNNAL9OXSBFLOEHKDGHWFQSHMPLYFCNXAAZYJLMQDEYRGL9QKCEUEJ9LLVUOINVSZZQHCIKPAGMT9CAYIIMTTBCPKWTYHOJIIY9GYNPAJNUJ9BKYYXSV9JSPEXYMCFAIKTGNRSQGUNIYZCRT9FOWENSZQPD9ALUPYYAVICHVYELYFPUYDTWUSWNIYFXPX9MICCCOOZIWRNJIDALWGWRATGLJXNAYTNIZWQ9YTVDBOFZRKO9CFWRPAQQRXTPACOWCPRLYRYSJARRKSQPR9TCFXDVIXLP9XVL99ERRDSOHBFJDJQQGGGCZNDQ9NYCTQJWVZIAELCRBJJFDMCNZU9FIZRPGNURTXOCDSQGXTQHKHUECGWFUUYS9J9NYQ9U9P9UUP9YMZHWWWCIASCFLCMSKTELZWUGCDE9YOKVOVKTAYPHDF9ZCCQAYPJIJNGSHUIHHCOSSOOBUDOKE9CJZGYSSGNCQJVBEFTZFJ9SQUHOASKRRGBSHWKBCBWBTJHOGQ9WOMQFHWJVEG9NYX9KWBTCAIXNXHEBDIOFO9ALYMFGRICLCKKLG9FOBOX9PDWNQRGHBKHGKKRLWTBEQMCWQRLHAVYYZDIIPKVQTHYTWQMTOACXZOQCDTJTBAAUWXSGJF9PNQIJ9AJRUMUVCPWYVYVARKR9RKGOUHHNKNVGGPDDLGKPQNOYHNKAVVKCXWXOQPZNSLATUJT9AUWRMPPSWHSTTYDFAQDXOCYTZHOYYGAIM9CELMZ9AZPWB9MJXGHOKDNNSZVUDAGXTJJSSZCPZVPZBYNNTUQABSXQWZCHDQSLGK9UOHCFKBIBNETK999999999999999999999999999999999999999999999999999999999999999999999999999999999NOXDXXKUDWLOFJLIPQIBRBMGDYCPGDNLQOLQS99EQYKBIU9VHCJVIPFUYCQDNY9APGEVYLCENJIOBLWNB999999999XKBRHUD99C99999999NKZKEKWLDKMJCI9N9XQOLWEPAYWSH9999999999999999999999999KDDTGZLIPBNZKMLTOLOXQVNGLASESDQVPTXALEKRMIOHQLUHD9ELQDBQETS9QFGTYOYWLNTSKKMVJAUXSIROUICDOXKSYZTDPEDKOQENTJOWJONDEWROCEJIEWFWLUAACVSJFTMCHHXJBJRKAAPUDXXVXFWP9X9999IROUICDOXKSYZTDPEDKOQENTJOWJONDEWROCEJIEWFWLUAACVSJFTMCHHXJBJRKAAPUDXXVXFWP9X9999";
private static final String TEST_TRYTES = "JUSTANOTHERTEST999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999PNGMCSNRCTRHCHPXYTPKEJYPCOWKOMRXZFHH9N9VDIKMNVAZCMIYRHVJIAZARZTUETJVFDMBEBIQE9QTH999999999999999999999999999JOTASPAM9999999999999999999VADPPWD99999999999999999999AQKWPYWBUEPGRZAVQUKYAVRPPNEIZZFHHLBESBBINMZCDU9GYMQAUKXSDLAHCB9XCFEPACLJGLHFUSTWJ999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999999";
private static final String TEST_MILESTONE = "SMYMAKKPSUKCKDRUEYCGZJTYCZ9HHDMDUWBAPXARGURPQRHTAJDASRWMIDTPTBNDKDEFBUTBGGAFX9999";
private static final Integer TEST_MILESTONE_INDEX = 8059;
private static final String TEST_MESSAGE = "JOTA";
private static final String TEST_TAG = "JOTASPAM9999999999999999999";
private static final String[] TEST_ADDRESSES = new String[]{"KHJXD9XKXPIVQRGREUIPVJTMEY9L9MXZAAKBBRYNINTIOXWBRMNLLW9MLGAXMGQWDBZLCOGFCBNKTDLDC"
, "MQSAAEDPMKIAJPPGNLIHPQIVFGLHNEGG9JNMSHOQSVQHBQBMLNHY9WVRTCOYUOWOIJHBQXIQVFPDF9YRW"
, "RGYOHMECRNVPYYPIAKEWHSOLBYOQPRFRPOJGHUMEGLICCUIPTZEXLWDLLPBNRXONUTQGLSAJSLHRXFVQD"
private static final String[] TEST_ADDRESSES = new String[]{"LXQHWNY9CQOHPNMKFJFIJHGEPAENAOVFRDIBF99PPHDTWJDCGHLYETXT9NPUVSNKT9XDTDYNJKJCPQMZCCOZVXMTXC"
, "P9UDUZMN9DEXCRQEKLJYSBSBZFCHOBPJSDKMLCCVJDOVOFDWMNBZRIRRZJGINOUMPJBMYYZEGRTIDUABD"
, "MIMVJEYREIIZLXOXQROMPJFCIX9NFVXD9ZQMNZERPI9OJIJFUWQ9WCTMKXEEPHYPWEZPHLJBJOFH9YTRB"
, "FOJHXRVJRFMJTFDUWJYYZXCZIJXKQALLXMLKHZFDMHWTIBBXUKSNSUYJLKYRQBNXKRSUXZHDTPWXYD9YF"
, "B9YNPQO9EXID9RDEEGLCBJBYKBLWHTOQOZKTLJDFPJZOPKJJTNUYUVVTDJPBCBYIWGPSCMNRZFGFHFSXH"
, "NQEFOAFIYKZOUXDFQ9X9PHCNSDETRTJZINZ9EYGKU99QJLDSTSC9VTBAA9FHLNLNYQXWLTNPRJDWCGIPP"
@ -59,7 +61,9 @@ public class IotaAPITest {
, "WDTFFXHBHMFQQVXQLBFJFVVHVIIAVYM9PFAZCHMKET9ESMHIRHSMVDJBZTXPTAFVIASMSXRDCIYVWVQNO"
, "XCCPS9GMTSUB9DXPVKLTBDHOFX9PJMBYZQYQEXMRQDPGQPLWRGZGXODYJKGVFOHHYUJRCSXAIDGYSAWRB"
, "KVEBCGMEOPDPRCQBPIEMZTTXYBURGZVNH9PLHKPMM9D9FUKWIGLKZROGNSYIFHULLWQWXCNAW9HKKVIDC"};
private static Gson gson = new GsonBuilder().create();
private static int MWM = 15;
private static Gson gson = new GsonBuilder().excludeFieldsWithModifiers(Modifier.TRANSIENT).create();
private IotaAPI iotaClient;
@Before
@ -96,6 +100,7 @@ public class IotaAPITest {
assertThat(res3.getAddresses().get(0), Is.is(TEST_ADDRESS_WITHOUT_CHECKSUM_SECURITY_LEVEL_3));
}
@Test
public void shouldPrepareTransfer() throws InvalidSecurityLevelException, NotEnoughBalanceException, InvalidAddressException, InvalidTransferException {
List<Transfer> transfers = new ArrayList<>();
@ -115,18 +120,20 @@ public class IotaAPITest {
@Test
public void shouldFindTransactionObjects() {
List<Transaction> ftr = iotaClient.findTransactionObjects(TEST_ADDRESSES);
System.out.println(ftr);
assertThat(ftr, IsNull.notNullValue());
}
@Test(expected = ArgumentException.class)
@Test(expected = IllegalAccessError.class)
public void shouldNotGetBundle() throws InvalidBundleException, ArgumentException, InvalidSignatureException {
GetBundleResponse gbr = iotaClient.getBundle(TEST_HASH);
GetBundleResponse gbr = iotaClient.getBundle("SADASD");
assertThat(gbr, IsNull.notNullValue());
}
@Test(expected = ArgumentException.class)
@Test
public void shouldGetBundle() throws InvalidBundleException, ArgumentException, InvalidSignatureException {
GetBundleResponse gbr = iotaClient.getBundle(TEST_HASH);
System.out.println(gbr);
assertThat(gbr, IsNull.notNullValue());
}
@ -145,20 +152,20 @@ public class IotaAPITest {
@Ignore
@Test
public void shouldReplayBundle() throws InvalidTrytesException, InvalidBundleException, InvalidSignatureException, ArgumentException {
ReplayBundleResponse rbr = iotaClient.replayBundle(TEST_TRYTES, 9, 18);
ReplayBundleResponse rbr = iotaClient.replayBundle(TEST_TRYTES, 9, MWM);
assertThat(rbr, IsNull.notNullValue());
}
@Ignore
@Test(expected = InvalidTrytesException.class)
public void shouldNotSendTrytes() throws InvalidTrytesException {
iotaClient.sendTrytes(new String[]{TEST_INVALID_TRYTES}, 9, 18);
iotaClient.sendTrytes(new String[]{TEST_INVALID_TRYTES}, 9, MWM);
}
@Ignore
@Test
public void shouldSendTrytes() throws InvalidTrytesException {
iotaClient.sendTrytes(new String[]{TEST_TRYTES}, 9, 18);
iotaClient.sendTrytes(new String[]{TEST_TRYTES}, 9, MWM);
}
@Ignore
@ -166,7 +173,7 @@ public class IotaAPITest {
public void shouldNotSendTransfer() throws ArgumentException, InvalidSignatureException, InvalidBundleException, NotEnoughBalanceException, InvalidSecurityLevelException, InvalidTrytesException, InvalidAddressException, InvalidTransferException {
List<Transfer> transfers = new ArrayList<>();
transfers.add(new jota.model.Transfer(TEST_ADDRESS_WITHOUT_CHECKSUM_SECURITY_LEVEL_2, 10000990, "JUSTANOTHERTEST", TEST_TAG));
SendTransferResponse str = iotaClient.sendTransfer(TEST_SEED2, 2, 9, 18, transfers, null, null);
SendTransferResponse str = iotaClient.sendTransfer(TEST_SEED2, 2, 9, MWM, transfers, null, null);
assertThat(str.getSuccessfully(), IsNull.notNullValue());
}
@ -174,8 +181,8 @@ public class IotaAPITest {
@Test
public void shouldSendTransfer() throws ArgumentException, InvalidSignatureException, InvalidBundleException, NotEnoughBalanceException, InvalidSecurityLevelException, InvalidTrytesException, InvalidAddressException, InvalidTransferException {
List<Transfer> transfers = new ArrayList<>();
transfers.add(new jota.model.Transfer(TEST_ADDRESS_WITHOUT_CHECKSUM_SECURITY_LEVEL_2, 0, "JUSTANOTHERTEST", TEST_TAG));
SendTransferResponse str = iotaClient.sendTransfer(TEST_SEED2, 2, 9, 18, transfers, null, null);
transfers.add(new jota.model.Transfer(TEST_ADDRESS_WITHOUT_CHECKSUM_SECURITY_LEVEL_2_2, 100, "JUSTANOTHERTEST", TEST_TAG));
SendTransferResponse str = iotaClient.sendTransfer(TEST_SEED1, 2, 9, MWM, transfers, null, null);
assertThat(str.getSuccessfully(), IsNull.notNullValue());
}
}

View File

@ -15,7 +15,7 @@ public class IotaCoreApiTest {
private static final String TEST_BUNDLE = "XZKJUUMQOYUQFKMWQZNTFMSS9FKJLOEV9DXXXWPMQRTNCOUSUQNTBIJTVORLOQPLYZOTMLFRHYKMTGZZU";
private static final String TEST_ADDRESS_WITH_CHECKSUM = "PNGMCSNRCTRHCHPXYTPKEJYPCOWKOMRXZFHH9N9VDIKMNVAZCMIYRHVJIAZARZTUETJVFDMBEBIQE9QTHBFWDAOEFA";
private static final String TEST_HASH = "OAATQS9VQLSXCLDJVJJVYUGONXAXOFMJOZNSYWRZSWECMXAQQURHQBJNLD9IOFEPGZEPEMPXCIVRX9999";
private static final String TEST_HASH = "OOAARHCXXCPMNZPUEYOOUIUCTWZSQGKNIECIKRBNUUJEVMLJAWGCXREXEQGNJUJKUXXQAWWAZYKB99999";
private static IotaAPICore proxy;
@Before