diff --git a/js/package.json b/js/package.json
index abff29f4b..218452bf6 100644
--- a/js/package.json
+++ b/js/package.json
@@ -139,7 +139,6 @@
"blockies": "0.0.2",
"brace": "0.9.0",
"bytes": "2.4.0",
- "crypto-js": "3.1.9-1",
"debounce": "1.0.0",
"es6-error": "4.0.0",
"es6-promise": "4.0.5",
diff --git a/js/src/api/util/format.js b/js/src/api/util/format.js
index 531dfc549..f6976c13b 100644
--- a/js/src/api/util/format.js
+++ b/js/src/api/util/format.js
@@ -20,15 +20,21 @@ export function bytesToHex (bytes) {
return '0x' + bytes.map((b) => ('0' + b.toString(16)).slice(-2)).join('');
}
-export function hex2Ascii (_hex) {
- const hex = /^(?:0x)?(.*)$/.exec(_hex.toString())[1];
+export function hexToBytes (hex) {
+ const raw = toHex(hex).slice(2);
+ const bytes = [];
- let str = '';
-
- for (let i = 0; i < hex.length; i += 2) {
- str += String.fromCharCode(parseInt(hex.substr(i, 2), 16));
+ for (let i = 0; i < raw.length; i += 2) {
+ bytes.push(parseInt(raw.substr(i, 2), 16));
}
+ return bytes;
+}
+
+export function hexToAscii (hex) {
+ const bytes = hexToBytes(hex);
+ const str = bytes.map((byte) => String.fromCharCode(byte)).join('');
+
return str;
}
diff --git a/js/src/api/util/format.spec.js b/js/src/api/util/format.spec.js
index cfb07dee7..384c26d64 100644
--- a/js/src/api/util/format.spec.js
+++ b/js/src/api/util/format.spec.js
@@ -14,7 +14,7 @@
// You should have received a copy of the GNU General Public License
// along with Parity. If not, see .
-import { bytesToHex } from './format';
+import { bytesToHex, hexToBytes, hexToAscii, bytesToAscii, asciiToHex } from './format';
describe('api/util/format', () => {
describe('bytesToHex', () => {
@@ -26,4 +26,46 @@ describe('api/util/format', () => {
expect(bytesToHex([0, 15, 16])).to.equal('0x000f10');
});
});
+
+ describe('hexToBytes', () => {
+ it('correctly converts an empty string', () => {
+ expect(hexToBytes('')).to.deep.equal([]);
+ expect(hexToBytes('0x')).to.deep.equal([]);
+ });
+
+ it('correctly converts a non-empty string', () => {
+ expect(hexToBytes('0x000f10')).to.deep.equal([0, 15, 16]);
+ });
+ });
+
+ describe('asciiToHex', () => {
+ it('correctly converts an empty string', () => {
+ expect(asciiToHex('')).to.equal('0x');
+ });
+
+ it('correctly converts a non-empty string', () => {
+ expect(asciiToHex('abc')).to.equal('0x616263');
+ });
+ });
+
+ describe('hexToAscii', () => {
+ it('correctly converts an empty string', () => {
+ expect(hexToAscii('')).to.equal('');
+ expect(hexToAscii('0x')).to.equal('');
+ });
+
+ it('correctly converts a non-empty string', () => {
+ expect(hexToAscii('0x616263')).to.equal('abc');
+ });
+ });
+
+ describe('bytesToAscii', () => {
+ it('correctly converts an empty string', () => {
+ expect(bytesToAscii([])).to.equal('');
+ });
+
+ it('correctly converts a non-empty string', () => {
+ expect(bytesToAscii([97, 98, 99])).to.equal('abc');
+ });
+ });
});
diff --git a/js/src/api/util/index.js b/js/src/api/util/index.js
index e33bb9273..414816cdd 100644
--- a/js/src/api/util/index.js
+++ b/js/src/api/util/index.js
@@ -16,7 +16,7 @@
import { isAddress as isAddressValid, toChecksumAddress } from '../../abi/util/address';
import { decodeCallData, decodeMethodInput, methodToAbi } from './decode';
-import { bytesToHex, hex2Ascii, asciiToHex } from './format';
+import { bytesToHex, hexToAscii, asciiToHex } from './format';
import { fromWei, toWei } from './wei';
import { sha3 } from './sha3';
import { isArray, isFunction, isHex, isInstanceOf, isString } from './types';
@@ -30,7 +30,7 @@ export default {
isInstanceOf,
isString,
bytesToHex,
- hex2Ascii,
+ hexToAscii,
asciiToHex,
createIdentityImg,
decodeCallData,
diff --git a/js/src/api/util/sha3.js b/js/src/api/util/sha3.js
index 5a2c7c273..11ca6189a 100644
--- a/js/src/api/util/sha3.js
+++ b/js/src/api/util/sha3.js
@@ -14,21 +14,17 @@
// You should have received a copy of the GNU General Public License
// along with Parity. If not, see .
-import CryptoJS from 'crypto-js';
-import CryptoSha3 from 'crypto-js/sha3';
+import { keccak_256 } from 'js-sha3'; // eslint-disable-line
+
+import { hexToBytes } from './format';
export function sha3 (value, options) {
if (options && options.encoding === 'hex') {
- if (value.length > 2 && value.substr(0, 2) === '0x') {
- value = value.substr(2);
- }
-
- value = CryptoJS.enc.Hex.parse(value);
+ const bytes = hexToBytes(value);
+ return sha3(bytes);
}
- const hash = CryptoSha3(value, {
- outputLength: 256
- }).toString();
+ const hash = keccak_256(value);
return `0x${hash}`;
}
diff --git a/js/src/api/util/sha3.spec.js b/js/src/api/util/sha3.spec.js
index 20cd0e7d5..3446f7def 100644
--- a/js/src/api/util/sha3.spec.js
+++ b/js/src/api/util/sha3.spec.js
@@ -21,5 +21,16 @@ describe('api/util/sha3', () => {
it('constructs a correct sha3 value', () => {
expect(sha3('jacogr')).to.equal('0x2f4ff4b5a87abbd2edfed699db48a97744e028c7f7ce36444d40d29d792aa4dc');
});
+
+ it('constructs a correct sha3 encoded as hex', () => {
+ const key = '000000000000000000000000391694e7e0b0cce554cb130d723a9d27458f9298' + '0000000000000000000000000000000000000000000000000000000000000001';
+ expect(sha3(key, { encoding: 'hex' })).to.equal('0x6661e9d6d8b923d5bbaab1b96e1dd51ff6ea2a93520fdc9eb75d059238b8c5e9');
+ expect(sha3(`0x${key}`, { encoding: 'hex' })).to.equal('0x6661e9d6d8b923d5bbaab1b96e1dd51ff6ea2a93520fdc9eb75d059238b8c5e9');
+ });
+
+ it('constructs a correct sha3 from Uint8Array', () => {
+ expect(sha3('01020304', { encoding: 'hex' })).to.equal('0xa6885b3731702da62e8e4a8f584ac46a7f6822f4e2ba50fba902f67b1588d23b');
+ expect(sha3(Uint8Array.from([1, 2, 3, 4]))).to.equal('0xa6885b3731702da62e8e4a8f584ac46a7f6822f4e2ba50fba902f67b1588d23b');
+ });
});
});
diff --git a/js/src/contracts/badgereg.js b/js/src/contracts/badgereg.js
index 370236a26..0813caa47 100644
--- a/js/src/contracts/badgereg.js
+++ b/js/src/contracts/badgereg.js
@@ -14,7 +14,7 @@
// You should have received a copy of the GNU General Public License
// along with Parity. If not, see .
-import { bytesToHex, hex2Ascii } from '~/api/util/format';
+import { bytesToHex, hexToAscii } from '~/api/util/format';
import ABI from './abi/certifier.json';
@@ -62,7 +62,7 @@ export default class BadgeReg {
name = bytesToHex(name);
name = name === ZERO32
? null
- : hex2Ascii(name);
+ : hexToAscii(name);
return this.fetchMeta(id)
.then(({ title, icon }) => {
@@ -84,7 +84,7 @@ export default class BadgeReg {
})
.then(([ title, icon ]) => {
title = bytesToHex(title);
- title = title === ZERO32 ? null : hex2Ascii(title);
+ title = title === ZERO32 ? null : hexToAscii(title);
if (bytesToHex(icon) === ZERO32) {
icon = null;
diff --git a/js/src/ui/MethodDecoding/methodDecoding.js b/js/src/ui/MethodDecoding/methodDecoding.js
index a929d2681..59704a731 100644
--- a/js/src/ui/MethodDecoding/methodDecoding.js
+++ b/js/src/ui/MethodDecoding/methodDecoding.js
@@ -167,7 +167,7 @@ class MethodDecoding extends Component {
getAscii () {
const { api } = this.context;
const { transaction } = this.props;
- const ascii = api.util.hex2Ascii(transaction.input || transaction.data);
+ const ascii = api.util.hexToAscii(transaction.input || transaction.data);
return { value: ascii, valid: ASCII_INPUT.test(ascii) };
}
diff --git a/js/src/util/wallet.js b/js/src/util/wallet.js
index b6240ff01..81fe2859e 100644
--- a/js/src/util/wallet.js
+++ b/js/src/util/wallet.js
@@ -15,7 +15,7 @@
// along with Parity. If not, see .
import scrypt from 'scryptsy';
-import Transaction from 'ethereumjs-tx';
+import * as Transaction from 'ethereumjs-tx';
import { pbkdf2Sync } from 'crypto';
import { createDecipheriv } from 'browserify-aes';