@ledgerhq/coin-solana 0.22.0 → 0.22.1-hotfix.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.turbo/turbo-build.log +1 -1
- package/CHANGELOG.md +6 -0
- package/lib/__tests__/unit/hw-signMessage.unit.test.js +9 -4
- package/lib/__tests__/unit/hw-signMessage.unit.test.js.map +1 -1
- package/lib/hw-signMessage.d.ts.map +1 -1
- package/lib/hw-signMessage.js +9 -2
- package/lib/hw-signMessage.js.map +1 -1
- package/lib-es/__tests__/unit/hw-signMessage.unit.test.js +9 -4
- package/lib-es/__tests__/unit/hw-signMessage.unit.test.js.map +1 -1
- package/lib-es/hw-signMessage.d.ts.map +1 -1
- package/lib-es/hw-signMessage.js +9 -2
- package/lib-es/hw-signMessage.js.map +1 -1
- package/package.json +1 -1
- package/src/__tests__/unit/hw-signMessage.unit.test.ts +11 -4
- package/src/hw-signMessage.ts +14 -5
package/.turbo/turbo-build.log
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
|
|
2
|
-
> @ledgerhq/coin-solana@0.22.0 build /home/runner/work/ledger-live/ledger-live/libs/coin-modules/coin-solana
|
|
2
|
+
> @ledgerhq/coin-solana@0.22.1-hotfix.0 build /home/runner/work/ledger-live/ledger-live/libs/coin-modules/coin-solana
|
|
3
3
|
> tsc --outDir lib --module commonjs --moduleResolution node10 && tsc -m ES6 --outDir lib-es
|
|
4
4
|
|
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,11 @@
|
|
|
1
1
|
# @ledgerhq/coin-solana
|
|
2
2
|
|
|
3
|
+
## 0.22.1-hotfix.0
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- [#10261](https://github.com/LedgerHQ/ledger-live/pull/10261) [`422c046`](https://github.com/LedgerHQ/ledger-live/commit/422c0468aa865a0840bb6c23506173621b0930be) Thanks [@live-github-bot](https://github.com/apps/live-github-bot)! - feat: solana off-chain message signing returns the envelope with the signedMessage
|
|
8
|
+
|
|
3
9
|
## 0.22.0
|
|
4
10
|
|
|
5
11
|
### Minor Changes
|
|
@@ -6,6 +6,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
6
6
|
const hw_signMessage_1 = require("../../hw-signMessage");
|
|
7
7
|
const signer_1 = require("../../signer");
|
|
8
8
|
const config_1 = __importDefault(require("../../config"));
|
|
9
|
+
const bs58_1 = __importDefault(require("bs58"));
|
|
9
10
|
config_1.default.setCoinConfig(() => ({
|
|
10
11
|
legacyOCMSMaxVersion: "1.8.2",
|
|
11
12
|
queuedInterval: 1,
|
|
@@ -16,7 +17,8 @@ describe("Testing call to hardware off-chain sign message on Solana", () => {
|
|
|
16
17
|
it("should sign a message off-chain on hardware and return the generated signature", async () => {
|
|
17
18
|
const APP_VERSION = "1.8.2";
|
|
18
19
|
const SIGNATURE = "4gVuB1KsM58fb3vRpnDucwW4Vi6fVGA51QDQd9ARvx4GH5yYVDPzDnvzUbSJf3YLWWdsX7zCMSN9N1GMnTYwWiJf";
|
|
19
|
-
const BASE58_SIGNATURE = "
|
|
20
|
+
const BASE58_SIGNATURE = "23mXB2pc8EQzc2mT3VJR4KkBFZaUVL9Pn7LUn8NMKeHKbS1hMj1QqGsUHHD3JMGhAWtFfcmnPhFSpPttChTNzsB9";
|
|
21
|
+
const BASE58_ENVELOPE = "LwsiJTXpooGk31Y4CaV1Qs12wTabaF83J9Tg32kPb7kk9BXc8ncpoDBzV1NPSumKckhx7dVwFH729vdvB71f8KGpp18g29N2XAD3MUiNz9tPJu36GGN4pkL7vXurXUeQqMTXdJMdH2tzaXkT3vQ9hSLDfBPhQ7Vx9Echz5CYu5u4hZapaytx177WNke8oWDTqABnqQZ3YDGt7vYDoJ2LkiGHqcqXfeVmmsAtuALSxqo75zrWi7EXadQ9CZWWX7tFnXHLY6kEksqVj2ERM9RZEyNQ3tt";
|
|
20
22
|
const getAppConfigurationMock = jest.fn(() => {
|
|
21
23
|
return Promise.resolve({
|
|
22
24
|
version: APP_VERSION,
|
|
@@ -39,14 +41,16 @@ describe("Testing call to hardware off-chain sign message on Solana", () => {
|
|
|
39
41
|
const messageHex = "54657374696E67206F6E20536F6C616E61";
|
|
40
42
|
const offchainMessage = "ff736f6c616e61206f6666636861696e00000000000000000000000000000000000000000000000000000000000000000000016b4a46c53959cac0eff146ab323053cfc503321adfd453a7c67c91a24be03235220035343635373337343639364536373230364636453230353336463643363136453631";
|
|
41
43
|
const result = await (0, hw_signMessage_1.signMessage)(signerContext)("", { freshAddressPath: accountFreshAddressPath, freshAddress }, { message: messageHex });
|
|
42
|
-
expect(result.signature).toEqual(
|
|
44
|
+
expect(result.signature).toEqual(BASE58_ENVELOPE);
|
|
45
|
+
expect(bs58_1.default.encode(bs58_1.default.decode(result.signature).subarray(1, 65))).toEqual(BASE58_SIGNATURE);
|
|
43
46
|
expect(signMessageMock).toHaveBeenCalledTimes(1);
|
|
44
47
|
expect(signMessageMock).toHaveBeenCalledWith(accountFreshAddressPath, offchainMessage);
|
|
45
48
|
});
|
|
46
49
|
it("should sign a message off-chain on legacy hardware and return the generated signature", async () => {
|
|
47
50
|
const APP_VERSION = "1.7.1";
|
|
48
51
|
const SIGNATURE = "4gVuB1KsM58fb3vRpnDucwW4Vi6fVGA51QDQd9ARvx4GH5yYVDPzDnvzUbSJf3YLWWdsX7zCMSN9N1GMnTYwWiJf";
|
|
49
|
-
const BASE58_SIGNATURE = "
|
|
52
|
+
const BASE58_SIGNATURE = "23mXB2pc8EQzc2mT3VJR4KkBFZaUVL9Pn7LUn8NMKeHKbS1hMj1QqGsUHHD3JMGhAWtFfcmnPhFSpPttChTNzsB9";
|
|
53
|
+
const BASE58_ENVELOPE = "tDAHsdMRLpSiAFbdWRS6d7TyG64QSwJFuRSHNH6UyjE8wQwDgawYRsUsau2n9s5drPkmDLTJdTrkA5uRYsHmmfzuMsBQvo6e72LwNjfNhmVko8ffmfM1ZNKZmyiurvDb2nfoFsLXmYTainNmRKwS6iGSBvWBYHRDMwUiX2z15gBokN2iMhuCvDsFHHVn7H4vQG";
|
|
50
54
|
const getAppConfigurationMock = jest.fn(() => {
|
|
51
55
|
return Promise.resolve({
|
|
52
56
|
version: APP_VERSION,
|
|
@@ -69,7 +73,8 @@ describe("Testing call to hardware off-chain sign message on Solana", () => {
|
|
|
69
73
|
const messageHex = "54657374696E67206F6E20536F6C616E61";
|
|
70
74
|
const offchainMessage = "ff736f6c616e61206f6666636861696e0000220035343635373337343639364536373230364636453230353336463643363136453631";
|
|
71
75
|
const result = await (0, hw_signMessage_1.signMessage)(signerContext)("", { freshAddressPath: accountFreshAddressPath, freshAddress }, { message: messageHex });
|
|
72
|
-
expect(result.signature).toEqual(
|
|
76
|
+
expect(result.signature).toEqual(BASE58_ENVELOPE);
|
|
77
|
+
expect(bs58_1.default.encode(bs58_1.default.decode(result.signature).subarray(1, 65))).toEqual(BASE58_SIGNATURE);
|
|
73
78
|
expect(signMessageMock).toHaveBeenCalledTimes(1);
|
|
74
79
|
expect(signMessageMock).toHaveBeenCalledWith(accountFreshAddressPath, offchainMessage);
|
|
75
80
|
});
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"hw-signMessage.unit.test.js","sourceRoot":"","sources":["../../../src/__tests__/unit/hw-signMessage.unit.test.ts"],"names":[],"mappings":";;;;;AAEA,yDAAmD;AACnD,yCAA+D;AAC/D,0DAAsC;
|
|
1
|
+
{"version":3,"file":"hw-signMessage.unit.test.js","sourceRoot":"","sources":["../../../src/__tests__/unit/hw-signMessage.unit.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"hw-signMessage.d.ts","sourceRoot":"","sources":["../src/hw-signMessage.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,aAAa,EAAE,MAAM,iCAAiC,CAAC;AAChE,OAAO,EAAE,OAAO,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,sBAAsB,CAAC;AACrE,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;
|
|
1
|
+
{"version":3,"file":"hw-signMessage.d.ts","sourceRoot":"","sources":["../src/hw-signMessage.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,aAAa,EAAE,MAAM,iCAAiC,CAAC;AAChE,OAAO,EAAE,OAAO,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,sBAAsB,CAAC;AACrE,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AAMxC,eAAO,MAAM,WAAW,kBACN,cAAc,YAAY,CAAC,gBAE/B,QAAQ,WACT,OAAO,kBACA,UAAU,KACzB,QAAQ;IACT,SAAS,EAAE,MAAM,CAAC;CACnB,CA2BA,CAAC"}
|
package/lib/hw-signMessage.js
CHANGED
|
@@ -8,17 +8,24 @@ const semver_1 = __importDefault(require("semver"));
|
|
|
8
8
|
const format_1 = require("./offchainMessage/format");
|
|
9
9
|
const config_1 = __importDefault(require("./config"));
|
|
10
10
|
const bs58_1 = __importDefault(require("bs58"));
|
|
11
|
+
const invariant_1 = __importDefault(require("invariant"));
|
|
11
12
|
const signMessage = (signerContext) => async (deviceId, account, messageOptions) => {
|
|
12
13
|
const message = messageOptions.message;
|
|
13
14
|
if (!message || typeof message !== "string") {
|
|
14
15
|
throw new Error("Sign off-chain message on Solana must be only used with DefaultMessage type");
|
|
15
16
|
}
|
|
17
|
+
let signedMessage;
|
|
16
18
|
const result = await signerContext(deviceId, async (signer) => {
|
|
17
19
|
const { version } = await signer.getAppConfiguration();
|
|
18
20
|
const isLegacy = semver_1.default.lt(version, config_1.default.getCoinConfig().legacyOCMSMaxVersion);
|
|
19
|
-
|
|
21
|
+
signedMessage = (0, format_1.toOffChainMessage)(message, account.freshAddress, isLegacy);
|
|
22
|
+
return signer.signMessage(account.freshAddressPath, signedMessage.toString("hex"));
|
|
20
23
|
});
|
|
21
|
-
|
|
24
|
+
(0, invariant_1.default)(signedMessage, "signedMessage should exist");
|
|
25
|
+
const signatureCount = Buffer.from([1]);
|
|
26
|
+
// https://docs.anza.xyz/proposals/off-chain-message-signing#envelope
|
|
27
|
+
const envelope = Buffer.concat([signatureCount, result.signature, signedMessage]);
|
|
28
|
+
return { signature: bs58_1.default.encode(envelope) };
|
|
22
29
|
};
|
|
23
30
|
exports.signMessage = signMessage;
|
|
24
31
|
//# sourceMappingURL=hw-signMessage.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"hw-signMessage.js","sourceRoot":"","sources":["../src/hw-signMessage.ts"],"names":[],"mappings":";;;;;;AAAA,oDAA4B;AAI5B,qDAA6D;AAC7D,sDAAkC;AAClC,gDAAwB;
|
|
1
|
+
{"version":3,"file":"hw-signMessage.js","sourceRoot":"","sources":["../src/hw-signMessage.ts"],"names":[],"mappings":";;;;;;AAAA,oDAA4B;AAI5B,qDAA6D;AAC7D,sDAAkC;AAClC,gDAAwB;AACxB,0DAAkC;AAE3B,MAAM,WAAW,GACtB,CAAC,aAA0C,EAAE,EAAE,CAC/C,KAAK,EACH,QAAkB,EAClB,OAAgB,EAChB,cAA0B,EAGzB,EAAE;IACH,MAAM,OAAO,GAAG,cAAc,CAAC,OAAO,CAAC;IACvC,IAAI,CAAC,OAAO,IAAI,OAAO,OAAO,KAAK,QAAQ,EAAE,CAAC;QAC5C,MAAM,IAAI,KAAK,CACb,6EAA6E,CAC9E,CAAC;IACJ,CAAC;IAED,IAAI,aAAiC,CAAC;IAEtC,MAAM,MAAM,GAAG,MAAM,aAAa,CAAC,QAAQ,EAAE,KAAK,EAAC,MAAM,EAAC,EAAE;QAC1D,MAAM,EAAE,OAAO,EAAE,GAAG,MAAM,MAAM,CAAC,mBAAmB,EAAE,CAAC;QACvD,MAAM,QAAQ,GAAG,gBAAM,CAAC,EAAE,CAAC,OAAO,EAAE,gBAAU,CAAC,aAAa,EAAE,CAAC,oBAAoB,CAAC,CAAC;QAErF,aAAa,GAAG,IAAA,0BAAiB,EAAC,OAAO,EAAE,OAAO,CAAC,YAAY,EAAE,QAAQ,CAAC,CAAC;QAE3E,OAAO,MAAM,CAAC,WAAW,CAAC,OAAO,CAAC,gBAAgB,EAAE,aAAa,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC;IACrF,CAAC,CAAC,CAAC;IAEH,IAAA,mBAAS,EAAC,aAAa,EAAE,4BAA4B,CAAC,CAAC;IAEvD,MAAM,cAAc,GAAG,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAExC,qEAAqE;IACrE,MAAM,QAAQ,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,cAAc,EAAE,MAAM,CAAC,SAAS,EAAE,aAAa,CAAC,CAAC,CAAC;IAElF,OAAO,EAAE,SAAS,EAAE,cAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,EAAE,CAAC;AAC9C,CAAC,CAAC;AAnCS,QAAA,WAAW,eAmCpB"}
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { signMessage } from "../../hw-signMessage";
|
|
2
2
|
import { PubKeyDisplayMode } from "../../signer";
|
|
3
3
|
import coinConfig from "../../config";
|
|
4
|
+
import bs58 from "bs58";
|
|
4
5
|
coinConfig.setCoinConfig(() => ({
|
|
5
6
|
legacyOCMSMaxVersion: "1.8.2",
|
|
6
7
|
queuedInterval: 1,
|
|
@@ -11,7 +12,8 @@ describe("Testing call to hardware off-chain sign message on Solana", () => {
|
|
|
11
12
|
it("should sign a message off-chain on hardware and return the generated signature", async () => {
|
|
12
13
|
const APP_VERSION = "1.8.2";
|
|
13
14
|
const SIGNATURE = "4gVuB1KsM58fb3vRpnDucwW4Vi6fVGA51QDQd9ARvx4GH5yYVDPzDnvzUbSJf3YLWWdsX7zCMSN9N1GMnTYwWiJf";
|
|
14
|
-
const BASE58_SIGNATURE = "
|
|
15
|
+
const BASE58_SIGNATURE = "23mXB2pc8EQzc2mT3VJR4KkBFZaUVL9Pn7LUn8NMKeHKbS1hMj1QqGsUHHD3JMGhAWtFfcmnPhFSpPttChTNzsB9";
|
|
16
|
+
const BASE58_ENVELOPE = "LwsiJTXpooGk31Y4CaV1Qs12wTabaF83J9Tg32kPb7kk9BXc8ncpoDBzV1NPSumKckhx7dVwFH729vdvB71f8KGpp18g29N2XAD3MUiNz9tPJu36GGN4pkL7vXurXUeQqMTXdJMdH2tzaXkT3vQ9hSLDfBPhQ7Vx9Echz5CYu5u4hZapaytx177WNke8oWDTqABnqQZ3YDGt7vYDoJ2LkiGHqcqXfeVmmsAtuALSxqo75zrWi7EXadQ9CZWWX7tFnXHLY6kEksqVj2ERM9RZEyNQ3tt";
|
|
15
17
|
const getAppConfigurationMock = jest.fn(() => {
|
|
16
18
|
return Promise.resolve({
|
|
17
19
|
version: APP_VERSION,
|
|
@@ -34,14 +36,16 @@ describe("Testing call to hardware off-chain sign message on Solana", () => {
|
|
|
34
36
|
const messageHex = "54657374696E67206F6E20536F6C616E61";
|
|
35
37
|
const offchainMessage = "ff736f6c616e61206f6666636861696e00000000000000000000000000000000000000000000000000000000000000000000016b4a46c53959cac0eff146ab323053cfc503321adfd453a7c67c91a24be03235220035343635373337343639364536373230364636453230353336463643363136453631";
|
|
36
38
|
const result = await signMessage(signerContext)("", { freshAddressPath: accountFreshAddressPath, freshAddress }, { message: messageHex });
|
|
37
|
-
expect(result.signature).toEqual(
|
|
39
|
+
expect(result.signature).toEqual(BASE58_ENVELOPE);
|
|
40
|
+
expect(bs58.encode(bs58.decode(result.signature).subarray(1, 65))).toEqual(BASE58_SIGNATURE);
|
|
38
41
|
expect(signMessageMock).toHaveBeenCalledTimes(1);
|
|
39
42
|
expect(signMessageMock).toHaveBeenCalledWith(accountFreshAddressPath, offchainMessage);
|
|
40
43
|
});
|
|
41
44
|
it("should sign a message off-chain on legacy hardware and return the generated signature", async () => {
|
|
42
45
|
const APP_VERSION = "1.7.1";
|
|
43
46
|
const SIGNATURE = "4gVuB1KsM58fb3vRpnDucwW4Vi6fVGA51QDQd9ARvx4GH5yYVDPzDnvzUbSJf3YLWWdsX7zCMSN9N1GMnTYwWiJf";
|
|
44
|
-
const BASE58_SIGNATURE = "
|
|
47
|
+
const BASE58_SIGNATURE = "23mXB2pc8EQzc2mT3VJR4KkBFZaUVL9Pn7LUn8NMKeHKbS1hMj1QqGsUHHD3JMGhAWtFfcmnPhFSpPttChTNzsB9";
|
|
48
|
+
const BASE58_ENVELOPE = "tDAHsdMRLpSiAFbdWRS6d7TyG64QSwJFuRSHNH6UyjE8wQwDgawYRsUsau2n9s5drPkmDLTJdTrkA5uRYsHmmfzuMsBQvo6e72LwNjfNhmVko8ffmfM1ZNKZmyiurvDb2nfoFsLXmYTainNmRKwS6iGSBvWBYHRDMwUiX2z15gBokN2iMhuCvDsFHHVn7H4vQG";
|
|
45
49
|
const getAppConfigurationMock = jest.fn(() => {
|
|
46
50
|
return Promise.resolve({
|
|
47
51
|
version: APP_VERSION,
|
|
@@ -64,7 +68,8 @@ describe("Testing call to hardware off-chain sign message on Solana", () => {
|
|
|
64
68
|
const messageHex = "54657374696E67206F6E20536F6C616E61";
|
|
65
69
|
const offchainMessage = "ff736f6c616e61206f6666636861696e0000220035343635373337343639364536373230364636453230353336463643363136453631";
|
|
66
70
|
const result = await signMessage(signerContext)("", { freshAddressPath: accountFreshAddressPath, freshAddress }, { message: messageHex });
|
|
67
|
-
expect(result.signature).toEqual(
|
|
71
|
+
expect(result.signature).toEqual(BASE58_ENVELOPE);
|
|
72
|
+
expect(bs58.encode(bs58.decode(result.signature).subarray(1, 65))).toEqual(BASE58_SIGNATURE);
|
|
68
73
|
expect(signMessageMock).toHaveBeenCalledTimes(1);
|
|
69
74
|
expect(signMessageMock).toHaveBeenCalledWith(accountFreshAddressPath, offchainMessage);
|
|
70
75
|
});
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"hw-signMessage.unit.test.js","sourceRoot":"","sources":["../../../src/__tests__/unit/hw-signMessage.unit.test.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,WAAW,EAAE,MAAM,sBAAsB,CAAC;AACnD,OAAO,EAAE,iBAAiB,EAAgB,MAAM,cAAc,CAAC;AAC/D,OAAO,UAAU,MAAM,cAAc,CAAC;
|
|
1
|
+
{"version":3,"file":"hw-signMessage.unit.test.js","sourceRoot":"","sources":["../../../src/__tests__/unit/hw-signMessage.unit.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"hw-signMessage.d.ts","sourceRoot":"","sources":["../src/hw-signMessage.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,aAAa,EAAE,MAAM,iCAAiC,CAAC;AAChE,OAAO,EAAE,OAAO,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,sBAAsB,CAAC;AACrE,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;
|
|
1
|
+
{"version":3,"file":"hw-signMessage.d.ts","sourceRoot":"","sources":["../src/hw-signMessage.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,aAAa,EAAE,MAAM,iCAAiC,CAAC;AAChE,OAAO,EAAE,OAAO,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,sBAAsB,CAAC;AACrE,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AAMxC,eAAO,MAAM,WAAW,kBACN,cAAc,YAAY,CAAC,gBAE/B,QAAQ,WACT,OAAO,kBACA,UAAU,KACzB,QAAQ;IACT,SAAS,EAAE,MAAM,CAAC;CACnB,CA2BA,CAAC"}
|
package/lib-es/hw-signMessage.js
CHANGED
|
@@ -2,16 +2,23 @@ import semver from "semver";
|
|
|
2
2
|
import { toOffChainMessage } from "./offchainMessage/format";
|
|
3
3
|
import coinConfig from "./config";
|
|
4
4
|
import bs58 from "bs58";
|
|
5
|
+
import invariant from "invariant";
|
|
5
6
|
export const signMessage = (signerContext) => async (deviceId, account, messageOptions) => {
|
|
6
7
|
const message = messageOptions.message;
|
|
7
8
|
if (!message || typeof message !== "string") {
|
|
8
9
|
throw new Error("Sign off-chain message on Solana must be only used with DefaultMessage type");
|
|
9
10
|
}
|
|
11
|
+
let signedMessage;
|
|
10
12
|
const result = await signerContext(deviceId, async (signer) => {
|
|
11
13
|
const { version } = await signer.getAppConfiguration();
|
|
12
14
|
const isLegacy = semver.lt(version, coinConfig.getCoinConfig().legacyOCMSMaxVersion);
|
|
13
|
-
|
|
15
|
+
signedMessage = toOffChainMessage(message, account.freshAddress, isLegacy);
|
|
16
|
+
return signer.signMessage(account.freshAddressPath, signedMessage.toString("hex"));
|
|
14
17
|
});
|
|
15
|
-
|
|
18
|
+
invariant(signedMessage, "signedMessage should exist");
|
|
19
|
+
const signatureCount = Buffer.from([1]);
|
|
20
|
+
// https://docs.anza.xyz/proposals/off-chain-message-signing#envelope
|
|
21
|
+
const envelope = Buffer.concat([signatureCount, result.signature, signedMessage]);
|
|
22
|
+
return { signature: bs58.encode(envelope) };
|
|
16
23
|
};
|
|
17
24
|
//# sourceMappingURL=hw-signMessage.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"hw-signMessage.js","sourceRoot":"","sources":["../src/hw-signMessage.ts"],"names":[],"mappings":"AAAA,OAAO,MAAM,MAAM,QAAQ,CAAC;AAI5B,OAAO,EAAE,iBAAiB,EAAE,MAAM,0BAA0B,CAAC;AAC7D,OAAO,UAAU,MAAM,UAAU,CAAC;AAClC,OAAO,IAAI,MAAM,MAAM,CAAC;
|
|
1
|
+
{"version":3,"file":"hw-signMessage.js","sourceRoot":"","sources":["../src/hw-signMessage.ts"],"names":[],"mappings":"AAAA,OAAO,MAAM,MAAM,QAAQ,CAAC;AAI5B,OAAO,EAAE,iBAAiB,EAAE,MAAM,0BAA0B,CAAC;AAC7D,OAAO,UAAU,MAAM,UAAU,CAAC;AAClC,OAAO,IAAI,MAAM,MAAM,CAAC;AACxB,OAAO,SAAS,MAAM,WAAW,CAAC;AAElC,MAAM,CAAC,MAAM,WAAW,GACtB,CAAC,aAA0C,EAAE,EAAE,CAC/C,KAAK,EACH,QAAkB,EAClB,OAAgB,EAChB,cAA0B,EAGzB,EAAE;IACH,MAAM,OAAO,GAAG,cAAc,CAAC,OAAO,CAAC;IACvC,IAAI,CAAC,OAAO,IAAI,OAAO,OAAO,KAAK,QAAQ,EAAE,CAAC;QAC5C,MAAM,IAAI,KAAK,CACb,6EAA6E,CAC9E,CAAC;IACJ,CAAC;IAED,IAAI,aAAiC,CAAC;IAEtC,MAAM,MAAM,GAAG,MAAM,aAAa,CAAC,QAAQ,EAAE,KAAK,EAAC,MAAM,EAAC,EAAE;QAC1D,MAAM,EAAE,OAAO,EAAE,GAAG,MAAM,MAAM,CAAC,mBAAmB,EAAE,CAAC;QACvD,MAAM,QAAQ,GAAG,MAAM,CAAC,EAAE,CAAC,OAAO,EAAE,UAAU,CAAC,aAAa,EAAE,CAAC,oBAAoB,CAAC,CAAC;QAErF,aAAa,GAAG,iBAAiB,CAAC,OAAO,EAAE,OAAO,CAAC,YAAY,EAAE,QAAQ,CAAC,CAAC;QAE3E,OAAO,MAAM,CAAC,WAAW,CAAC,OAAO,CAAC,gBAAgB,EAAE,aAAa,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC;IACrF,CAAC,CAAC,CAAC;IAEH,SAAS,CAAC,aAAa,EAAE,4BAA4B,CAAC,CAAC;IAEvD,MAAM,cAAc,GAAG,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAExC,qEAAqE;IACrE,MAAM,QAAQ,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,cAAc,EAAE,MAAM,CAAC,SAAS,EAAE,aAAa,CAAC,CAAC,CAAC;IAElF,OAAO,EAAE,SAAS,EAAE,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,EAAE,CAAC;AAC9C,CAAC,CAAC"}
|
package/package.json
CHANGED
|
@@ -3,6 +3,7 @@ import { Account, AnyMessage, TypedEvmMessage } from "@ledgerhq/types-live";
|
|
|
3
3
|
import { signMessage } from "../../hw-signMessage";
|
|
4
4
|
import { PubKeyDisplayMode, SolanaSigner } from "../../signer";
|
|
5
5
|
import coinConfig from "../../config";
|
|
6
|
+
import bs58 from "bs58";
|
|
6
7
|
|
|
7
8
|
coinConfig.setCoinConfig(() => ({
|
|
8
9
|
legacyOCMSMaxVersion: "1.8.2",
|
|
@@ -18,7 +19,9 @@ describe("Testing call to hardware off-chain sign message on Solana", () => {
|
|
|
18
19
|
"4gVuB1KsM58fb3vRpnDucwW4Vi6fVGA51QDQd9ARvx4GH5yYVDPzDnvzUbSJf3YLWWdsX7zCMSN9N1GMnTYwWiJf";
|
|
19
20
|
|
|
20
21
|
const BASE58_SIGNATURE =
|
|
21
|
-
"
|
|
22
|
+
"23mXB2pc8EQzc2mT3VJR4KkBFZaUVL9Pn7LUn8NMKeHKbS1hMj1QqGsUHHD3JMGhAWtFfcmnPhFSpPttChTNzsB9";
|
|
23
|
+
const BASE58_ENVELOPE =
|
|
24
|
+
"LwsiJTXpooGk31Y4CaV1Qs12wTabaF83J9Tg32kPb7kk9BXc8ncpoDBzV1NPSumKckhx7dVwFH729vdvB71f8KGpp18g29N2XAD3MUiNz9tPJu36GGN4pkL7vXurXUeQqMTXdJMdH2tzaXkT3vQ9hSLDfBPhQ7Vx9Echz5CYu5u4hZapaytx177WNke8oWDTqABnqQZ3YDGt7vYDoJ2LkiGHqcqXfeVmmsAtuALSxqo75zrWi7EXadQ9CZWWX7tFnXHLY6kEksqVj2ERM9RZEyNQ3tt";
|
|
22
25
|
|
|
23
26
|
const getAppConfigurationMock = jest.fn(() => {
|
|
24
27
|
return Promise.resolve({
|
|
@@ -50,7 +53,8 @@ describe("Testing call to hardware off-chain sign message on Solana", () => {
|
|
|
50
53
|
{ message: messageHex },
|
|
51
54
|
);
|
|
52
55
|
|
|
53
|
-
expect(result.signature).toEqual(
|
|
56
|
+
expect(result.signature).toEqual(BASE58_ENVELOPE);
|
|
57
|
+
expect(bs58.encode(bs58.decode(result.signature).subarray(1, 65))).toEqual(BASE58_SIGNATURE);
|
|
54
58
|
expect(signMessageMock).toHaveBeenCalledTimes(1);
|
|
55
59
|
expect(signMessageMock).toHaveBeenCalledWith(accountFreshAddressPath, offchainMessage);
|
|
56
60
|
});
|
|
@@ -61,7 +65,9 @@ describe("Testing call to hardware off-chain sign message on Solana", () => {
|
|
|
61
65
|
"4gVuB1KsM58fb3vRpnDucwW4Vi6fVGA51QDQd9ARvx4GH5yYVDPzDnvzUbSJf3YLWWdsX7zCMSN9N1GMnTYwWiJf";
|
|
62
66
|
|
|
63
67
|
const BASE58_SIGNATURE =
|
|
64
|
-
"
|
|
68
|
+
"23mXB2pc8EQzc2mT3VJR4KkBFZaUVL9Pn7LUn8NMKeHKbS1hMj1QqGsUHHD3JMGhAWtFfcmnPhFSpPttChTNzsB9";
|
|
69
|
+
const BASE58_ENVELOPE =
|
|
70
|
+
"tDAHsdMRLpSiAFbdWRS6d7TyG64QSwJFuRSHNH6UyjE8wQwDgawYRsUsau2n9s5drPkmDLTJdTrkA5uRYsHmmfzuMsBQvo6e72LwNjfNhmVko8ffmfM1ZNKZmyiurvDb2nfoFsLXmYTainNmRKwS6iGSBvWBYHRDMwUiX2z15gBokN2iMhuCvDsFHHVn7H4vQG";
|
|
65
71
|
|
|
66
72
|
const getAppConfigurationMock = jest.fn(() => {
|
|
67
73
|
return Promise.resolve({
|
|
@@ -93,7 +99,8 @@ describe("Testing call to hardware off-chain sign message on Solana", () => {
|
|
|
93
99
|
{ message: messageHex },
|
|
94
100
|
);
|
|
95
101
|
|
|
96
|
-
expect(result.signature).toEqual(
|
|
102
|
+
expect(result.signature).toEqual(BASE58_ENVELOPE);
|
|
103
|
+
expect(bs58.encode(bs58.decode(result.signature).subarray(1, 65))).toEqual(BASE58_SIGNATURE);
|
|
97
104
|
expect(signMessageMock).toHaveBeenCalledTimes(1);
|
|
98
105
|
expect(signMessageMock).toHaveBeenCalledWith(accountFreshAddressPath, offchainMessage);
|
|
99
106
|
});
|
package/src/hw-signMessage.ts
CHANGED
|
@@ -5,6 +5,7 @@ import { SolanaSigner } from "./signer";
|
|
|
5
5
|
import { toOffChainMessage } from "./offchainMessage/format";
|
|
6
6
|
import coinConfig from "./config";
|
|
7
7
|
import bs58 from "bs58";
|
|
8
|
+
import invariant from "invariant";
|
|
8
9
|
|
|
9
10
|
export const signMessage =
|
|
10
11
|
(signerContext: SignerContext<SolanaSigner>) =>
|
|
@@ -22,15 +23,23 @@ export const signMessage =
|
|
|
22
23
|
);
|
|
23
24
|
}
|
|
24
25
|
|
|
26
|
+
let signedMessage: Buffer | undefined;
|
|
27
|
+
|
|
25
28
|
const result = await signerContext(deviceId, async signer => {
|
|
26
29
|
const { version } = await signer.getAppConfiguration();
|
|
27
30
|
const isLegacy = semver.lt(version, coinConfig.getCoinConfig().legacyOCMSMaxVersion);
|
|
28
31
|
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
);
|
|
32
|
+
signedMessage = toOffChainMessage(message, account.freshAddress, isLegacy);
|
|
33
|
+
|
|
34
|
+
return signer.signMessage(account.freshAddressPath, signedMessage.toString("hex"));
|
|
33
35
|
});
|
|
34
36
|
|
|
35
|
-
|
|
37
|
+
invariant(signedMessage, "signedMessage should exist");
|
|
38
|
+
|
|
39
|
+
const signatureCount = Buffer.from([1]);
|
|
40
|
+
|
|
41
|
+
// https://docs.anza.xyz/proposals/off-chain-message-signing#envelope
|
|
42
|
+
const envelope = Buffer.concat([signatureCount, result.signature, signedMessage]);
|
|
43
|
+
|
|
44
|
+
return { signature: bs58.encode(envelope) };
|
|
36
45
|
};
|