Skip to content

Commit 6f3cf57

Browse files
committed
generate random keys
1 parent c6a832c commit 6f3cf57

File tree

3 files changed

+63
-7
lines changed

3 files changed

+63
-7
lines changed

js/ethereum-utils/src/address.ts

Lines changed: 30 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,25 @@ import { H160 } from '@polkadot/types/interfaces';
22
import { KeyringPair } from '@polkadot/keyring/types';
33
import { encodeAddress, ethereumEncode } from '@polkadot/util-crypto';
44
import { hexToU8a, u8aToHex } from '@polkadot/util';
5-
import { HexString } from './payloads';
5+
import { EthereumKeyPair, HexString } from './payloads';
6+
import { ethers } from 'ethers';
7+
8+
/**
9+
* Creates a Random Ethereum key
10+
*/
11+
export function createRandomKey(): EthereumKeyPair {
12+
const k = ethers.Wallet.createRandom();
13+
return {
14+
publicKey: k.publicKey,
15+
privateKey: k.privateKey,
16+
address: {
17+
ethereumAddress: k.address,
18+
unifiedAddress: getUnified32BytesAddress(k.address),
19+
unifiedAddressSS58: getSS58AccountFromEthereumAccount(k.address),
20+
},
21+
mnemonic: k.mnemonic?.phrase ?? '',
22+
} as EthereumKeyPair;
23+
}
624

725
/**
826
* Create a partial KeyringPair from an Ethereum address
@@ -36,12 +54,8 @@ export function getUnifiedAddress(pair: KeyringPair): string {
3654
*/
3755
export function getUnifiedPublicKey(pair: KeyringPair): Uint8Array {
3856
if ('ethereum' === pair.type) {
39-
const ethAddressBytes = hexToU8a(ethereumEncode(pair.publicKey));
40-
const suffix = new Uint8Array(12).fill(0xee);
41-
const result = new Uint8Array(32);
42-
result.set(ethAddressBytes, 0);
43-
result.set(suffix, 20);
44-
return result;
57+
const unifiedHex = getUnified32BytesAddress(u8aToHex(pair.publicKey));
58+
return hexToU8a(unifiedHex);
4559
}
4660
if (pair.type === 'ecdsa') {
4761
throw new Error('Ecdsa key type is not supported and it should be replaced with ethereum ones!');
@@ -68,3 +82,12 @@ export function getSS58AccountFromEthereumAccount(accountId20Hex: string): strin
6882
result.set(suffix, 20);
6983
return encodeAddress(result);
7084
}
85+
86+
function getUnified32BytesAddress(ethAddressOrPublicKey: string): HexString {
87+
const ethAddressBytes = hexToU8a(ethereumEncode(ethAddressOrPublicKey));
88+
const suffix = new Uint8Array(12).fill(0xee);
89+
const result = new Uint8Array(32);
90+
result.set(ethAddressBytes, 0);
91+
result.set(suffix, 20);
92+
return u8aToHex(result);
93+
}

js/ethereum-utils/src/payloads.ts

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,26 @@ export interface EcdsaSignature {
66

77
export type ChainType = 'Mainnet-Frequency' | 'Paseo-Testnet-Frequency';
88

9+
export interface AddressWrapper {
10+
// 20 byte ethereum address in hex
11+
ethereumAddress: HexString;
12+
// 32 byte unified address in hex
13+
unifiedAddress: HexString;
14+
// SS58 unified address
15+
unifiedAddressSS58: string;
16+
}
17+
18+
export interface EthereumKeyPair {
19+
// private key of ethereum key
20+
privateKey: HexString;
21+
// 33 bytes public key
22+
publicKey: HexString;
23+
// different address representations
24+
address: AddressWrapper;
25+
// 12 word mnemonic
26+
mnemonic: string;
27+
}
28+
929
export interface PaginatedUpsertSignaturePayloadV2 {
1030
// type discriminator
1131
type: 'PaginatedUpsertSignaturePayloadV2';

js/ethereum-utils/test/address.test.ts

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import {
55
getSS58AccountFromEthereumAccount,
66
getUnifiedPublicKey,
77
getUnifiedAddress,
8+
createRandomKey,
89
} from '../src';
910
import { hexToU8a, u8aToHex } from '@polkadot/util';
1011

@@ -107,4 +108,16 @@ describe('Address tests', function () {
107108
assert.deepEqual(result, unifiedPublicKey);
108109
});
109110
});
111+
112+
describe('should create new keys', function () {
113+
it('it should generate random keys', function () {
114+
const key1 = createRandomKey();
115+
const key2 = createRandomKey();
116+
117+
assert.notDeepEqual(key1.publicKey, key2.publicKey);
118+
assert.notDeepEqual(key1.privateKey, key2.privateKey);
119+
assert.notDeepEqual(key1.address, key2.address);
120+
assert.notDeepEqual(key1.mnemonic, key2.mnemonic);
121+
});
122+
});
110123
});

0 commit comments

Comments
 (0)