mirror of
https://github.com/BlowaterNostr/blowater.git
synced 2024-10-18 15:43:20 +00:00
maintain all user information in a stateful class
This commit is contained in:
parent
13eba08177
commit
934818e7a9
27
UI/app.tsx
27
UI/app.tsx
@ -14,10 +14,9 @@ import { MessagePanel } from "./message-panel.tsx";
|
|||||||
import { Setting } from "./setting.tsx";
|
import { Setting } from "./setting.tsx";
|
||||||
import { Database_Contextual_View } from "../database.ts";
|
import { Database_Contextual_View } from "../database.ts";
|
||||||
|
|
||||||
import { getAllUsersInformation, ProfilesSyncer, UserInfo } from "./contact-list.ts";
|
import { AllUsersInformation, ProfilesSyncer, UserInfo } from "./contact-list.ts";
|
||||||
|
|
||||||
import { new_DM_EditorModel } from "./editor.tsx";
|
import { new_DM_EditorModel } from "./editor.tsx";
|
||||||
import { Channel } from "https://raw.githubusercontent.com/BlowaterNostr/csp/master/csp.ts";
|
|
||||||
import { initialModel, Model } from "./app_model.ts";
|
import { initialModel, Model } from "./app_model.ts";
|
||||||
import {
|
import {
|
||||||
AppEventBus,
|
AppEventBus,
|
||||||
@ -156,6 +155,7 @@ async function initProfileSyncer(
|
|||||||
export class App {
|
export class App {
|
||||||
profileSyncer!: ProfilesSyncer;
|
profileSyncer!: ProfilesSyncer;
|
||||||
eventSyncer: EventSyncer;
|
eventSyncer: EventSyncer;
|
||||||
|
public readonly allUsersInfo: AllUsersInformation;
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
public readonly database: Database_Contextual_View,
|
public readonly database: Database_Contextual_View,
|
||||||
@ -166,10 +166,11 @@ export class App {
|
|||||||
public readonly relayPool: ConnectionPool,
|
public readonly relayPool: ConnectionPool,
|
||||||
) {
|
) {
|
||||||
this.eventSyncer = new EventSyncer(this.relayPool, this.database);
|
this.eventSyncer = new EventSyncer(this.relayPool, this.database);
|
||||||
|
this.allUsersInfo = new AllUsersInformation(myAccountContext);
|
||||||
}
|
}
|
||||||
|
|
||||||
initApp = async (accountContext: NostrAccountContext) => {
|
initApp = async (accountContext: NostrAccountContext) => {
|
||||||
const events = this.database.filterEvents((e) => e.kind == NostrKind.TEXT_NOTE);
|
// const events = this.database.filterEvents((e) => e.kind == NostrKind.TEXT_NOTE);
|
||||||
|
|
||||||
console.log("App.initApp");
|
console.log("App.initApp");
|
||||||
const profilesSyncer = await initProfileSyncer(this.relayPool, accountContext, this.database);
|
const profilesSyncer = await initProfileSyncer(this.relayPool, accountContext, this.database);
|
||||||
@ -179,15 +180,16 @@ export class App {
|
|||||||
|
|
||||||
this.profileSyncer = profilesSyncer;
|
this.profileSyncer = profilesSyncer;
|
||||||
|
|
||||||
this.model.allUsersInfo = getAllUsersInformation(this.database, this.myAccountContext);
|
this.allUsersInfo.addEvents(this.database.events);
|
||||||
console.log("App allUsersInfo");
|
console.log("App allUsersInfo");
|
||||||
this.model.social.threads = getSocialPosts(this.database, this.model.allUsersInfo);
|
this.model.social.threads = getSocialPosts(this.database, this.allUsersInfo.userInfos);
|
||||||
|
|
||||||
/* my profile */
|
/* my profile */
|
||||||
this.model.myProfile = this.model.allUsersInfo.get(accountContext.publicKey.hex)?.profile?.profile;
|
this.model.myProfile = this.allUsersInfo.userInfos.get(accountContext.publicKey.hex)?.profile
|
||||||
|
?.profile;
|
||||||
|
|
||||||
/* contacts */
|
/* contacts */
|
||||||
for (const contact of this.model.allUsersInfo.values()) {
|
for (const contact of this.allUsersInfo.userInfos.values()) {
|
||||||
const editor = this.model.editors.get(contact.pubkey.hex);
|
const editor = this.model.editors.get(contact.pubkey.hex);
|
||||||
if (editor == null) {
|
if (editor == null) {
|
||||||
const pubkey = PublicKey.FromHex(contact.pubkey.hex);
|
const pubkey = PublicKey.FromHex(contact.pubkey.hex);
|
||||||
@ -206,7 +208,7 @@ export class App {
|
|||||||
}
|
}
|
||||||
|
|
||||||
await profilesSyncer.add(
|
await profilesSyncer.add(
|
||||||
...Array.from(this.model.allUsersInfo.keys()),
|
...Array.from(this.allUsersInfo.userInfos.keys()),
|
||||||
);
|
);
|
||||||
console.log("user set", profilesSyncer.userSet);
|
console.log("user set", profilesSyncer.userSet);
|
||||||
|
|
||||||
@ -221,6 +223,7 @@ export class App {
|
|||||||
this.profileSyncer,
|
this.profileSyncer,
|
||||||
this.lamport,
|
this.lamport,
|
||||||
this.eventBus,
|
this.eventBus,
|
||||||
|
this.allUsersInfo,
|
||||||
)
|
)
|
||||||
) {
|
) {
|
||||||
render(<AppComponent model={this.model} eventBus={this.eventBus} />, document.body);
|
render(<AppComponent model={this.model} eventBus={this.eventBus} />, document.body);
|
||||||
@ -261,7 +264,11 @@ export function AppComponent(props: {
|
|||||||
if (model.navigationModel.activeNav == "Social") {
|
if (model.navigationModel.activeNav == "Social") {
|
||||||
let focusedContentGetter = () => {
|
let focusedContentGetter = () => {
|
||||||
// console.log("AppComponent:getFocusedContent before", Date.now() - t);
|
// console.log("AppComponent:getFocusedContent before", Date.now() - t);
|
||||||
let _ = getFocusedContent(model.social.focusedContent, model.allUsersInfo, model.social.threads);
|
let _ = getFocusedContent(
|
||||||
|
model.social.focusedContent,
|
||||||
|
app.allUsersInfo.userInfos,
|
||||||
|
model.social.threads,
|
||||||
|
);
|
||||||
// console.log("AppComponent:getFocusedContent", Date.now() - t);
|
// console.log("AppComponent:getFocusedContent", Date.now() - t);
|
||||||
if (_?.type === "MessageThread") {
|
if (_?.type === "MessageThread") {
|
||||||
let editor = model.social.replyEditors.get(_.data.root.event.id);
|
let editor = model.social.replyEditors.get(_.data.root.event.id);
|
||||||
@ -354,7 +361,7 @@ export function AppComponent(props: {
|
|||||||
myAccountContext: myAccountCtx,
|
myAccountContext: myAccountCtx,
|
||||||
db: app.database,
|
db: app.database,
|
||||||
pool: app.relayPool,
|
pool: app.relayPool,
|
||||||
allUserInfo: model.allUsersInfo,
|
allUserInfo: app.allUsersInfo.userInfos,
|
||||||
profilesSyncer: app.profileSyncer,
|
profilesSyncer: app.profileSyncer,
|
||||||
eventSyncer: app.eventSyncer,
|
eventSyncer: app.eventSyncer,
|
||||||
})}
|
})}
|
||||||
|
@ -24,7 +24,7 @@ export type Model = {
|
|||||||
key: string;
|
key: string;
|
||||||
value: string;
|
value: string;
|
||||||
};
|
};
|
||||||
allUsersInfo: Map<string, UserInfo>;
|
// allUsersInfo: Map<string, UserInfo>;
|
||||||
|
|
||||||
// social
|
// social
|
||||||
social: {
|
social: {
|
||||||
@ -57,7 +57,7 @@ export function initialModel(): Model {
|
|||||||
hasNewMessages: new Set(),
|
hasNewMessages: new Set(),
|
||||||
currentSelectedContact: undefined,
|
currentSelectedContact: undefined,
|
||||||
},
|
},
|
||||||
allUsersInfo: new Map(),
|
// allUsersInfo: new Map(),
|
||||||
editors: editors,
|
editors: editors,
|
||||||
newProfileField: {
|
newProfileField: {
|
||||||
key: "",
|
key: "",
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
import { getProfileEvent, getProfilesByName, saveProfile } from "../features/profile.ts";
|
import { getProfileEvent, getProfilesByName, saveProfile } from "../features/profile.ts";
|
||||||
|
|
||||||
import { App } from "./app.tsx";
|
import { App } from "./app.tsx";
|
||||||
import { getAllUsersInformation, getGroupOf, ProfilesSyncer, UserInfo } from "./contact-list.ts";
|
import { AllUsersInformation, getGroupOf, ProfilesSyncer, UserInfo } from "./contact-list.ts";
|
||||||
|
|
||||||
import * as csp from "https://raw.githubusercontent.com/BlowaterNostr/csp/master/csp.ts";
|
import * as csp from "https://raw.githubusercontent.com/BlowaterNostr/csp/master/csp.ts";
|
||||||
import { Database_Contextual_View } from "../database.ts";
|
import { Database_Contextual_View } from "../database.ts";
|
||||||
@ -27,7 +27,15 @@ import {
|
|||||||
} from "https://raw.githubusercontent.com/BlowaterNostr/nostr.ts/main/nostr.ts";
|
} from "https://raw.githubusercontent.com/BlowaterNostr/nostr.ts/main/nostr.ts";
|
||||||
import { ConnectionPool } from "https://raw.githubusercontent.com/BlowaterNostr/nostr.ts/main/relay.ts";
|
import { ConnectionPool } from "https://raw.githubusercontent.com/BlowaterNostr/nostr.ts/main/relay.ts";
|
||||||
import { SignInEvent, signInWithExtension, signInWithPrivateKey } from "./signIn.tsx";
|
import { SignInEvent, signInWithExtension, signInWithPrivateKey } from "./signIn.tsx";
|
||||||
import { computeThreads, getTags, PinContact, UnpinContact } from "../nostr.ts";
|
import {
|
||||||
|
computeThreads,
|
||||||
|
Decrypted_Nostr_Event,
|
||||||
|
getTags,
|
||||||
|
PinContact,
|
||||||
|
PlainText_Nostr_Event,
|
||||||
|
Profile_Nostr_Event,
|
||||||
|
UnpinContact,
|
||||||
|
} from "../nostr.ts";
|
||||||
import { MessageThread } from "./dm.tsx";
|
import { MessageThread } from "./dm.tsx";
|
||||||
import { DexieDatabase } from "./dexie-db.ts";
|
import { DexieDatabase } from "./dexie-db.ts";
|
||||||
import { getSocialPosts } from "../features/social.ts";
|
import { getSocialPosts } from "../features/social.ts";
|
||||||
@ -192,7 +200,7 @@ export async function* UI_Interaction_Update(
|
|||||||
};
|
};
|
||||||
const group = getGroupOf(
|
const group = getGroupOf(
|
||||||
event.pubkey,
|
event.pubkey,
|
||||||
model.allUsersInfo,
|
model.app.allUsersInfo.userInfos,
|
||||||
);
|
);
|
||||||
model.dm.selectedContactGroup = group;
|
model.dm.selectedContactGroup = group;
|
||||||
updateConversation(model.app.model, event.pubkey);
|
updateConversation(model.app.model, event.pubkey);
|
||||||
@ -440,12 +448,13 @@ export async function* Database_Update(
|
|||||||
profileSyncer: ProfilesSyncer,
|
profileSyncer: ProfilesSyncer,
|
||||||
lamport: LamportTime,
|
lamport: LamportTime,
|
||||||
eventEmitter: EventEmitter<SelectProfile>,
|
eventEmitter: EventEmitter<SelectProfile>,
|
||||||
|
allUserInfo: AllUsersInformation,
|
||||||
) {
|
) {
|
||||||
const changes = database.onChange((_) => true);
|
const changes = database.onChange((_) => true);
|
||||||
while (true) {
|
while (true) {
|
||||||
await csp.sleep(333);
|
await csp.sleep(333);
|
||||||
await changes.ready();
|
await changes.ready();
|
||||||
const changes_events: NostrEvent[] = [];
|
const changes_events: (PlainText_Nostr_Event | Decrypted_Nostr_Event | Profile_Nostr_Event)[] = [];
|
||||||
while (true) {
|
while (true) {
|
||||||
if (!changes.isReadyToPop()) {
|
if (!changes.isReadyToPop()) {
|
||||||
break;
|
break;
|
||||||
@ -460,7 +469,7 @@ export async function* Database_Update(
|
|||||||
|
|
||||||
let hasKind_1 = false;
|
let hasKind_1 = false;
|
||||||
for (let e of changes_events) {
|
for (let e of changes_events) {
|
||||||
model.allUsersInfo = getAllUsersInformation(database, ctx);
|
allUserInfo.addEvents([e]);
|
||||||
const t = getTags(e).lamport_timestamp;
|
const t = getTags(e).lamport_timestamp;
|
||||||
if (t) {
|
if (t) {
|
||||||
lamport.set(t);
|
lamport.set(t);
|
||||||
@ -470,7 +479,7 @@ export async function* Database_Update(
|
|||||||
await profileSyncer.add(key.hex);
|
await profileSyncer.add(key.hex);
|
||||||
}
|
}
|
||||||
if (e.kind == NostrKind.META_DATA || e.kind == NostrKind.DIRECT_MESSAGE) {
|
if (e.kind == NostrKind.META_DATA || e.kind == NostrKind.DIRECT_MESSAGE) {
|
||||||
for (const contact of model.allUsersInfo.values()) {
|
for (const contact of allUserInfo.userInfos.values()) {
|
||||||
const editor = model.editors.get(contact.pubkey.hex);
|
const editor = model.editors.get(contact.pubkey.hex);
|
||||||
if (editor == null) { // a stranger sends a message
|
if (editor == null) { // a stranger sends a message
|
||||||
const pubkey = PublicKey.FromHex(contact.pubkey.hex);
|
const pubkey = PublicKey.FromHex(contact.pubkey.hex);
|
||||||
@ -547,7 +556,7 @@ export async function* Database_Update(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (hasKind_1) {
|
if (hasKind_1) {
|
||||||
model.social.threads = getSocialPosts(database, model.allUsersInfo);
|
model.social.threads = getSocialPosts(database, allUserInfo.userInfos);
|
||||||
}
|
}
|
||||||
yield model;
|
yield model;
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
import { Database_Contextual_View } from "../database.ts";
|
import { Database_Contextual_View } from "../database.ts";
|
||||||
import { ProfileFromNostrEvent, profilesStream } from "../features/profile.ts";
|
import { profilesStream } from "../features/profile.ts";
|
||||||
|
|
||||||
import { Channel } from "https://raw.githubusercontent.com/BlowaterNostr/csp/master/csp.ts";
|
import { Channel } from "https://raw.githubusercontent.com/BlowaterNostr/csp/master/csp.ts";
|
||||||
import { ContactGroup } from "./contact-list.tsx";
|
import { ContactGroup } from "./contact-list.tsx";
|
||||||
@ -13,8 +13,13 @@ import {
|
|||||||
ConnectionPool,
|
ConnectionPool,
|
||||||
newSubID,
|
newSubID,
|
||||||
} from "https://raw.githubusercontent.com/BlowaterNostr/nostr.ts/main/relay.ts";
|
} from "https://raw.githubusercontent.com/BlowaterNostr/nostr.ts/main/relay.ts";
|
||||||
import { CustomAppData, getTags, Profile_Nostr_Event } from "../nostr.ts";
|
import {
|
||||||
import { assertEquals } from "https://deno.land/std@0.176.0/testing/asserts.ts";
|
CustomAppData,
|
||||||
|
Decrypted_Nostr_Event,
|
||||||
|
getTags,
|
||||||
|
PlainText_Nostr_Event,
|
||||||
|
Profile_Nostr_Event,
|
||||||
|
} from "../nostr.ts";
|
||||||
|
|
||||||
export interface UserInfo {
|
export interface UserInfo {
|
||||||
pubkey: PublicKey;
|
pubkey: PublicKey;
|
||||||
@ -97,18 +102,18 @@ function socialPostsStream(pubkeys: Iterable<string>, pool: ConnectionPool) {
|
|||||||
return chan;
|
return chan;
|
||||||
}
|
}
|
||||||
|
|
||||||
export function getAllUsersInformation(
|
export class AllUsersInformation {
|
||||||
database: Database_Contextual_View,
|
readonly userInfos = new Map<string, UserInfo>();
|
||||||
ctx: NostrAccountContext,
|
|
||||||
): Map<string, UserInfo> {
|
constructor(public readonly ctx: NostrAccountContext) {}
|
||||||
const t = Date.now();
|
|
||||||
const res = new Map<string, UserInfo>();
|
addEvents(events: (Profile_Nostr_Event | PlainText_Nostr_Event | Decrypted_Nostr_Event)[]) {
|
||||||
{
|
// const t = Date.now();
|
||||||
for (const event of database.filterEvents((_) => true)) {
|
for (const event of events) {
|
||||||
switch (event.kind) {
|
switch (event.kind) {
|
||||||
case NostrKind.META_DATA:
|
case NostrKind.META_DATA:
|
||||||
{
|
{
|
||||||
const userInfo = res.get(event.pubkey);
|
const userInfo = this.userInfos.get(event.pubkey);
|
||||||
const profileEvent = event;
|
const profileEvent = event;
|
||||||
if (userInfo) {
|
if (userInfo) {
|
||||||
if (userInfo.profile) {
|
if (userInfo.profile) {
|
||||||
@ -126,7 +131,7 @@ export function getAllUsersInformation(
|
|||||||
newestEventSendByMe: undefined,
|
newestEventSendByMe: undefined,
|
||||||
profile: profileEvent,
|
profile: profileEvent,
|
||||||
};
|
};
|
||||||
res.set(event.pubkey, newUserInfo);
|
this.userInfos.set(event.pubkey, newUserInfo);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
@ -139,19 +144,19 @@ export function getAllUsersInformation(
|
|||||||
case NostrKind.DIRECT_MESSAGE:
|
case NostrKind.DIRECT_MESSAGE:
|
||||||
{
|
{
|
||||||
let whoAm_I_TalkingTo = "";
|
let whoAm_I_TalkingTo = "";
|
||||||
if (event.pubkey == ctx.publicKey.hex) {
|
if (event.pubkey == this.ctx.publicKey.hex) {
|
||||||
// I am the sender
|
// I am the sender
|
||||||
whoAm_I_TalkingTo = getTags(event).p[0];
|
whoAm_I_TalkingTo = getTags(event).p[0];
|
||||||
} else if (getTags(event).p[0] == ctx.publicKey.hex) {
|
} else if (getTags(event).p[0] == this.ctx.publicKey.hex) {
|
||||||
// I am the receiver
|
// I am the receiver
|
||||||
whoAm_I_TalkingTo = event.pubkey;
|
whoAm_I_TalkingTo = event.pubkey;
|
||||||
} else {
|
} else {
|
||||||
// I am neither. Possible because other user has used this device before
|
// I am neither. Possible because other user has used this device before
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
const userInfo = res.get(whoAm_I_TalkingTo);
|
const userInfo = this.userInfos.get(whoAm_I_TalkingTo);
|
||||||
if (userInfo) {
|
if (userInfo) {
|
||||||
if (whoAm_I_TalkingTo == ctx.publicKey.hex) {
|
if (whoAm_I_TalkingTo == this.ctx.publicKey.hex) {
|
||||||
// talking to myself
|
// talking to myself
|
||||||
if (userInfo.newestEventSendByMe) {
|
if (userInfo.newestEventSendByMe) {
|
||||||
if (event.created_at > userInfo.newestEventSendByMe?.created_at) {
|
if (event.created_at > userInfo.newestEventSendByMe?.created_at) {
|
||||||
@ -163,7 +168,7 @@ export function getAllUsersInformation(
|
|||||||
userInfo.newestEventReceivedByMe = event;
|
userInfo.newestEventReceivedByMe = event;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if (ctx.publicKey.hex == event.pubkey) {
|
if (this.ctx.publicKey.hex == event.pubkey) {
|
||||||
// I am the sender
|
// I am the sender
|
||||||
if (userInfo.newestEventSendByMe) {
|
if (userInfo.newestEventSendByMe) {
|
||||||
if (event.created_at > userInfo.newestEventSendByMe.created_at) {
|
if (event.created_at > userInfo.newestEventSendByMe.created_at) {
|
||||||
@ -191,12 +196,12 @@ export function getAllUsersInformation(
|
|||||||
newestEventSendByMe: undefined,
|
newestEventSendByMe: undefined,
|
||||||
profile: undefined,
|
profile: undefined,
|
||||||
};
|
};
|
||||||
if (whoAm_I_TalkingTo == ctx.publicKey.hex) {
|
if (whoAm_I_TalkingTo == this.ctx.publicKey.hex) {
|
||||||
// talking to myself
|
// talking to myself
|
||||||
newUserInfo.newestEventSendByMe = event;
|
newUserInfo.newestEventSendByMe = event;
|
||||||
newUserInfo.newestEventReceivedByMe = event;
|
newUserInfo.newestEventReceivedByMe = event;
|
||||||
} else {
|
} else {
|
||||||
if (ctx.publicKey.hex == event.pubkey) {
|
if (this.ctx.publicKey.hex == event.pubkey) {
|
||||||
// I am the sender
|
// I am the sender
|
||||||
newUserInfo.newestEventSendByMe = event;
|
newUserInfo.newestEventSendByMe = event;
|
||||||
} else {
|
} else {
|
||||||
@ -204,7 +209,7 @@ export function getAllUsersInformation(
|
|||||||
newUserInfo.newestEventReceivedByMe = event;
|
newUserInfo.newestEventReceivedByMe = event;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
res.set(whoAm_I_TalkingTo, newUserInfo);
|
this.userInfos.set(whoAm_I_TalkingTo, newUserInfo);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
@ -216,7 +221,7 @@ export function getAllUsersInformation(
|
|||||||
}
|
}
|
||||||
const obj: CustomAppData = JSON.parse(event.decryptedContent);
|
const obj: CustomAppData = JSON.parse(event.decryptedContent);
|
||||||
if (obj.type == "PinContact" || obj.type == "UnpinContact") {
|
if (obj.type == "PinContact" || obj.type == "UnpinContact") {
|
||||||
const userInfo = res.get(obj.pubkey);
|
const userInfo = this.userInfos.get(obj.pubkey);
|
||||||
if (userInfo) {
|
if (userInfo) {
|
||||||
if (userInfo.pinEvent) {
|
if (userInfo.pinEvent) {
|
||||||
if (event.created_at > userInfo.pinEvent.created_at) {
|
if (event.created_at > userInfo.pinEvent.created_at) {
|
||||||
@ -232,7 +237,7 @@ export function getAllUsersInformation(
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
res.set(obj.pubkey, {
|
this.userInfos.set(obj.pubkey, {
|
||||||
pubkey: PublicKey.FromHex(obj.pubkey) as PublicKey, // todo: could throw
|
pubkey: PublicKey.FromHex(obj.pubkey) as PublicKey, // todo: could throw
|
||||||
pinEvent: {
|
pinEvent: {
|
||||||
content: obj,
|
content: obj,
|
||||||
@ -247,17 +252,8 @@ export function getAllUsersInformation(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// console.log("AllUsersInformation:addEvents", Date.now() - t);
|
||||||
}
|
}
|
||||||
// todo: should write a unit test for it instead of runtime assertion
|
|
||||||
for (const [pubkey, userInfo] of res) {
|
|
||||||
assertEquals(pubkey, userInfo.pubkey.hex);
|
|
||||||
if (userInfo.profile) {
|
|
||||||
assertEquals(pubkey, userInfo.profile.pubkey);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
console.log("getAllUsersInformation", Date.now() - t);
|
|
||||||
return res;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export const sortUserInfo = (a: UserInfo, b: UserInfo) => {
|
export const sortUserInfo = (a: UserInfo, b: UserInfo) => {
|
||||||
|
@ -332,9 +332,11 @@ export class Database_Contextual_View {
|
|||||||
//////////////////
|
//////////////////
|
||||||
// On DB Change //
|
// On DB Change //
|
||||||
//////////////////
|
//////////////////
|
||||||
onChange(filter: (e: NostrEvent) => boolean) {
|
onChange(filter: (e: PlainText_Nostr_Event | Decrypted_Nostr_Event | Profile_Nostr_Event) => boolean) {
|
||||||
const c = this.caster.copy();
|
const c = this.caster.copy();
|
||||||
const res = csp.chan<NostrEvent>(buffer_size);
|
const res = csp.chan<PlainText_Nostr_Event | Decrypted_Nostr_Event | Profile_Nostr_Event>(
|
||||||
|
buffer_size,
|
||||||
|
);
|
||||||
(async () => {
|
(async () => {
|
||||||
for await (const newE of c) {
|
for await (const newE of c) {
|
||||||
if (filter(newE)) {
|
if (filter(newE)) {
|
||||||
|
Loading…
Reference in New Issue
Block a user