mirror of
https://github.com/coracle-social/coracle.git
synced 2024-09-30 00:41:12 +00:00
Opt for fast rather than complete loading
This commit is contained in:
parent
c781e88574
commit
383fb6e85d
@ -76,13 +76,11 @@ If you like Coracle and want to support its development, you can donate sats via
|
||||
- [x] Load feeds from network rather than user relays?
|
||||
- [x] Still use "my" relays for global, this could make global feed more useful
|
||||
- [x] If we use my relays for global, we don't have to wait for network to load initially
|
||||
- [ ] Figure out fast vs complete tradeoff. Skipping loadContext speeds things up a ton.
|
||||
- [ ] Make loadParents false by default. Maybe make fast the default
|
||||
- [ ] Figure out how to make threads fast and complete. Load only the note, then preload entire thread in background?
|
||||
- [x] Figure out fast vs complete tradeoff. Skipping loadContext speeds things up a ton.
|
||||
- [ ] Add relays/mentions to note and reply composition
|
||||
- [ ] Add layout component with max-w, padding, etc. Test on mobile size
|
||||
- [ ] Figure out migrations from previous version
|
||||
- [ ] Fix search
|
||||
- [ ] Move add note to modal
|
||||
|
||||
## 0.2.7
|
||||
|
||||
|
@ -23,6 +23,7 @@
|
||||
import PubKeyLogin from "src/views/PubKeyLogin.svelte"
|
||||
import NoteDetail from "src/views/NoteDetail.svelte"
|
||||
import PersonSettings from "src/views/PersonSettings.svelte"
|
||||
import NoteCreate from "src/views/NoteCreate.svelte"
|
||||
import NotFound from "src/routes/NotFound.svelte"
|
||||
import Search from "src/routes/Search.svelte"
|
||||
import Alerts from "src/routes/Alerts.svelte"
|
||||
@ -35,7 +36,6 @@
|
||||
import RelayList from "src/routes/RelayList.svelte"
|
||||
import AddRelay from "src/routes/AddRelay.svelte"
|
||||
import Person from "src/routes/Person.svelte"
|
||||
import NoteCreate from "src/routes/NoteCreate.svelte"
|
||||
import Bech32Entity from "src/routes/Bech32Entity.svelte"
|
||||
|
||||
export let url = ""
|
||||
@ -122,7 +122,6 @@
|
||||
<Route path="/alerts" component={Alerts} />
|
||||
<Route path="/search/:activeTab" component={Search} />
|
||||
<Route path="/notes/:activeTab" component={Notes} />
|
||||
<Route path="/notes/new" component={NoteCreate} />
|
||||
<Route path="/people/:npub/:activeTab" let:params>
|
||||
{#key params.npub}
|
||||
<Person {...params} />
|
||||
@ -171,7 +170,7 @@
|
||||
</li>
|
||||
{/if}
|
||||
<li class="cursor-pointer">
|
||||
<a class="block px-4 py-2 hover:bg-accent transition-all" href="/notes/latest">
|
||||
<a class="block px-4 py-2 hover:bg-accent transition-all" href="/notes/global">
|
||||
<i class="fa-solid fa-tag mr-2" /> Notes
|
||||
</a>
|
||||
</li>
|
||||
@ -228,9 +227,9 @@
|
||||
{#if $canSign}
|
||||
<div class="fixed bottom-0 right-0 m-8">
|
||||
<a
|
||||
href="/notes/new"
|
||||
class="rounded-full bg-accent color-white w-16 h-16 flex justify-center
|
||||
items-center border border-dark shadow-2xl cursor-pointer">
|
||||
items-center border border-dark shadow-2xl cursor-pointer"
|
||||
on:click={() => modal.set({form: 'note/create'})}>
|
||||
<span class="fa-sold fa-plus fa-2xl" />
|
||||
</a>
|
||||
</div>
|
||||
@ -242,6 +241,8 @@
|
||||
{#key $modal.note.id}
|
||||
<NoteDetail {...$modal} />
|
||||
{/key}
|
||||
{:else if $modal.form === 'note/create'}
|
||||
<NoteCreate />
|
||||
{:else if $modal.form === 'relay'}
|
||||
<AddRelay />
|
||||
{:else if $modal.form === 'signUp'}
|
||||
|
@ -52,11 +52,11 @@ export const getRelays = pubkey => {
|
||||
}
|
||||
|
||||
export const getEventRelays = event => {
|
||||
if (event.seen_on) {
|
||||
return [{url: event.seen_on}]
|
||||
}
|
||||
|
||||
return uniq(getRelays(event.pubkey).concat(Tags.from(event).relays())).map(objOf('url'))
|
||||
return uniq(
|
||||
getRelays(event.pubkey)
|
||||
.concat(Tags.from(event).relays())
|
||||
.concat(event.seen_on)
|
||||
).map(objOf('url'))
|
||||
}
|
||||
|
||||
export const publish = async (relays, event) => {
|
||||
|
@ -167,30 +167,27 @@ const subscribe = async (relays, filters) => {
|
||||
}
|
||||
}
|
||||
|
||||
const request = (relays, filters, {mode = "most"} = {}) => {
|
||||
const request = (relays, filters, {threshold = 1} = {}) => {
|
||||
relays = uniqBy(prop('url'), relays.filter(r => isRelay(r.url)))
|
||||
|
||||
return new Promise(async resolve => {
|
||||
const agg = await subscribe(relays, filters)
|
||||
const now = Date.now()
|
||||
const relaysWithEvents = new Set()
|
||||
const events = []
|
||||
const eose = []
|
||||
|
||||
const attemptToComplete = () => {
|
||||
// If we have all relays, most after a short timeout, or all after
|
||||
// a long timeout, go ahead and unsubscribe.
|
||||
// If we have all relays, more than `threshold` reporting events, most after
|
||||
// a short timeout, or all after a long timeout, go ahead and unsubscribe.
|
||||
const done = (
|
||||
eose.length === agg.subs.length
|
||||
|| Date.now() - now >= 5000
|
||||
|| eose.filter(url => relaysWithEvents.has(url)).length > threshold
|
||||
|| (
|
||||
mode === "fast"
|
||||
&& events.length
|
||||
)
|
||||
|| (
|
||||
mode === "most"
|
||||
&& Date.now() - now >= 1000
|
||||
Date.now() - now >= 1000
|
||||
&& eose.length > agg.subs.length - Math.round(agg.subs.length / 10)
|
||||
)
|
||||
|| Date.now() - now >= 5000
|
||||
)
|
||||
|
||||
if (done) {
|
||||
@ -212,7 +209,10 @@ const request = (relays, filters, {mode = "most"} = {}) => {
|
||||
}
|
||||
}
|
||||
|
||||
agg.onEvent(e => events.push(e))
|
||||
agg.onEvent(e => {
|
||||
relaysWithEvents.add(e.seen_on)
|
||||
events.push(e)
|
||||
})
|
||||
|
||||
agg.onEose(async url => {
|
||||
if (!eose.includes(url)) {
|
||||
|
@ -1,10 +1,10 @@
|
||||
import {whereEq, sortBy, identity, when, assoc, reject} from 'ramda'
|
||||
import {pluck, whereEq, sortBy, identity, when, assoc, reject} from 'ramda'
|
||||
import {navigate} from 'svelte-routing'
|
||||
import {createMap, ellipsize} from 'hurdak/lib/hurdak'
|
||||
import {get} from 'svelte/store'
|
||||
import {renderContent} from 'src/util/html'
|
||||
import {Tags, displayPerson, findReplyId} from 'src/util/nostr'
|
||||
import {user, people, getPerson, getRelays, load, keys} from 'src/agent'
|
||||
import {user, people, getPerson, getRelays, keys} from 'src/agent'
|
||||
import defaults from 'src/agent/defaults'
|
||||
import {toast, routes, modal, settings} from 'src/app/ui'
|
||||
import cmd from 'src/app/cmd'
|
||||
@ -29,7 +29,7 @@ export const login = async ({privkey, pubkey}, usingExtension = false) => {
|
||||
alerts.load(getRelays(), pubkey),
|
||||
alerts.listen(getRelays(), pubkey),
|
||||
|
||||
navigate('/notes/latest')
|
||||
navigate('/notes/global')
|
||||
}
|
||||
|
||||
export const addRelay = async relay => {
|
||||
@ -77,16 +77,6 @@ export const setRelayWriteCondition = async (url, write) => {
|
||||
}
|
||||
}
|
||||
|
||||
export const loadNote = async (relays, id) => {
|
||||
const [found] = await load(relays, {ids: [id]})
|
||||
|
||||
if (!found) {
|
||||
return null
|
||||
}
|
||||
|
||||
return annotate(found, await loaders.loadContext(relays, found, {mode: 'fast', loadChildren: true}))
|
||||
}
|
||||
|
||||
export const render = (note, {showEntire = false}) => {
|
||||
const shouldEllipsize = note.content.length > 500 && !showEntire
|
||||
const $people = get(people)
|
||||
@ -133,8 +123,7 @@ export const annotate = (note, context) => {
|
||||
}
|
||||
|
||||
export const threadify = (events, context, {muffle = []} = {}) => {
|
||||
const contextById = createMap('id', context)
|
||||
|
||||
const contextById = createMap('id', events.concat(context))
|
||||
// Show parents when possible. For reactions, if there's no parent,
|
||||
// throw it away. Sort by created date descending
|
||||
const notes = sortBy(
|
||||
@ -144,14 +133,19 @@ export const threadify = (events, context, {muffle = []} = {}) => {
|
||||
.filter(e => e && !muffle.includes(e.pubkey))
|
||||
)
|
||||
|
||||
// Annotate our feed with parents, reactions, replies
|
||||
return notes.map(note => {
|
||||
let parent = contextById[findReplyId(note)]
|
||||
// Don't show notes that will also show up as children
|
||||
const noteIds = new Set(pluck('id', notes))
|
||||
|
||||
if (parent) {
|
||||
parent = annotate(parent, context)
|
||||
}
|
||||
// Annotate our feed with parents, reactions, replies.
|
||||
return notes
|
||||
.filter(note => !noteIds.has(findReplyId(note)))
|
||||
.map(note => {
|
||||
let parent = contextById[findReplyId(note)]
|
||||
|
||||
return annotate({...note, parent}, context)
|
||||
})
|
||||
if (parent) {
|
||||
parent = annotate(parent, context)
|
||||
}
|
||||
|
||||
return annotate({...note, parent}, context)
|
||||
})
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
import {propEq, uniqBy, prop, uniq, flatten, pluck, identity} from 'ramda'
|
||||
import {uniqBy, prop, uniq, flatten, pluck, identity} from 'ramda'
|
||||
import {ensurePlural, createMap, chunk} from 'hurdak/lib/hurdak'
|
||||
import {findReply, personKinds, Tags} from 'src/util/nostr'
|
||||
import {now, timedelta} from 'src/util/misc'
|
||||
@ -41,10 +41,10 @@ const loadNetwork = async (relays, pubkey) => {
|
||||
const tags = Tags.wrap(petnames)
|
||||
|
||||
// Use nip-2 recommended relays to load our user's second-order follows
|
||||
await loadPeople(tags.relays(), tags.values().all(), {mode: 'fast'})
|
||||
await loadPeople(tags.relays(), tags.values().all())
|
||||
}
|
||||
|
||||
const loadContext = async (relays, notes, {loadParents = true, loadChildren = false, ...opts} = {}) => {
|
||||
const loadContext = async (relays, notes, {loadParents = false, depth = 0, ...opts} = {}) => {
|
||||
notes = ensurePlural(notes)
|
||||
|
||||
if (notes.length === 0) {
|
||||
@ -53,34 +53,39 @@ const loadContext = async (relays, notes, {loadParents = true, loadChildren = fa
|
||||
|
||||
return flatten(await Promise.all(
|
||||
chunk(256, notes).map(async chunk => {
|
||||
const authors = getStalePubkeys(pluck('pubkey', notes))
|
||||
const parentTags = uniq(notes.map(findReply).filter(identity))
|
||||
const chunkIds = pluck('id', chunk)
|
||||
const authors = getStalePubkeys(pluck('pubkey', chunk))
|
||||
const parentTags = uniq(chunk.map(findReply).filter(identity))
|
||||
const parentIds = Tags.wrap(parentTags).values().all()
|
||||
const combinedRelays = uniq(relays.concat(Tags.wrap(parentTags).relays()))
|
||||
const filter = [{kinds: [1, 7], '#e': pluck('id', notes)}]
|
||||
const filter = [{kinds: [1, 7], '#e': chunkIds}]
|
||||
|
||||
if (authors.length > 0) {
|
||||
filter.push({kinds: personKinds, authors})
|
||||
}
|
||||
|
||||
if (loadParents && parentTags.length > 0) {
|
||||
filter.push({kinds: [1], ids: Tags.wrap(parentTags).values().all()})
|
||||
filter.push({kinds: [1], ids: parentIds})
|
||||
}
|
||||
|
||||
let events = await load(combinedRelays, filter, opts)
|
||||
|
||||
const children = events.filter(propEq('kind', 1))
|
||||
const childRelays = Tags.from(children).relays()
|
||||
// Find children, but only if we didn't already get them
|
||||
const children = events.filter(e => e.kind === 1)
|
||||
const childRelays = relays.concat(Tags.from(children).relays())
|
||||
|
||||
if (loadChildren && children.length > 0) {
|
||||
events = events.concat(await loadContext(childRelays, children, {loadParents: false, ...opts}))
|
||||
if (depth > 0 && children.length > 0) {
|
||||
events = events.concat(
|
||||
await loadContext(childRelays, children, {depth: depth - 1, ...opts})
|
||||
)
|
||||
}
|
||||
|
||||
if (loadParents && parentTags.length > 0) {
|
||||
if (loadParents && parentIds.length > 0) {
|
||||
const eventsById = createMap('id', events)
|
||||
const parents = Tags.wrap(parentTags).values().all().map(id => eventsById[id]).filter(identity)
|
||||
const parentRelays = Tags.from(parents).relays()
|
||||
const parents = parentIds.map(id => eventsById[id]).filter(identity)
|
||||
const parentRelays = relays.concat(Tags.from(parents).relays())
|
||||
|
||||
events = events.concat(await loadContext(parentRelays, parents, {loadParents: false, ...opts}))
|
||||
events = events.concat(await loadContext(parentRelays, parents, opts))
|
||||
}
|
||||
|
||||
// We're recurring and so may end up with duplicates here
|
||||
|
@ -21,6 +21,6 @@
|
||||
)
|
||||
</script>
|
||||
|
||||
<a on:click {...$$props} {href} class={className} target={external ? '_blank noopener' : null}>
|
||||
<a on:click {...$$props} {href} class={className} target={external ? '_blank' : null}>
|
||||
<slot />
|
||||
</a>
|
||||
|
@ -11,8 +11,8 @@
|
||||
in:fly={{y: 20}}
|
||||
class={cx("py-2 px-3 flex flex-col gap-2 text-white", {
|
||||
"cursor-pointer transition-all": interactive,
|
||||
"border border-solid border-black hover:border-medium hover:bg-dark": interactive && !invertColors,
|
||||
"border border-solid border-dark hover:border-medium hover:bg-medium": interactive && invertColors,
|
||||
"hover:bg-dark": interactive && !invertColors,
|
||||
"hover:bg-medium": interactive && invertColors,
|
||||
})}>
|
||||
<slot />
|
||||
</li>
|
||||
|
@ -3,7 +3,7 @@
|
||||
|
||||
export let size = "2xl"
|
||||
|
||||
const className = "flex flex-col m-auto text-white gap-8"
|
||||
const className = "flex flex-col m-auto text-white gap-6"
|
||||
|
||||
if (!['lg', '2xl'].includes(size)) {
|
||||
throw new Error(`Invalid size: ${size}`)
|
||||
|
@ -15,7 +15,7 @@
|
||||
import Badge from "src/partials/Badge.svelte"
|
||||
import Compose from "src/partials/Compose.svelte"
|
||||
import Card from "src/partials/Card.svelte"
|
||||
import {user, getPerson, getRelays, getEventRelays} from 'src/agent'
|
||||
import {user, people, getRelays, getEventRelays} from 'src/agent'
|
||||
import cmd from 'src/app/cmd'
|
||||
|
||||
export let note
|
||||
@ -31,7 +31,9 @@
|
||||
const interactive = !anchorId || !showEntire
|
||||
const relays = getEventRelays(note)
|
||||
|
||||
let likes, flags, like, flag
|
||||
let likes, flags, like, flag, person
|
||||
|
||||
$: person = $people[note.pubkey] || {pubkey: note.pubkey}
|
||||
|
||||
$: {
|
||||
likes = note.reactions.filter(n => isLike(n.content))
|
||||
@ -116,7 +118,7 @@
|
||||
|
||||
<Card on:click={onClick} {interactive} {invertColors}>
|
||||
<div class="flex gap-4 items-center justify-between">
|
||||
<Badge person={getPerson(note.pubkey, true)} />
|
||||
<Badge person={person} />
|
||||
<Anchor
|
||||
href={"/" + nip19.neventEncode({id: note.id, relays: pluck('url', relays)})}
|
||||
class="text-sm text-light"
|
||||
|
@ -53,14 +53,17 @@
|
||||
{#if newNotes.length > 0}
|
||||
<div
|
||||
in:slide
|
||||
class="mb-2 cursor-pointer text-center underline text-light"
|
||||
class="cursor-pointer text-center underline text-light"
|
||||
on:click={showNewNotes}>
|
||||
Load {quantify(newNotes.length, 'new note')}
|
||||
</div>
|
||||
{/if}
|
||||
{#each notes as note (note.id)}
|
||||
<Note {note} {depth} />
|
||||
{/each}
|
||||
</Content>
|
||||
|
||||
<Spinner />
|
||||
<div>
|
||||
{#each notes as note (note.id)}
|
||||
<Note {note} {depth} />
|
||||
{/each}
|
||||
</div>
|
||||
|
||||
<Spinner />
|
||||
</Content>
|
||||
|
@ -1,6 +1,7 @@
|
||||
<script>
|
||||
import {objOf} from 'ramda'
|
||||
import {nip19} from 'nostr-tools'
|
||||
import Content from 'src/partials/Content.svelte'
|
||||
import NoteDetail from 'src/views/NoteDetail.svelte'
|
||||
import Person from 'src/routes/Person.svelte'
|
||||
|
||||
@ -11,9 +12,13 @@
|
||||
</script>
|
||||
|
||||
{#if type === "nevent"}
|
||||
<NoteDetail note={{id: data.id}} {relays} />
|
||||
<Content>
|
||||
<NoteDetail note={{id: data.id}} {relays} />
|
||||
</Content>
|
||||
{:else if type === "note"}
|
||||
<NoteDetail note={{id: data}} />
|
||||
<Content>
|
||||
<NoteDetail note={{id: data}} />
|
||||
</Content>
|
||||
{:else if type === "nprofile"}
|
||||
<Person npub={nip19.npubEncode(data.pubkey)} {relays} activeTab="notes" />
|
||||
{:else if type === "npub"}
|
||||
|
@ -2,5 +2,5 @@
|
||||
import {onMount} from 'svelte'
|
||||
import {navigate} from 'svelte-routing'
|
||||
|
||||
onMount(() => navigate('/notes/latest'))
|
||||
onMount(() => navigate('/notes/global'))
|
||||
</script>
|
||||
|
@ -1,48 +0,0 @@
|
||||
<script>
|
||||
import {onMount} from "svelte"
|
||||
import {fly} from 'svelte/transition'
|
||||
import {navigate} from "svelte-routing"
|
||||
import Button from "src/partials/Button.svelte"
|
||||
import Compose from "src/partials/Compose.svelte"
|
||||
import Content from "src/partials/Content.svelte"
|
||||
import Heading from 'src/partials/Heading.svelte'
|
||||
import {user, getRelays} from "src/agent"
|
||||
import {toast} from "src/app"
|
||||
import cmd from "src/app/cmd"
|
||||
|
||||
let input = null
|
||||
|
||||
const onSubmit = async e => {
|
||||
const {content, mentions} = input.parse()
|
||||
|
||||
if (content) {
|
||||
await cmd.createNote(getRelays(), content, mentions)
|
||||
|
||||
toast.show("info", `Your note has been created!`)
|
||||
|
||||
history.back()
|
||||
}
|
||||
}
|
||||
|
||||
onMount(() => {
|
||||
if (!$user) {
|
||||
navigate("/login")
|
||||
}
|
||||
})
|
||||
</script>
|
||||
|
||||
<form on:submit|preventDefault={onSubmit} in:fly={{y: 20}}>
|
||||
<Content size="lg">
|
||||
<Heading class="text-center">Create a note</Heading>
|
||||
<div class="flex flex-col gap-4 w-full">
|
||||
<div class="flex flex-col gap-2">
|
||||
<strong>What do you want to say?</strong>
|
||||
<div class="border-l-2 border-solid border-medium pl-4">
|
||||
<Compose bind:this={input} {onSubmit} />
|
||||
</div>
|
||||
</div>
|
||||
<Button type="submit" class="text-center">Send</Button>
|
||||
</div>
|
||||
</Content>
|
||||
</form>
|
||||
|
@ -4,7 +4,7 @@
|
||||
import Content from "src/partials/Content.svelte"
|
||||
import Tabs from "src/partials/Tabs.svelte"
|
||||
import Network from "src/views/notes/Network.svelte"
|
||||
import Latest from "src/views/notes/Latest.svelte"
|
||||
import Global from "src/views/notes/Global.svelte"
|
||||
import {user} from 'src/agent'
|
||||
|
||||
export let activeTab
|
||||
@ -12,18 +12,21 @@
|
||||
const setActiveTab = tab => navigate(`/notes/${tab}`)
|
||||
</script>
|
||||
|
||||
{#if !$user}
|
||||
<Content size="lg" class="text-center">
|
||||
<p>
|
||||
Don't have an account? Click <Anchor href="/login">here</Anchor> to join the nostr network.
|
||||
</p>
|
||||
<Content>
|
||||
{#if !$user}
|
||||
<Content size="lg" class="text-center">
|
||||
<p>
|
||||
Don't have an account? Click <Anchor href="/login">here</Anchor> to join the nostr network.
|
||||
</p>
|
||||
</Content>
|
||||
{/if}
|
||||
|
||||
<div>
|
||||
<Tabs tabs={['global', 'network']} {activeTab} {setActiveTab} />
|
||||
{#if activeTab === 'network'}
|
||||
<Network />
|
||||
{:else}
|
||||
<Global />
|
||||
{/if}
|
||||
</div>
|
||||
</Content>
|
||||
{/if}
|
||||
|
||||
<Tabs tabs={['latest', 'network']} {activeTab} {setActiveTab} />
|
||||
|
||||
{#if activeTab === 'network'}
|
||||
<Network />
|
||||
{:else}
|
||||
<Latest />
|
||||
{/if}
|
||||
|
@ -1,5 +1,5 @@
|
||||
<script>
|
||||
import {fly} from 'svelte/transition'
|
||||
import {navigate} from 'svelte-routing'
|
||||
import Input from "src/partials/Input.svelte"
|
||||
import Content from 'src/partials/Content.svelte'
|
||||
import Tabs from 'src/partials/Tabs.svelte'
|
||||
|
@ -97,7 +97,7 @@ export const renderContent = content => {
|
||||
const $a = document.createElement('a')
|
||||
|
||||
$a.href = url
|
||||
$a.target = "_blank noopener"
|
||||
$a.target = "_blank"
|
||||
$a.className = "underline"
|
||||
|
||||
/* eslint no-useless-escape: 0 */
|
||||
@ -107,5 +107,5 @@ export const renderContent = content => {
|
||||
content = content.replace(url, $a.outerHTML)
|
||||
}
|
||||
|
||||
return content
|
||||
return content.trim()
|
||||
}
|
||||
|
@ -49,6 +49,10 @@ export const findRoot = e =>
|
||||
export const findRootId = e => Tags.wrap([findRoot(e)]).values().first()
|
||||
|
||||
export const displayPerson = p => {
|
||||
if (p.display_name) {
|
||||
return p.display_name
|
||||
}
|
||||
|
||||
if (p.name) {
|
||||
return p.name
|
||||
}
|
||||
|
@ -1,7 +1,10 @@
|
||||
<script>
|
||||
import {onMount} from 'svelte'
|
||||
import {nip19} from 'nostr-tools'
|
||||
import {fly} from 'svelte/transition'
|
||||
import {loadNote} from 'src/app'
|
||||
import {load} from 'src/agent'
|
||||
import {annotate} from 'src/app'
|
||||
import loaders from 'src/app/loaders'
|
||||
import Note from 'src/partials/Note.svelte'
|
||||
import Content from 'src/partials/Content.svelte'
|
||||
import Spinner from 'src/partials/Spinner.svelte'
|
||||
@ -11,17 +14,28 @@
|
||||
|
||||
let loading = true
|
||||
|
||||
const logNote = () => {
|
||||
if (note) {
|
||||
onMount(async () => {
|
||||
const [found] = await load(relays, {ids: [note.id]})
|
||||
|
||||
if (found) {
|
||||
// Show the main note without waiting for context
|
||||
if (!note.pubkey) {
|
||||
note = annotate(found, [])
|
||||
}
|
||||
|
||||
const context = await loaders.loadContext(relays, found, {
|
||||
depth: 3,
|
||||
loadParents: true,
|
||||
})
|
||||
|
||||
note = annotate(found, context)
|
||||
|
||||
console.log('NoteDetail', nip19.noteEncode(note.id), note)
|
||||
} else if (!note.pubkey) {
|
||||
note = null
|
||||
}
|
||||
}
|
||||
|
||||
loadNote(relays, note.id).then(found => {
|
||||
note = found
|
||||
loading = false
|
||||
|
||||
logNote()
|
||||
})
|
||||
</script>
|
||||
|
||||
|
@ -1,6 +1,5 @@
|
||||
<script>
|
||||
import {prop} from 'ramda'
|
||||
import {fly} from 'svelte/transition'
|
||||
import {ellipsize} from 'hurdak/lib/hurdak'
|
||||
import {fuzzy} from "src/util/misc"
|
||||
import {renderContent} from "src/util/html"
|
||||
|
@ -18,7 +18,7 @@
|
||||
|
||||
const loadNotes = async () => {
|
||||
const {limit, until} = cursor
|
||||
const notes = await load(relays, {...filter, limit, until}, {mode: 'fast'})
|
||||
const notes = await load(relays, {...filter, limit, until})
|
||||
const context = await loaders.loadContext(relays, notes)
|
||||
|
||||
cursor.onChunk(notes)
|
@ -24,7 +24,7 @@
|
||||
|
||||
const loadNotes = async () => {
|
||||
const {limit, until} = cursor
|
||||
const notes = await load(relays, {...filter, limit, until}, {mode: 'fast'})
|
||||
const notes = await load(relays, {...filter, limit, until})
|
||||
const context = await loaders.loadContext(relays, notes)
|
||||
|
||||
cursor.onChunk(notes)
|
||||
|
Loading…
Reference in New Issue
Block a user