Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 20 additions & 0 deletions src/model/account/Account.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,8 @@ import {NetworkType} from '../blockchain/NetworkType';
import {AggregateTransaction} from '../transaction/AggregateTransaction';
import {CosignatureSignedTransaction} from '../transaction/CosignatureSignedTransaction';
import {CosignatureTransaction} from '../transaction/CosignatureTransaction';
import {EncryptedMessage} from '../transaction/EncryptedMessage';
import {PlainMessage} from '../transaction/PlainMessage';
import {SignedTransaction} from '../transaction/SignedTransaction';
import {Transaction} from '../transaction/Transaction';
import {Address} from './Address';
Expand Down Expand Up @@ -79,7 +81,25 @@ export class Account {
const address = Address.createFromPublicKey(convert.uint8ToHex(keyPair.publicKey), networkType);
return new Account(address, keyPair);
}
/**
* Create a new encrypted Message
* @param message
* @param recipientPublicAccount
* @returns {EncryptedMessage}
*/
public encryptMessage(message: string, recipientPublicAccount: PublicAccount): EncryptedMessage {
return EncryptedMessage.create(message, recipientPublicAccount, this.privateKey);
}

/**
* Decrypts an encrypted message
* @param encryptedMessage
* @param recipientPublicAccount
* @returns {PlainMessage}
*/
public decryptMessage(encryptedMessage: EncryptedMessage, recipientPublicAccount: PublicAccount): PlainMessage {
return EncryptedMessage.decrypt(encryptedMessage, this.privateKey, recipientPublicAccount);
}
/**
* Account public key.
* @return {string}
Expand Down
63 changes: 63 additions & 0 deletions src/model/transaction/EncryptedMessage.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
/*
* Copyright 2019 NEM
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

import {crypto} from 'nem2-library';
import {PublicAccount} from '../account/PublicAccount';
import {Message} from './Message';
import {MessageType} from './MessageType';
import {PlainMessage} from './PlainMessage';

/**
* Encrypted Message model
*/
export class EncryptedMessage extends Message {

public readonly recipientPublicAccount?: PublicAccount;

constructor(payload: string,
recipientPublicAccount?: PublicAccount){
super(MessageType.EncryptedMessage,payload);
this.recipientPublicAccount = recipientPublicAccount;
}

/**
*
* @param message
* @param recipientPublicAccount
* @param privateKey
*/
public static create(message: string, recipientPublicAccount: PublicAccount, privateKey) {
return new EncryptedMessage(crypto.encode(privateKey, recipientPublicAccount.publicKey, message), recipientPublicAccount);
}

/**
*
* @param payload
*/
public static createFromDTO(payload: string): EncryptedMessage {
return new EncryptedMessage(payload);
}

/**
*
* @param encryptMessage
* @param privateKey
* @param recipientPublicAccount
*/
public static decrypt(encryptMessage: EncryptedMessage, privateKey, recipientPublicAccount: PublicAccount): PlainMessage {
return new PlainMessage(Message.decodeHex(crypto.decode(privateKey, recipientPublicAccount.publicKey, encryptMessage.payload)));
}
}
25 changes: 25 additions & 0 deletions src/model/transaction/MessageType.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
/*
* Copyright 2019 NEM
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

/**
* The Message type. Supported supply types are:
* 0: PlainMessage
* 1: EncryptedMessage.
*/
export enum MessageType {
PlainMessage = 0,
EncryptedMessage = 1,
}
3 changes: 2 additions & 1 deletion src/model/transaction/PlainMessage.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
*/

import {Message} from './Message';
import {MessageType} from './MessageType';

/**
* The plain message model defines a plain string. When sending it to the network we transform the payload to hex-string.
Expand All @@ -40,7 +41,7 @@ export class PlainMessage extends Message {
* @param payload
*/
constructor(payload: string) {
super(0, payload);
super(MessageType.PlainMessage, payload);
}

}
Expand Down
58 changes: 58 additions & 0 deletions test/model/transaction/EncryptedMessage.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
/*
* Copyright 2019 NEM
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

import {expect} from 'chai';
import {Account} from '../../../src/model/account/Account';

import {PublicAccount} from '../../../src/model/account/PublicAccount';
import {NetworkType} from '../../../src/model/blockchain/NetworkType';
import {EncryptedMessage} from '../../../src/model/transaction/EncryptedMessage';


describe('EncryptedMessage', () => {

const accountInformation = {
address: 'SCTVW23D2MN5VE4AQ4TZIDZENGNOZXPRPRLIKCF2',
privateKey: '26b64cb10f005e5988a36744ca19e20d835ccc7c105aaa5f3b212da593180930'.toUpperCase(),
publicKey: 'c2f93346e27ce6ad1a9f8f5e3066f8326593a406bdf357acb041e2f9ab402efe'.toUpperCase(),
};
let recipientPublicAccount:PublicAccount;

before(() => {
recipientPublicAccount = PublicAccount.createFromPublicKey(accountInformation.publicKey,NetworkType.MIJIN_TEST);
});

it("should create a encrypted message from a DTO", () => {
const encryptedMessage = EncryptedMessage.createFromDTO("test transaction");
expect(encryptedMessage.payload).to.be.equal("test transaction");
});

it("should return encrypted message dto", () => {
const account = Account.createFromPrivateKey(accountInformation.privateKey,NetworkType.MIJIN_TEST);
const publicAccount = PublicAccount.createFromPublicKey(account.publicKey,NetworkType.MIJIN_TEST);
const encryptedMessage = account.encryptMessage("test transaction", publicAccount);
const plainMessage = account.decryptMessage(encryptedMessage, publicAccount);
expect(plainMessage.payload).to.be.equal("test transaction");
});

it("should create an encrypted message from a DTO and decrypt it", () => {
const account = Account.createFromPrivateKey(accountInformation.privateKey,NetworkType.MIJIN_TEST);
const publicAccount = PublicAccount.createFromPublicKey("0414fe7647ec008e533aac98a4bf1c5fbf1d236c75b81fdadf1f5d1042fdd2ff",NetworkType.MIJIN_TEST);
const encryptMessage = EncryptedMessage.createFromDTO("02bb332c0fdd445455117882b2bec5e49f5713860d6b34650d0f769159d021a27518ea03539af8913231b9f80f600daae9291bb100a6d32e36b52a6c457fea287ca9942a32368618fe1fd0c185dbf834");
const plainMessage = account.decryptMessage(encryptMessage, publicAccount);
expect(plainMessage.payload).to.be.equal("test transaction");
});
});