Base58Utils { public static byte[] decode(final String input) throws IOException { if (null == input || input.length() == 0) { return new byte[0]; } final byte[] input58 = new byte[input.length()]; for (int i = 0; i < input.length(); ++i) { char c = input.charAt(i); int digit = c < 128 ? INDEXES[c] : -1; if (digit < 0) { if (logger.isInfoEnabled()) { logger.info("Input:\n{}", HexUtils.dump(input.getBytes())); } throw new UnsupportedEncodingException("Base58 decoding failed: " + digit + " at " + i); } input58[i] = (byte) digit; } int zeros = 0; while (zeros < input58.length && input58[zeros] == 0) { ++zeros; } byte[] decoded = new byte[input.length()]; int outputStart = decoded.length; for (int inputStart = zeros; inputStart < input58.length;) { decoded[--outputStart] = divmod(input58, inputStart, 58, 256); if (input58[inputStart] == 0) { ++inputStart; } } while (outputStart < decoded.length && decoded[outputStart] == 0) { ++outputStart; } return Arrays.copyOfRange(decoded, outputStart - zeros, decoded.length); }  static String encode(final byte[] input); static byte[] decode(final String input); static String encodeWithCheck(final byte[] rawData); static byte[] decodeWithCheck(final String encoded);  }
@Test public void testDecode() throws IOException { assertTrue(Arrays.equals(DECODED, Base58Utils.decode(ENCODED))); assertTrue(Arrays.equals(new byte[0], Base58Utils.decode(""))); assertTrue(Arrays.equals(new byte[0], Base58Utils.decode(null))); }
@Test(expected = IOException.class) public void shouldThrowExceptionWhenDecode() throws IOException { Base58Utils.decode("="); }
@Test(expected = IOException.class) public void shouldThrowExceptionWhenDecodeWithCheck() throws IOException { Base58Utils.decode("="); }