|
|
@@ -5,7 +5,7 @@ import { Storage } from './storage';
|
|
|
import { IWebClient } from './webclient';
|
|
|
const TextEncoder = util.TextEncoder;
|
|
|
import { UploadItemParameters } from './upload-item-parameters';
|
|
|
-import { encodeHex } from './util';
|
|
|
+import { encodeHex, mergeDeep, uuid } from './util';
|
|
|
import WebClientNode from './webclient-node';
|
|
|
|
|
|
export class BankClient {
|
|
|
@@ -209,8 +209,14 @@ export class BankClient {
|
|
|
return result;
|
|
|
}
|
|
|
|
|
|
- public async appendPrivate(peerAddr: string, topic: string, hash: string) {
|
|
|
- const payload = await this.makePlaintextPayload(hash);
|
|
|
+ public async appendPrivate(peerAddr: string, topic: string, hash: string, replaceHash?: string) {
|
|
|
+ const nonce = await this.getNonce();
|
|
|
+ const payload = await this.makePlaintextPayload(JSON.stringify({
|
|
|
+ _date: new Date().toISOString(),
|
|
|
+ _nonce: nonce,
|
|
|
+ hash,
|
|
|
+ replaceHash
|
|
|
+ }));
|
|
|
const topicURL = this.urlBase + '/bank/private/' + encodeURIComponent(peerAddr) + '/' + encodeURIComponent(topic);
|
|
|
const result = await this.webClient.request({
|
|
|
body: JSON.stringify(payload),
|
|
|
@@ -222,40 +228,58 @@ export class BankClient {
|
|
|
});
|
|
|
}
|
|
|
|
|
|
- public async getOrCreateContact(peerAddr: string, contact: string, type: string) {
|
|
|
- const contactList = await this.retrievePrivate(peerAddr, '📇');
|
|
|
+ public async getOrCreateContact(peerId: string, contactAddr: string) {
|
|
|
+ const contactList = await this.retrievePrivate(peerId, '📇');
|
|
|
const itemList = await this.getItemsForCommaList(contactList);
|
|
|
- const contactHash = await this.getContactHash(contact, type);
|
|
|
// console.log('contact hash for', contact, type, 'is', contactHash);
|
|
|
- const existing = itemList.filter(item => item.contactHash === contactHash)[0];
|
|
|
+ const existing = itemList.filter(item => item.addrs && item.addrs.includes(contactAddr))[0];
|
|
|
if (existing != null) {
|
|
|
return existing;
|
|
|
}
|
|
|
const newItem = {
|
|
|
- contact,
|
|
|
- contactHash,
|
|
|
- type,
|
|
|
+ addrs: [
|
|
|
+ contactAddr
|
|
|
+ ],
|
|
|
+ id: uuid()
|
|
|
};
|
|
|
const newItemHash = await this.uploadSlimJSON(newItem);
|
|
|
- await this.appendPrivate(peerAddr, '📇', newItemHash);
|
|
|
+ await this.appendPrivate(peerId, '📇', newItemHash);
|
|
|
return newItem;
|
|
|
}
|
|
|
|
|
|
- private async getContactHash(contact: string, type: string) {
|
|
|
- const value = type + ':' + contact;
|
|
|
- return await this.uploadSlimText(value);
|
|
|
+ public async getContactById(peerId: string, contactId: string) {
|
|
|
+ const contactList = await this.retrievePrivate(peerId, '📇');
|
|
|
+ const itemList = await this.getItemsForCommaList(contactList);
|
|
|
+ const existing = itemList.filter(item => item.id === contactId)[0];
|
|
|
+ if (!existing) {
|
|
|
+ throw new Error('Cannot find contact with id ' + contactId);
|
|
|
+ }
|
|
|
+ return existing;
|
|
|
+ }
|
|
|
+
|
|
|
+ public async updateContact(peerId: string, contactId: string, newProperties: any) {
|
|
|
+ const existing = await this.getContactById(peerId, contactId);
|
|
|
+ const newProps: any = mergeDeep({}, newProperties);
|
|
|
+ delete newProps.id;
|
|
|
+ const newItem: any = mergeDeep(existing, newProps);
|
|
|
+ delete newItem.hash;
|
|
|
+ const newItemHash = await this.uploadSlimJSON(newItem);
|
|
|
+ await this.appendPrivate(peerId, '📇', newItemHash, existing.hash);
|
|
|
+ return await this.getContactById(peerId, contactId);
|
|
|
}
|
|
|
|
|
|
private async getItemsForCommaList(commaList: string): Promise<any[]> {
|
|
|
- // console.log('commaList', commaList);
|
|
|
const itemHashes = commaList.split(',').filter(x => x.trim() !== '');
|
|
|
- // console.log('itemHashes', itemHashes);
|
|
|
- return await Promise.all(itemHashes.map(itemId => {
|
|
|
+ const items: any[] = await Promise.all(itemHashes.map(itemId => {
|
|
|
return this.webClient.requestJSON({
|
|
|
method: 'get',
|
|
|
url: this.ipfsUrlBase + '/ipfs/' + itemId,
|
|
|
});
|
|
|
}));
|
|
|
+ for (const item of items) {
|
|
|
+ item.hash = itemHashes.shift();
|
|
|
+ }
|
|
|
+ return items;
|
|
|
}
|
|
|
|
|
|
private getPriv(): RsaPrivateKey {
|