Skip to content

Commit

Permalink
client-web: cleanup components, improve queue and relay list
Browse files Browse the repository at this point in the history
  • Loading branch information
franzos committed Aug 21, 2023
1 parent acc632e commit fbfd9cf
Show file tree
Hide file tree
Showing 21 changed files with 462 additions and 255 deletions.
45 changes: 45 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,8 @@ Nostr web client built with React.

Initial support for `nos2x` and any other extention following NIP-07 is available.

A new, live version builds from master on every commit: [https://franzos.github.io/nostr-ts/](https://franzos.github.io/nostr-ts/).

![Preview](./client-web/preview.png)

## Highlights
Expand Down Expand Up @@ -234,6 +236,49 @@ supportedNips [
Event a04308c18a5f73b97be1f66fddba1741dd8dcf8a057701a2b4f1713d557ae384 not published to wss://nostr.wine because not all needed NIPS are supported.
```

- [ ] NIP-13 [Proof of work](https://github.com/nostr-protocol/nips/blob/master/13.md)

```js
const difficulty = 28
const ev = NewShortTextNote({ text: "Let's have a discussion about Bitcoin!" });
ev.pubkey = keypair.pub
ev.proofOfWork(difficulty);
ev.sign()
```

If you need anything above ~20 bits and work in the browser, there's a helper function for web worker (`proofOfWork(event, bits)`):

```js
// pow-worker.ts
import { proofOfWork } from "@nostr-ts/common";

self.onmessage = function (e) {
const data = e.data;
const result = proofOfWork(data.event, data.bits);
self.postMessage({ result });
};

// client.ts
return new Promise((resolve, reject) => {
const worker = new Worker(new URL("./pow-worker.ts", import.meta.url), {
type: "module",
});

// Setup an event listener to receive results from the worker
worker.onmessage = function (e) {
resolve(e.data.result);
// Terminate the worker after receiving the result
worker.terminate();
};

// Send a message to the worker to start the calculation
worker.postMessage({
event: event,
bits: bits,
});
});
```
- [ ] NIP-14 [Subject tag in Text events](https://github.com/nostr-protocol/nips/blob/master/14.md)
```js
Expand Down
60 changes: 29 additions & 31 deletions client-web/src/components/bottom-bar.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,37 +4,33 @@ import { useEffect, useState } from "react";
import { RELAY_MESSAGE_TYPE } from "@nostr-ts/common";

export function BottomBar() {
const [connected] = useNClient((state) => [state.connected]);
const [userCount, setUserCount] = useState(0);
const [lastUpdate, setLastUpdate] = useState(0);
const [events] = useNClient((state) => [state.events]);
const [maxEvents] = useNClient((state) => [state.maxEvents]);
const [relayEvents] = useNClient((state) => [state.relayEvents]);
const [eventsCount, maxEvents, relayEvents] = useNClient((state) => [
state.events.length,
state.maxEvents,
state.relayEvents,
]);
const [lastCount, setLastCount] = useState(0);

const toast = useToast();

useEffect(() => {
const statsUpdateInterval = setInterval(async () => {
const now = Date.now();

if (now - lastUpdate > 5000) {
setLastUpdate(now);
const count = await useNClient.getState().countUsers();
if (count) {
setUserCount(count);
}
const count = await useNClient.getState().countUsers();
if (count) {
setUserCount(count);
}
}, 1000);

return () => clearInterval(statsUpdateInterval);
}, []);

/**
* Relay events
*/
useEffect(() => {
const current = relayEvents.length;
if (current > 0) {
console.log(`current: ${current}, lastCount: ${lastCount}`);
console.log(relayEvents);
const diff = current - lastCount;
if (diff > 0) {
setLastCount(current);
Expand All @@ -45,9 +41,13 @@ export function BottomBar() {
if (event.data[0] === RELAY_MESSAGE_TYPE.NOTICE) {
description = event.data[1];
} else if (event.data[0] === RELAY_MESSAGE_TYPE.OK) {
description = `OK?: ${event.data[2]}. Event ${event.data[1]}: ${event.data[3]}`;
description = `${event.data[2]}. Event ${event.data[1]}: ${event.data[3]}`;
} else if (event.data[0] === RELAY_MESSAGE_TYPE.EOSE) {
description = `Eose: ${event.data[1]}`;
description = `${event.data[1]}`;
} else if (event.data[0] === RELAY_MESSAGE_TYPE.COUNT) {
description = `Relay ${event.data[1]}: ${JSON.stringify(
event.data[2]
)} events`;
}
console.log(description);
if (description !== "") {
Expand Down Expand Up @@ -76,20 +76,18 @@ export function BottomBar() {
p={3}
>
<HStack spacing={4}>
{connected && (
<>
<HStack spacing={2}>
<Text fontSize="sm">Events:</Text>
<Text fontSize="xl" marginLeft={1}>
{events.length} (max {maxEvents})
</Text>
</HStack>
<HStack spacing={2}>
<Text fontSize="sm">Users:</Text>
<Text fontSize="xl">{userCount}</Text>
</HStack>
</>
)}
<>
<HStack spacing={2}>
<Text fontSize="sm">Events:</Text>
<Text fontSize="xl" marginLeft={1}>
{eventsCount} (max {maxEvents})
</Text>
</HStack>
<HStack spacing={2}>
<Text fontSize="sm">Users:</Text>
<Text fontSize="xl">{userCount}</Text>
</HStack>
</>
</HStack>
</Box>
);
Expand Down
30 changes: 22 additions & 8 deletions client-web/src/components/create-event-form.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -35,11 +35,15 @@ export const CreateEventForm = () => {
state.connected && state.keystore !== "none",
]);
const [errors, setErrors] = useState<string[]>([]);
const [keystore] = useNClient((state) => [state.keystore]);
const [keypair] = useNClient((state) => [state.keypair]);
const [eventKind] = useNClient((state) => [state.newEvent?.kind || 0]);
const [newEventName] = useNClient((state) => [state.newEventName]);
const [newEvent] = useNClient((state) => [state.newEvent]);
const [keystore, keypair, eventKind, newEventName, newEvent] = useNClient(
(state) => [
state.keystore,
state.keypair,
state.newEvent?.kind || 0,
state.newEventName,
state.newEvent,
]
);
const toast = useToast();

const [users, setUsers] = useState<NUser[]>([]);
Expand Down Expand Up @@ -116,9 +120,19 @@ export const CreateEventForm = () => {
}

try {
await useNClient.getState().signAndSendEvent(newEvent);
const overwrite = true;
setKind(newEventName, overwrite);
const evId = await useNClient.getState().signAndSendEvent(newEvent);
if (evId) {
toast({
title: "Success",
description: `Event ${evId} submitted`,
status: "success",
duration: 5000,
isClosable: true,
});

const overwrite = true;
setKind(newEventName, overwrite);
}
} catch (e) {
let error = "";
if (e instanceof Error) {
Expand Down
Loading

0 comments on commit fbfd9cf

Please sign in to comment.