on master help sign in
adding listing management and easy content adds
commit55e85fe48de315a0ef67684284d4424e9b74c664 authorHunter Miller <hunter@hmiller.dev> dateSun 17 Jul 2022, 20:46 (4 years ago) parent5c2e31a
10 files changed+85−15
desk/app/sphinx.hoon+14−5 desk/lib/sphinx-json.hoon+6 desk/mar/directory.hoon+1 ui/src/components/Listings.tsx+1−1 ui/src/components/Meta.tsx+1−1 ui/src/manage-listings/Apps.tsx+14−3 ui/src/manage-listings/Groups.tsx+12−2 ui/src/manage-listings/MyListings.tsx+30−1 ui/src/state/apps.ts+2−2 ui/src/types/sphinx.ts+4
desk/app/sphinx.hoon+14−5
@@ -100,14 +100,20 @@
100100 ?+ mark ~|(bad-poke/mark !!)
101101 %declare
102102 =+ !<(=declare:s vase)
103− di-abet:(publish declare di-core)
103+ (publish declare cor)
104+ ::
105+ %declarations
106+ =+ !<(decs=(list declare:s) vase)
107+ =. cor (roll decs publish)
108+ cor
109+ ::
104110 %remove
105111 =+ !<(=hash:s vase)
106112 di-abet:di-remove:(di-abed:di-core hash)
107113 ==
108114 ++ publish
109− |= [=declare:s core=_di-core]
110− ^+ di-core
115+ |= [=declare:s core=_cor]
116+ ^+ cor
111117 ::
112118 ?> from-self
113119 =/ listing
@@ -119,8 +125,8 @@
119125 ==
120126 ?: (~(has by directory) hash.listing)
121127 ~& 'Listing already exists.'
122− di-core
123− (di-publish:(di-abed:core hash.listing) listing)
128+ cor
129+ di-abet:(di-publish:(di-abed:di-core:core hash.listing) listing)
124130 --
125131::
126132++ watch
@@ -169,6 +175,9 @@
169175 |= =path
170176 ^- (unit (unit cage))
171177 ?+ path [~ ~]
178+ [%x %published ~]
179+ ``directory+!>(published)
180+ ::
172181 [%x %lookup @ @ @ @ ~]
173182 =- ``search+!>(-)
174183 ^- search:s
desk/lib/sphinx-json.hoon+6
@@ -30,6 +30,12 @@
3030 size/n/(scot %ud size.search)
3131 total/n/(scot %ud total.search)
3232 ==
33+ ++ directory
34+ |= d=directory:s
35+ %- pairs
36+ %+ turn ~(tap by d)
37+ |= [=hash:s l=listing:s]
38+ [(scot %uv hash) (listing l)]
3339 --
3440++ dejs
3541 =, dejs:format
desk/mar/directory.hoon+1
@@ -5,6 +5,7 @@
55++ grow
66 |%
77 ++ noun directory
8+ ++ json (directory:enjs:j directory)
89 --
910++ grab
1011 |%
ui/src/components/Listings.tsx+1−1
@@ -27,7 +27,7 @@ export const Listings = ({ listings, remove, className }: ListingsProps) => {
2727 }
2828
2929 return (
30− <ul className={cn('px-2 space-y-6', className)}>
30+ <ul className={cn('space-y-6', className)}>
3131 {listings && listings.map(l => (
3232 <li key={l.hash}>
3333 <article className='group-1 flex w-full'>
ui/src/components/Meta.tsx+1−1
@@ -31,7 +31,7 @@ export const Meta = ({ className }: MetaProps) => {
3131 {version && <span className='mb-[3px]'>v{version}</span>}
3232 </div>
3333 <a
34− className="inline-block font-mono default-ring underline rounded-md hover:text-rosy mb-4"
34+ className="inline-block font-mono default-ring underline rounded-md hover:text-rosy"
3535 href="web+urbitgraph://group/~nocsyx-lassul/sphinx"
3636 >
3737 ~nocsyx-lassul/sphinx
ui/src/manage-listings/Apps.tsx+14−3
@@ -1,9 +1,10 @@
11import React, { useCallback, useEffect, useState } from 'react';
22import { FormProvider, useForm } from 'react-hook-form';
33import { Link } from 'react-router-dom';
4+import api from '../api';
45import { PostOptions } from '../components/PostOptions';
56import { useApps } from '../state/apps';
6−import { PostOption, PostOptionsForm } from '../types/sphinx';
7+import { Declare, Listing, PostOption, PostOptionsForm } from '../types/sphinx';
78
89function getAppKeys(apps: PostOption[]): string[] {
910 return apps.map(({ key }) => key);
@@ -27,9 +28,19 @@ export const Apps = () => {
2728 }
2829 }, [apps, options, setValue]);
2930
30− const onSubmit = useCallback(() => {
31+ const onSubmit = useCallback((values: PostOptionsForm) => {
32+ debugger;
33+ api.poke<Declare[]>({
34+ app: 'sphinx',
35+ mark: 'declarations',
36+ json: apps.filter(a => values.options.includes(a.key)).map(a => ({
37+ post: a.post,
38+ reach: 'friends'
39+ }))
40+ });
41+
3142 reset();
32− }, [reset]);
43+ }, [apps, reset]);
3344
3445 return (
3546 <>
ui/src/manage-listings/Groups.tsx+12−2
@@ -1,9 +1,10 @@
11import React, { useCallback, useEffect, useState } from 'react';
22import { FormProvider, useForm } from 'react-hook-form';
33import { Link } from 'react-router-dom';
4+import api from '../api';
45import { PostOptions } from '../components/PostOptions';
56import { useGroups } from '../state/groups';
6−import { PostOption, PostOptionsForm } from '../types/sphinx';
7+import { Declare, PostOption, PostOptionsForm } from '../types/sphinx';
78
89export const Groups = () => {
910 const groups = useGroups();
@@ -34,7 +35,16 @@ export const Groups = () => {
3435 }
3536 }, [groups, options, setValue]);
3637
37− const onSubmit = useCallback(() => {
38+ const onSubmit = useCallback((values: PostOptionsForm) => {
39+ api.poke<Declare[]>({
40+ app: 'sphinx',
41+ mark: 'declarations',
42+ json: groups.filter(a => values.options.includes(a.key)).map(a => ({
43+ post: a.post,
44+ reach: 'friends'
45+ }))
46+ });
47+
3848 reset();
3949 }, [reset]);
4050
ui/src/manage-listings/MyListings.tsx+30−1
@@ -1,5 +1,34 @@
1+import { size } from 'lodash';
12import React from 'react';
3+import { useMutation, useQuery, useQueryClient } from 'react-query';
4+import api from '../api';
5+import { Listings } from '../components/Listings';
6+import { Directory, Remove } from '../types/sphinx';
27
38export const MyListings = () => {
4− return <div />;
9+ const queryClient = useQueryClient();
10+ const { data } = useQuery('published', () => api.scry<Directory>({
11+ app: 'sphinx',
12+ path: '/published'
13+ }));
14+ const { mutate } = useMutation((hash: string) => {
15+ return api.poke<Remove>({
16+ app: 'sphinx',
17+ mark: 'remove',
18+ json: hash
19+ })
20+ }, {
21+ onSuccess: () => {
22+ queryClient.invalidateQueries('published');
23+ }
24+ });
25+
26+ return (
27+ <>
28+ <header className='flex items-center'>
29+ <h1 className='text-2xl font-semibold'>My Listings</h1>
30+ </header>
31+ <Listings listings={Object.values(data || {})} remove={mutate} className="mt-6" />
32+ </>
33+ )
534}
ui/src/state/apps.ts+2−2
@@ -4,12 +4,12 @@ import api from "../api";
44import { Post } from "../types/sphinx";
55
66function getAppPost(app: string, vat: Vat, charge: Charge): Post {
7− const ship = vat.arak.rail?.publisher || vat.arak.rail?.ship;
7+ const ship = vat.arak.rail?.publisher || vat.arak.rail?.ship || `~${window.ship}`;
88
99 return {
1010 type: 'app',
1111 title: charge.title,
12− link: `${ship}/${app}`,
12+ link: `web+urbitgraph://${ship}/${app}`,
1313 description: charge.info || charge.title,
1414 image: charge.image || '',
1515 tags: ['app']
ui/src/types/sphinx.ts+4
@@ -33,6 +33,10 @@ export type Search = {
3333 total: number;
3434}
3535
36+export interface Directory {
37+ [hash: string]: Listing;
38+}
39+
3640export interface PostOption {
3741 post: Post;
3842 key: string;