refactor RelayManagement

This commit is contained in:
=
2023-03-09 21:51:20 +00:00
parent 3e1771c655
commit 9996e5bbd5
3 changed files with 51 additions and 41 deletions

View File

@@ -1,30 +1,25 @@
import { Event, SimplePool } from 'nostr-tools'; import { Event, SimplePool } from 'nostr-tools';
const pool = new SimplePool(); const pool = new SimplePool();
let currentrelays = [
'wss://relay.damus.io',
'wss://nostr-pub.wellorder.net',
'wss://nostr-relay.wlvs.space',
];
export const requestMyProfileFromRelays = async ( export const requestEventsFromRelays = async (
pubkey:string, pubkeys:string[],
eventProcesser: (event: Event) => void, eventProcesser: (event: Event) => void,
relays?:string[], relays:string[],
kinds: number[],
) => { ) => {
if (relays) currentrelays = relays;
const sub = pool.sub( const sub = pool.sub(
currentrelays, relays,
[{ [{
kinds: [0, 2, 10002, 3], kinds,
authors: [pubkey], authors: pubkeys,
}], }],
); );
return new Promise<void>((r) => { return new Promise<void>((r) => {
sub.on('event', (event:Event) => { sub.on('event', (event:Event) => {
if ( if (
event.pubkey === pubkey pubkeys.indexOf(event.pubkey) !== -1
&& (event.kind === 0 || event.kind === 2 || event.kind === 10002 || event.kind === 3) && kinds.indexOf(event.kind) !== -1
) { ) {
eventProcesser(event); eventProcesser(event);
} }
@@ -35,8 +30,8 @@ export const requestMyProfileFromRelays = async (
}); });
}; };
export const publishEventToRelay = async (event:Event):Promise<boolean> => { export const publishEventToRelay = async (event:Event, relays:string[]):Promise<boolean> => {
const pub = pool.publish(currentrelays, event); const pub = pool.publish(relays, event);
return new Promise((r) => { return new Promise((r) => {
pub.on('ok', () => r(true)); pub.on('ok', () => r(true));
pub.on('failed', () => r(false)); pub.on('failed', () => r(false));

View File

@@ -161,14 +161,14 @@ describe('', () => {
describe('fetchMyProfileEvents', () => { describe('fetchMyProfileEvents', () => {
const fetchCachedProfileEventSpy = jest.spyOn(FetchEvents, 'fetchCachedProfileEvent'); const fetchCachedProfileEventSpy = jest.spyOn(FetchEvents, 'fetchCachedProfileEvent');
const mockEventProcessor = jest.fn(); const mockEventProcessor = jest.fn();
const mockrequestMyProfileFromRelays = jest.spyOn(RelayManagement, 'requestMyProfileFromRelays'); const mockrequestEventsFromRelays = jest.spyOn(RelayManagement, 'requestEventsFromRelays');
const mockupdateLastFetchDate = jest.spyOn(FetchEvents, 'updateLastFetchDate'); const mockupdateLastFetchDate = jest.spyOn(FetchEvents, 'updateLastFetchDate');
const mocklastFetchDate = jest.spyOn(FetchEvents, 'lastFetchDate'); const mocklastFetchDate = jest.spyOn(FetchEvents, 'lastFetchDate');
const mockisUptodate = jest.spyOn(FetchEvents, 'isUptodate'); const mockisUptodate = jest.spyOn(FetchEvents, 'isUptodate');
beforeEach(async () => { beforeEach(async () => {
fetchCachedProfileEventSpy.mockReset(); fetchCachedProfileEventSpy.mockReset();
mockEventProcessor.mockReset(); mockEventProcessor.mockReset();
mockrequestMyProfileFromRelays.mockReset(); mockrequestEventsFromRelays.mockReset();
mockupdateLastFetchDate.mockReset(); mockupdateLastFetchDate.mockReset();
mocklastFetchDate.mockReset(); mocklastFetchDate.mockReset();
mockisUptodate.mockReset(); mockisUptodate.mockReset();
@@ -185,8 +185,8 @@ describe('', () => {
}); });
await fetchMyProfileEvents(SampleEvents.kind0.pubkey, mockEventProcessor); await fetchMyProfileEvents(SampleEvents.kind0.pubkey, mockEventProcessor);
}); });
test('requestMyProfileFromRelays never called', () => { test('requestEventsFromRelays never called', () => {
expect(mockrequestMyProfileFromRelays).toBeCalledTimes(0); expect(mockrequestEventsFromRelays).toBeCalledTimes(0);
}); });
test('updateLastFetchDate never called', () => { test('updateLastFetchDate never called', () => {
expect(mockupdateLastFetchDate).toBeCalledTimes(0); expect(mockupdateLastFetchDate).toBeCalledTimes(0);
@@ -208,7 +208,7 @@ describe('', () => {
describe('and when cached 10002 event is present', () => { describe('and when cached 10002 event is present', () => {
const doBefore = async () => { const doBefore = async () => {
mockisUptodate.mockReturnValue(false); mockisUptodate.mockReturnValue(false);
mockrequestMyProfileFromRelays.mockReset() mockrequestEventsFromRelays.mockReset()
.mockImplementation(async (_pubkey, eventProcessor) => { .mockImplementation(async (_pubkey, eventProcessor) => {
eventProcessor({ ...SampleEvents.kind0 }); eventProcessor({ ...SampleEvents.kind0 });
eventProcessor({ ...SampleEvents.kind3 }); eventProcessor({ ...SampleEvents.kind3 });
@@ -223,7 +223,7 @@ describe('', () => {
], ],
}); });
await doBefore(); await doBefore();
expect(mockrequestMyProfileFromRelays).toBeCalledWith( expect(mockrequestEventsFromRelays).toBeCalledWith(
expect.anything(), expect.anything(),
expect.anything(), expect.anything(),
[ [
@@ -232,6 +232,7 @@ describe('', () => {
'wss://nostr-pub.wellorder.net', 'wss://nostr-pub.wellorder.net',
'wss://nostr.mutinywallet.com', 'wss://nostr.mutinywallet.com',
], ],
expect.anything(),
); );
}); });
test('2 write relays function called with custom relays and 1 default relays + blaster', async () => { test('2 write relays function called with custom relays and 1 default relays + blaster', async () => {
@@ -243,7 +244,7 @@ describe('', () => {
], ],
}); });
await doBefore(); await doBefore();
expect(mockrequestMyProfileFromRelays).toBeCalledWith( expect(mockrequestEventsFromRelays).toBeCalledWith(
expect.anything(), expect.anything(),
expect.anything(), expect.anything(),
[ [
@@ -252,6 +253,7 @@ describe('', () => {
'wss://relay.damus.io', 'wss://relay.damus.io',
'wss://nostr.mutinywallet.com', 'wss://nostr.mutinywallet.com',
], ],
expect.anything(),
); );
}); });
test('2 write relays including first defauly relay. function called with custom relays and 1 different default relays + blaster', async () => { test('2 write relays including first defauly relay. function called with custom relays and 1 different default relays + blaster', async () => {
@@ -263,7 +265,7 @@ describe('', () => {
], ],
}); });
await doBefore(); await doBefore();
expect(mockrequestMyProfileFromRelays).toBeCalledWith( expect(mockrequestEventsFromRelays).toBeCalledWith(
expect.anything(), expect.anything(),
expect.anything(), expect.anything(),
[ [
@@ -272,6 +274,7 @@ describe('', () => {
'wss://nostr-pub.wellorder.net', 'wss://nostr-pub.wellorder.net',
'wss://nostr.mutinywallet.com', 'wss://nostr.mutinywallet.com',
], ],
expect.anything(),
); );
}); });
test('with 4 write relays function called with all custom relays + blaster', async () => { test('with 4 write relays function called with all custom relays + blaster', async () => {
@@ -285,7 +288,7 @@ describe('', () => {
], ],
}); });
await doBefore(); await doBefore();
expect(mockrequestMyProfileFromRelays).toBeCalledWith( expect(mockrequestEventsFromRelays).toBeCalledWith(
expect.anything(), expect.anything(),
expect.anything(), expect.anything(),
[ [
@@ -295,6 +298,7 @@ describe('', () => {
'wss://alicerelay.example3.com', 'wss://alicerelay.example3.com',
'wss://nostr.mutinywallet.com', 'wss://nostr.mutinywallet.com',
], ],
expect.anything(),
); );
}); });
test('custom read relays ignored', async () => { test('custom read relays ignored', async () => {
@@ -308,7 +312,7 @@ describe('', () => {
], ],
}); });
await doBefore(); await doBefore();
expect(mockrequestMyProfileFromRelays).toBeCalledWith( expect(mockrequestEventsFromRelays).toBeCalledWith(
expect.anything(), expect.anything(),
expect.anything(), expect.anything(),
[ [
@@ -317,6 +321,7 @@ describe('', () => {
'wss://expensive-relay.example2.com', 'wss://expensive-relay.example2.com',
'wss://nostr.mutinywallet.com', 'wss://nostr.mutinywallet.com',
], ],
expect.anything(),
); );
}); });
}); });
@@ -324,7 +329,7 @@ describe('', () => {
const mockstoreMyProfileEvent = jest.spyOn(FetchEvents, 'storeMyProfileEvent'); const mockstoreMyProfileEvent = jest.spyOn(FetchEvents, 'storeMyProfileEvent');
beforeEach(async () => { beforeEach(async () => {
mockisUptodate.mockReturnValue(false); mockisUptodate.mockReturnValue(false);
mockrequestMyProfileFromRelays.mockReset() mockrequestEventsFromRelays.mockReset()
.mockImplementation(async (_pubkey, eventProcessor) => { .mockImplementation(async (_pubkey, eventProcessor) => {
eventProcessor({ ...SampleEvents.kind0 }); eventProcessor({ ...SampleEvents.kind0 });
eventProcessor({ ...SampleEvents.kind3 }); eventProcessor({ ...SampleEvents.kind3 });
@@ -337,18 +342,19 @@ describe('', () => {
test('fetchCachedProfileEvent only to be called once to getRelays', () => { test('fetchCachedProfileEvent only to be called once to getRelays', () => {
expect(fetchCachedProfileEventSpy).toBeCalledTimes(1); expect(fetchCachedProfileEventSpy).toBeCalledTimes(1);
}); });
test('requestMyProfileFromRelays called', () => { test('requestEventsFromRelays called', () => {
expect(mockrequestMyProfileFromRelays).toBeCalledTimes(1); expect(mockrequestEventsFromRelays).toBeCalledTimes(1);
}); });
test('mockrequestMyProfileFromRelays called with correct pubkey', () => { test('mockrequestEventsFromRelays called with correct pubkey', () => {
expect(mockrequestMyProfileFromRelays).toBeCalledWith( expect(mockrequestEventsFromRelays).toBeCalledWith(
SampleEvents.kind0.pubkey, [SampleEvents.kind0.pubkey],
expect.anything(),
expect.anything(), expect.anything(),
expect.anything(), expect.anything(),
); );
}); });
test('mockrequestMyProfileFromRelays called with correct default relays', () => { test('mockrequestEventsFromRelays called with correct default relays', () => {
expect(mockrequestMyProfileFromRelays).toBeCalledWith( expect(mockrequestEventsFromRelays).toBeCalledWith(
expect.anything(), expect.anything(),
expect.anything(), expect.anything(),
[ [
@@ -357,17 +363,26 @@ describe('', () => {
'wss://nostr-relay.wlvs.space', 'wss://nostr-relay.wlvs.space',
'wss://nostr.mutinywallet.com', 'wss://nostr.mutinywallet.com',
], ],
expect.anything(),
); );
}); });
test('eventProcessor called with events passed through by requestMyProfileFromRelays\'s event processor', async () => { test('mockrequestEventsFromRelays called with correct kind 0, 2 10002, 3', () => {
expect(mockrequestEventsFromRelays).toBeCalledWith(
expect.anything(),
expect.anything(),
expect.anything(),
[0, 2, 10002, 3],
);
});
test('eventProcessor called with events passed through by requestEventsFromRelays\'s event processor', async () => {
expect(mockEventProcessor).toBeCalledWith({ ...SampleEvents.kind0 }); expect(mockEventProcessor).toBeCalledWith({ ...SampleEvents.kind0 });
expect(mockEventProcessor).toBeCalledWith({ ...SampleEvents.kind3 }); expect(mockEventProcessor).toBeCalledWith({ ...SampleEvents.kind3 });
}); });
test('storeMyProfileEvent called with events passed through by requestMyProfileFromRelays\'s event processor', async () => { test('storeMyProfileEvent called with events passed through by requestEventsFromRelays\'s event processor', async () => {
expect(mockstoreMyProfileEvent).toBeCalledWith({ ...SampleEvents.kind0 }); expect(mockstoreMyProfileEvent).toBeCalledWith({ ...SampleEvents.kind0 });
expect(mockstoreMyProfileEvent).toBeCalledWith({ ...SampleEvents.kind3 }); expect(mockstoreMyProfileEvent).toBeCalledWith({ ...SampleEvents.kind3 });
}); });
test('eventProcessor not called when profile event kind isn\'t found by requestMyProfileFromRelays', async () => { test('eventProcessor not called when profile event kind isn\'t found by requestEventsFromRelays', async () => {
expect(mockEventProcessor).toBeCalledTimes(2); expect(mockEventProcessor).toBeCalledTimes(2);
}); });
}); });

View File

@@ -1,6 +1,6 @@
import { Event, UnsignedEvent } from 'nostr-tools'; import { Event, UnsignedEvent } from 'nostr-tools';
import { localStorageGetItem, localStorageSetItem } from './LocalStorage'; import { localStorageGetItem, localStorageSetItem } from './LocalStorage';
import { publishEventToRelay, requestMyProfileFromRelays } from './RelayManagement'; import { publishEventToRelay, requestEventsFromRelays } from './RelayManagement';
export const lastFetchDate = ():number | null => { export const lastFetchDate = ():number | null => {
const d = localStorageGetItem('my-profile-last-fetch-date'); const d = localStorageGetItem('my-profile-last-fetch-date');
@@ -114,10 +114,10 @@ export const fetchMyProfileEvents = async (
): Promise<void> => { ): Promise<void> => {
// get events from relays, store them and run profileEventProcesser // get events from relays, store them and run profileEventProcesser
if (!isUptodate()) { if (!isUptodate()) {
await requestMyProfileFromRelays(pubkey, (event: Event) => { await requestEventsFromRelays([pubkey], (event: Event) => {
storeMyProfileEvent(event); storeMyProfileEvent(event);
profileEventProcesser(event); profileEventProcesser(event);
}, getRelays()); }, getRelays(), [0, 2, 10002, 3]);
// update last-fetch-from-relays date // update last-fetch-from-relays date
updateLastFetchDate(); updateLastFetchDate();
} else { } else {
@@ -130,7 +130,7 @@ export const fetchMyProfileEvents = async (
}; };
export const publishEvent = async (event:Event):Promise<boolean> => { export const publishEvent = async (event:Event):Promise<boolean> => {
const r = await publishEventToRelay(event); const r = await publishEventToRelay(event, getRelays());
if (r) storeMyProfileEvent(event); if (r) storeMyProfileEvent(event);
return r; return r;
}; };