From 52f7573475798b853293ae0acb60f9ce55da2c55 Mon Sep 17 00:00:00 2001 From: Shusui MOYATANI Date: Thu, 23 Nov 2023 00:54:04 +0900 Subject: [PATCH] fix: eslint errors --- .eslintrc.js | 7 +++ .github/ISSUE_TEMPLATE/bug_report.md | 18 ++++---- .github/ISSUE_TEMPLATE/bug_report_jp.md | 18 ++++---- .github/ISSUE_TEMPLATE/feature_request.md | 1 - .github/ISSUE_TEMPLATE/feature_request_jp.md | 1 - .../pull_request_template.md | 1 - .../pull_request_template_jp.md | 1 - .github/workflows/ci.yml | 2 +- README.md | 10 ++--- index.html | 14 ++++-- package.json | 6 ++- public/404.html | 23 +++++----- public/manifest.json | 21 +++++---- scripts/fix.sh | 2 +- src/components/EmojiPicker.tsx | 1 + src/components/column/BookmarkColumn.tsx | 5 ++- src/components/column/ChannelColumn.tsx | 5 +-- src/components/column/ColumnSettings.tsx | 14 +++--- src/components/event/EventDisplay.tsx | 4 +- src/components/event/LongFormContent.tsx | 24 ---------- src/components/event/TextNote.tsx | 1 - src/components/modal/AddColumn.tsx | 4 +- src/components/modal/EventDebugModal.tsx | 2 +- src/components/modal/ProfileDisplay.tsx | 2 - src/components/timeline/Notification.tsx | 14 ++---- src/components/utils/Copy.tsx | 4 +- src/core/useConfig.ts | 4 +- src/hooks/useFileInput.ts | 11 ----- src/hooks/useMessageBus.ts | 1 + src/hooks/useResizedImage.ts | 6 +-- src/hooks/useShortcutKeys.ts | 5 +-- src/nostr/event.ts | 2 +- src/nostr/event/LongFormContent.ts | 44 ------------------- src/nostr/event/Profile.ts | 1 + src/nostr/event/Reaction.ts | 2 +- src/nostr/event/TextNote.ts | 4 +- src/nostr/parseTextNote.test.ts | 3 +- src/nostr/parseTextNote.ts | 2 +- src/nostr/useBatchedEvents.ts | 10 ++--- src/nostr/useDecrypt.ts | 2 + src/nostr/useEvent.ts | 2 +- src/nostr/useParameterizedReplaceableEvent.ts | 2 +- src/nostr/useVerification.ts | 2 +- src/pages/Home.tsx | 1 - src/utils/ensureNonNull.ts | 19 ++++---- src/utils/ensureSchema.ts | 1 + src/utils/imageUpload.ts | 32 -------------- src/utils/stripMargin.ts | 1 + tsconfig.json | 21 ++------- 49 files changed, 130 insertions(+), 253 deletions(-) delete mode 100644 src/components/event/LongFormContent.tsx delete mode 100644 src/hooks/useFileInput.ts delete mode 100644 src/nostr/event/LongFormContent.ts diff --git a/.eslintrc.js b/.eslintrc.js index dbf8c5b..312b896 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -81,6 +81,13 @@ module.exports = { 'created-at', 'actions', 'content', + 'profile', + 'profile-icon', + 'profile-name', + 'profile-username', + 'notification-icon', + 'notification-user', + 'notification-event', ], }, }, diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md index dac250b..2871f7d 100644 --- a/.github/ISSUE_TEMPLATE/bug_report.md +++ b/.github/ISSUE_TEMPLATE/bug_report.md @@ -4,7 +4,6 @@ about: Create a report to help us improve title: '' labels: bug assignees: syusui-s - --- **Describe the bug** @@ -12,6 +11,7 @@ A clear and concise description of what the bug is. **To Reproduce** Steps to reproduce the behavior: + 1. Go to '...' 2. Click on '....' 3. Scroll down to '....' @@ -24,15 +24,17 @@ A clear and concise description of what you expected to happen. If applicable, add screenshots to help explain your problem. **Desktop (please complete the following information):** - - OS: [e.g. iOS] - - Browser [e.g. chrome, safari] - - Version [e.g. 22] + +- OS: [e.g. iOS] +- Browser [e.g. chrome, safari] +- Version [e.g. 22] **Smartphone (please complete the following information):** - - Device: [e.g. iPhone6] - - OS: [e.g. iOS8.1] - - Browser [e.g. stock browser, safari] - - Version [e.g. 22] + +- Device: [e.g. iPhone6] +- OS: [e.g. iOS8.1] +- Browser [e.g. stock browser, safari] +- Version [e.g. 22] **Additional context** Add any other context about the problem here. diff --git a/.github/ISSUE_TEMPLATE/bug_report_jp.md b/.github/ISSUE_TEMPLATE/bug_report_jp.md index f0419af..b17015a 100644 --- a/.github/ISSUE_TEMPLATE/bug_report_jp.md +++ b/.github/ISSUE_TEMPLATE/bug_report_jp.md @@ -4,7 +4,6 @@ about: 改善に取り組めるように報告を作成します title: '' labels: bug assignees: syusui-s - --- **バグの説明** @@ -12,6 +11,7 @@ assignees: syusui-s **再現手順** 発生させる手順を説明してください: + 1. '...'に移動 2. '....'をクリック 3. '....'までスクロールする @@ -24,15 +24,17 @@ assignees: syusui-s スクリーンショットがあればこちらに。 **デスクトップ (該当する場合は以下の情報を埋めてください):** - - OS: (例: Windows 11, macOS Ventura) - - ブラウザ: (例: Chrome, Firefox, Safari, Edge) - - バージョン: (例: 110) + +- OS: (例: Windows 11, macOS Ventura) +- ブラウザ: (例: Chrome, Firefox, Safari, Edge) +- バージョン: (例: 110) **スマートフォン (該当する場合は以下の情報を埋めてください):** - - デバイス: (例: iPhone 12) - - OS: (例: iOS 16.2, Android 13) - - ブラウザ: (例: Safari, Chrome) - - バージョン: (例: 110) + +- デバイス: (例: iPhone 12) +- OS: (例: iOS 16.2, Android 13) +- ブラウザ: (例: Safari, Chrome) +- バージョン: (例: 110) **追加の情報** 問題に関する他の情報があればこちらに。 diff --git a/.github/ISSUE_TEMPLATE/feature_request.md b/.github/ISSUE_TEMPLATE/feature_request.md index 214a521..03d0556 100644 --- a/.github/ISSUE_TEMPLATE/feature_request.md +++ b/.github/ISSUE_TEMPLATE/feature_request.md @@ -4,7 +4,6 @@ about: Suggest an idea for this project title: '' labels: enhancement assignees: syusui-s - --- **Is your feature request related to a problem? Please describe.** diff --git a/.github/ISSUE_TEMPLATE/feature_request_jp.md b/.github/ISSUE_TEMPLATE/feature_request_jp.md index 11e1f5f..37eb9e2 100644 --- a/.github/ISSUE_TEMPLATE/feature_request_jp.md +++ b/.github/ISSUE_TEMPLATE/feature_request_jp.md @@ -4,7 +4,6 @@ about: このプロジェクトにアイデアを提案します title: '' labels: enhancement assignees: syusui-s - --- **要望は何らかの問題に関連していますか?説明してください** diff --git a/.github/PULL_REQUEST_TEMPLATE/pull_request_template.md b/.github/PULL_REQUEST_TEMPLATE/pull_request_template.md index 8501d07..01cf080 100644 --- a/.github/PULL_REQUEST_TEMPLATE/pull_request_template.md +++ b/.github/PULL_REQUEST_TEMPLATE/pull_request_template.md @@ -3,7 +3,6 @@ name: Pull request about: Suggest changes title: '' labels: - --- **Describe the changes** diff --git a/.github/PULL_REQUEST_TEMPLATE/pull_request_template_jp.md b/.github/PULL_REQUEST_TEMPLATE/pull_request_template_jp.md index 45d0282..a2594b1 100644 --- a/.github/PULL_REQUEST_TEMPLATE/pull_request_template_jp.md +++ b/.github/PULL_REQUEST_TEMPLATE/pull_request_template_jp.md @@ -3,7 +3,6 @@ name: プルリクエスト about: 変更を提案します title: '' labels: - --- **変更について説明してください** diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index b16aa4e..e5fceec 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -3,7 +3,7 @@ name: CI on: push: branch: - - "*" + - '*' jobs: ci: permissions: diff --git a/README.md b/README.md index 8aef255..6d029c6 100644 --- a/README.md +++ b/README.md @@ -5,7 +5,7 @@ A nostr client like TweetDeck made with SolidJS. ## 使い方 1. NIP-07に対応したブラウザ拡張機能のインストールが事前に必要です - * [NIP-07](https://scrapbox.io/nostr/NIP-07#63e1c10c8b8fcb00000584fc) を参考に拡張機能をインストールしてください。 + - [NIP-07](https://scrapbox.io/nostr/NIP-07#63e1c10c8b8fcb00000584fc) を参考に拡張機能をインストールしてください。 1. https://syusui-s.github.io/rabbit/ にアクセス 1. NIP-07拡張機能に許可を求められるので許可ボタンを押す 1. タイムラインが表示されます @@ -29,11 +29,11 @@ the Free Software Foundation, either version 3 of the License, or This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more details. You should have received a copy of the GNU Affero General Public License -along with this program. If not, see . +along with this program. If not, see . ### 日本語 @@ -41,8 +41,8 @@ along with this program. If not, see . GNUアフェロー一般公衆利用許諾書(バージョン3か、それ以降のいずれかのバージョン) が定める条件の下で再頒布または改変することができます。 -このプログラムは有用であることを願って頒布されますが、 *全くの無保証* です。 -*商業可能性* や *特定目的への適合性* に対する保証は言外に示されたものも含め、全く存在しません。 +このプログラムは有用であることを願って頒布されますが、 _全くの無保証_ です。 +_商業可能性_ や _特定目的への適合性_ に対する保証は言外に示されたものも含め、全く存在しません。 詳しくはGNUアフェロー一般公衆利用許諾書をご覧ください。 あなたはこのプログラムと共にGNUアフェロー一般公衆利用許諾書のコピーを一部受け取っているはずです。 diff --git a/index.html b/index.html index d90c221..cf0adf2 100644 --- a/index.html +++ b/index.html @@ -1,4 +1,4 @@ - + @@ -6,12 +6,18 @@ - + - - + + diff --git a/package.json b/package.json index 7939100..445e09f 100644 --- a/package.json +++ b/package.json @@ -9,9 +9,11 @@ "dev": "npm run generatePackageInfo && vite", "build": "npm run generatePackageInfo && vite build", "serve": "npm run generatePackageInfo && vite preview", - "eslint": "eslint --cache .", + "lint": "npm run prettier && npm run eslint", + "fix": "npm run prettier-fix && npm run eslint-fix", + "eslint": "eslint .", "prettier": "prettier -c .", - "eslint-fix": "eslint --cache --fix .", + "eslint-fix": "eslint --fix .", "prettier-fix": "prettier --write .", "tsc": "tsc --noEmit --skipLibCheck", "test": "vitest run --no-watch", diff --git a/public/404.html b/public/404.html index aa006c5..ddf48f0 100644 --- a/public/404.html +++ b/public/404.html @@ -1,15 +1,14 @@ - - - -Rabbit - - -

お探しのページは見つかりませんでした

-

- トップに戻る -

- + + + + Rabbit + + +

お探しのページは見つかりませんでした

+

+ トップに戻る +

+ - diff --git a/public/manifest.json b/public/manifest.json index 7e69bd3..219b823 100644 --- a/public/manifest.json +++ b/public/manifest.json @@ -6,13 +6,16 @@ "display": "browser", "background_color": "#fff", "description": "A deck style nostr client.", - "icons": [{ - "src": "images/rabbit_app_256.png", - "sizes": "256x256", - "type": "image/png" - }, { - "src": "images/rabbit_app_1280.png", - "sizes": "1280x1280", - "type": "image/png" - }] + "icons": [ + { + "src": "images/rabbit_app_256.png", + "sizes": "256x256", + "type": "image/png" + }, + { + "src": "images/rabbit_app_1280.png", + "sizes": "1280x1280", + "type": "image/png" + } + ] } diff --git a/scripts/fix.sh b/scripts/fix.sh index f2f2c07..b8f34dd 100755 --- a/scripts/fix.sh +++ b/scripts/fix.sh @@ -1,4 +1,4 @@ #!/bin/sh prettier --write "$@" -eslint --cache --fix "$@" +eslint --fix "$@" diff --git a/src/components/EmojiPicker.tsx b/src/components/EmojiPicker.tsx index 892ffc0..4f27e56 100644 --- a/src/components/EmojiPicker.tsx +++ b/src/components/EmojiPicker.tsx @@ -76,6 +76,7 @@ const EmojiPicker: Component = (props) => { }, }); + // eslint-disable-next-line @typescript-eslint/no-explicit-any pickerElement = picker as any as HTMLElement; popupRef?.elem?.appendChild(pickerElement); }; diff --git a/src/components/column/BookmarkColumn.tsx b/src/components/column/BookmarkColumn.tsx index 399402f..a340e01 100644 --- a/src/components/column/BookmarkColumn.tsx +++ b/src/components/column/BookmarkColumn.tsx @@ -1,4 +1,4 @@ -import { Component, Show, createEffect, onCleanup, onMount } from 'solid-js'; +import { Component, Show } from 'solid-js'; import BookmarkIcon from 'heroicons/24/outline/bookmark.svg'; @@ -9,7 +9,6 @@ import Bookmark from '@/components/timeline/Bookmark'; import { BookmarkColumnType } from '@/core/column'; import useConfig from '@/core/useConfig'; import { useTranslation } from '@/i18n/useTranslation'; -import useDecrypt from '@/nostr/useDecrypt'; import useParameterizedReplaceableEvent from '@/nostr/useParameterizedReplaceableEvent'; type BookmarkColumnDisplayProps = { @@ -28,6 +27,8 @@ const BookmarkColumn: Component = (props) => { identifier: props.column.identifier, })); + // TODO 暗号化されたデータがある場合は復号する + return ( = (props) => { - return ( -
-
{props.title}
-
{props.children}
-
- ); -}; +const ColumnSettingsSection: Component = (props) => ( +
+
{props.title}
+
{props.children}
+
+); const ColumnSettings: Component = (props) => { const i18n = useTranslation(); diff --git a/src/components/event/EventDisplay.tsx b/src/components/event/EventDisplay.tsx index b83dd31..5d54e05 100644 --- a/src/components/event/EventDisplay.tsx +++ b/src/components/event/EventDisplay.tsx @@ -39,10 +39,10 @@ const EventDisplay: Component = (props) => { - + - + diff --git a/src/components/event/LongFormContent.tsx b/src/components/event/LongFormContent.tsx deleted file mode 100644 index 717e6c6..0000000 --- a/src/components/event/LongFormContent.tsx +++ /dev/null @@ -1,24 +0,0 @@ -import { Component } from 'solid-js'; - -import DocumentText from 'heroicons/24/outline/document-text.svg'; -import { Kind, Event as NostrEvent } from 'nostr-tools'; - -import { genericEvent } from '@/nostr/event'; - -export type LongFormContentProps = { - event: NostrEvent; -}; - -const LongFormContent: Component = (props) => ( - // const event = () => genericEvent(props.event); - - -); -export default LongFormContent; diff --git a/src/components/event/TextNote.tsx b/src/components/event/TextNote.tsx index 282942a..bff8be2 100644 --- a/src/components/event/TextNote.tsx +++ b/src/components/event/TextNote.tsx @@ -1,6 +1,5 @@ import { Show, type Component } from 'solid-js'; -import ColumnItem from '@/components/ColumnItem'; // eslint-disable-next-line import/no-cycle import TextNoteDisplay, { TextNoteDisplayProps } from '@/components/event/textNote/TextNoteDisplay'; import useConfig from '@/core/useConfig'; diff --git a/src/components/modal/AddColumn.tsx b/src/components/modal/AddColumn.tsx index 8943470..156fffa 100644 --- a/src/components/modal/AddColumn.tsx +++ b/src/components/modal/AddColumn.tsx @@ -1,13 +1,13 @@ import { Component } from 'solid-js'; import Bell from 'heroicons/24/outline/bell.svg'; -import BookmarkIcon from 'heroicons/24/outline/bookmark.svg'; -import ChatBubbleLeftRight from 'heroicons/24/outline/chat-bubble-left-right.svg'; import GlobeAlt from 'heroicons/24/outline/globe-alt.svg'; import Heart from 'heroicons/24/outline/heart.svg'; import Home from 'heroicons/24/outline/home.svg'; import MagnifyingGlass from 'heroicons/24/outline/magnifying-glass.svg'; import User from 'heroicons/24/outline/user.svg'; +// import BookmarkIcon from 'heroicons/24/outline/bookmark.svg'; +// import ChatBubbleLeftRight from 'heroicons/24/outline/chat-bubble-left-right.svg'; import BasicModal from '@/components/modal/BasicModal'; import { diff --git a/src/components/modal/EventDebugModal.tsx b/src/components/modal/EventDebugModal.tsx index e6feb51..8819e10 100644 --- a/src/components/modal/EventDebugModal.tsx +++ b/src/components/modal/EventDebugModal.tsx @@ -1,4 +1,4 @@ -import { Component, For, createMemo } from 'solid-js'; +import { Component, createMemo } from 'solid-js'; import { type Event as NostrEvent } from 'nostr-tools'; diff --git a/src/components/modal/ProfileDisplay.tsx b/src/components/modal/ProfileDisplay.tsx index a5cbd75..25b5f65 100644 --- a/src/components/modal/ProfileDisplay.tsx +++ b/src/components/modal/ProfileDisplay.tsx @@ -25,7 +25,6 @@ import useVerification from '@/nostr/useVerification'; import ensureNonNull from '@/utils/ensureNonNull'; import epoch from '@/utils/epoch'; import npubEncodeFallback from '@/utils/npubEncodeFallback'; -import stripMargin from '@/utils/stripMargin'; import timeout from '@/utils/timeout'; export type ProfileDisplayProps = { @@ -83,7 +82,6 @@ const ProfileDisplay: Component = (props) => { })), ); const following = () => myFollowingPubkeys().includes(props.pubkey); - const refetchMyFollowing = () => myFollowingQuery.refetch(); const { followingPubkeys: userFollowingPubkeys, query: userFollowingQuery } = useFollowings( () => ({ pubkey: props.pubkey }), diff --git a/src/components/timeline/Notification.tsx b/src/components/timeline/Notification.tsx index b3bfbb7..41bd381 100644 --- a/src/components/timeline/Notification.tsx +++ b/src/components/timeline/Notification.tsx @@ -6,7 +6,6 @@ import ColumnItem from '@/components/ColumnItem'; import Reaction from '@/components/event/Reaction'; import Repost from '@/components/event/Repost'; import TextNote from '@/components/event/TextNote'; -import ZapReceipt from '@/components/event/ZapReceipt'; import useConfig from '@/core/useConfig'; export type NotificationProps = { @@ -21,29 +20,22 @@ const Notification: Component = (props) => { {(event) => ( unknown event}> - + - + {/* TODO ちゃんとnotification用のコンポーネント使う */} - + - {/* - - - - - - */} )} diff --git a/src/components/utils/Copy.tsx b/src/components/utils/Copy.tsx index d76aa8f..119517b 100644 --- a/src/components/utils/Copy.tsx +++ b/src/components/utils/Copy.tsx @@ -1,4 +1,4 @@ -import { createSignal, Show, type Component, type JSX } from 'solid-js'; +import { createSignal, Show, type Component } from 'solid-js'; import ClipboardDocument from 'heroicons/24/outline/clipboard-document.svg'; @@ -13,7 +13,7 @@ const Copy: Component = (props) => { const handleClick = () => { navigator.clipboard .writeText(props.text) - .then((e) => { + .then(() => { setShowPopup(true); setTimeout(() => setShowPopup(false), 1000); }) diff --git a/src/core/useConfig.ts b/src/core/useConfig.ts index ec8b040..c881e60 100644 --- a/src/core/useConfig.ts +++ b/src/core/useConfig.ts @@ -181,7 +181,7 @@ const useConfig = (): UseConfig => { const isPubkeyMuted = (pubkey: string) => config.mutedPubkeys.includes(pubkey); const hasMutedKeyword = (event: NostrEvent) => { - if (event.kind === Kind.Text) { + if (event.kind === (Kind.Text as number)) { return config.mutedKeywords.some((keyword) => event.content.includes(keyword)); } return false; @@ -192,7 +192,7 @@ const useConfig = (): UseConfig => { return ( isPubkeyMuted(event.pubkey) || ev.taggedPubkeys().some(isPubkeyMuted) || - (event.kind === Kind.Text && hasMutedKeyword(event)) + (event.kind === (Kind.Text as number) && hasMutedKeyword(event)) ); }; diff --git a/src/hooks/useFileInput.ts b/src/hooks/useFileInput.ts deleted file mode 100644 index 1e6ee6a..0000000 --- a/src/hooks/useFileInput.ts +++ /dev/null @@ -1,11 +0,0 @@ -import { createSignal, type JSX } from 'solid-js'; - -const useFileInput = () => { - const [file, setFile] = createSignal(); - - const handleChange: JSX.EventHandler = (ev) => { - setFile(ev.currentTarget.files?.[0]); - }; - - return { file, handleChange }; -}; diff --git a/src/hooks/useMessageBus.ts b/src/hooks/useMessageBus.ts index 9a08004..9491167 100644 --- a/src/hooks/useMessageBus.ts +++ b/src/hooks/useMessageBus.ts @@ -16,6 +16,7 @@ export type MessageChannelRequest = { export type MessageChannelResponse = | { requestId: string; ok: true; response: T } + // eslint-disable-next-line @typescript-eslint/no-explicit-any | { requestId: string; ok: false; error: any }; const [channels, setChannels]: Signal> = createSignal({}); diff --git a/src/hooks/useResizedImage.ts b/src/hooks/useResizedImage.ts index dc32cf5..fc6260b 100644 --- a/src/hooks/useResizedImage.ts +++ b/src/hooks/useResizedImage.ts @@ -5,14 +5,14 @@ export type UseResizedImageProps = { imageUrl: Accessor; width: number; height: number; - encoderOption?: number; + encoderOptions?: number; }; const useResizedImage = ({ imageUrl, width, height, - encoderOption, + encoderOptions, }: UseResizedImageProps): Accessor => { const [resizedImage, setResizedImage] = createSignal(undefined); @@ -39,7 +39,7 @@ const useResizedImage = ({ ctx.drawImage(img, 0, 0, img.width, img.height, 0, 0, dw, dh); - const dataUrl = canvas.toDataURL('image/jpeg'); + const dataUrl = canvas.toDataURL('image/jpeg', encoderOptions); setResizedImage(dataUrl); }); diff --git a/src/hooks/useShortcutKeys.ts b/src/hooks/useShortcutKeys.ts index a78645f..053fff9 100644 --- a/src/hooks/useShortcutKeys.ts +++ b/src/hooks/useShortcutKeys.ts @@ -1,7 +1,4 @@ -// const commands = ['openPostForm'] as const; -// type Commands = (typeof commands)[number]; - -import { onMount, onCleanup, type JSX } from 'solid-js'; +import { onMount, onCleanup } from 'solid-js'; import throttle from 'lodash/throttle'; diff --git a/src/nostr/event.ts b/src/nostr/event.ts index e3a529a..4ba64dd 100644 --- a/src/nostr/event.ts +++ b/src/nostr/event.ts @@ -1,4 +1,4 @@ -import { Kind, Event as NostrEvent } from 'nostr-tools'; +import { Event as NostrEvent } from 'nostr-tools'; import GenericEvent from '@/nostr/event/GenericEvent'; import Reaction from '@/nostr/event/Reaction'; diff --git a/src/nostr/event/LongFormContent.ts b/src/nostr/event/LongFormContent.ts deleted file mode 100644 index 5e0cc67..0000000 --- a/src/nostr/event/LongFormContent.ts +++ /dev/null @@ -1,44 +0,0 @@ -import { Event as NostrEvent, Kind } from 'nostr-tools'; - -import GenericEvent from '@/nostr/event/GenericEvent'; - -class LongFormContent extends GenericEvent { - constructor(rawEvent: NostrEvent) { - if (rawEvent.kind !== Kind.Article) { - throw new TypeError('kind should be 30023'); - } - super(rawEvent); - } - - #getMeta(tagName: string): string | null { - const tags = this.findTagsByName(tagName); - if (tags.length === 0) return null; - const [, value] = tags[0]; - return value; - } - - title(): string | null { - return this.#getMeta('title'); - } - - image(): string | null { - return this.#getMeta('image'); - } - - summary(): string | null { - return this.#getMeta('image'); - } - - publishedAt(): string | null { - return this.#getMeta('publishedAt'); - } - - publishedAtAsDate(): Date | null { - const publishedAt = this.publishedAt(); - if (publishedAt == null) return null; - - return new Date(parseInt(publishedAt, 10) * 1000); - } -} - -export default LongFormContent; diff --git a/src/nostr/event/Profile.ts b/src/nostr/event/Profile.ts index 59ed361..139f96e 100644 --- a/src/nostr/event/Profile.ts +++ b/src/nostr/event/Profile.ts @@ -19,6 +19,7 @@ export type NonStandardProfile = { export type Profile = StandardProfile & NonStandardProfile; +// eslint-disable-next-line @typescript-eslint/no-explicit-any export type ProfileWithOtherProperties = Profile & Record; export const parseProfile = (content: string | null): Profile => { diff --git a/src/nostr/event/Reaction.ts b/src/nostr/event/Reaction.ts index 6b3315e..5a6bda3 100644 --- a/src/nostr/event/Reaction.ts +++ b/src/nostr/event/Reaction.ts @@ -30,7 +30,7 @@ const reactionToReactionTypes = (event: Reaction): ReactionTypes => { export default class Reaction extends GenericEvent { constructor(rawEvent: NostrEvent) { - if (rawEvent.kind !== Kind.Reaction) { + if (rawEvent.kind !== (Kind.Reaction as number)) { throw new TypeError('kind should be 7'); } super(rawEvent); diff --git a/src/nostr/event/TextNote.ts b/src/nostr/event/TextNote.ts index 95f0b90..3e91faf 100644 --- a/src/nostr/event/TextNote.ts +++ b/src/nostr/event/TextNote.ts @@ -1,5 +1,4 @@ import { Event as NostrEvent, Kind } from 'nostr-tools'; -import { z } from 'zod'; import GenericEvent from '@/nostr/event/GenericEvent'; import isValidId from '@/nostr/event/isValidId'; @@ -9,7 +8,6 @@ import parseTextNote, { ParsedTextNote, TagReference, } from '@/nostr/parseTextNote'; -import ensureSchema from '@/utils/ensureSchema'; export type EventMarker = 'reply' | 'root' | 'mention'; @@ -69,7 +67,7 @@ export default class TextNote extends GenericEvent { #memoizedParsed: ParsedTextNote | undefined; constructor(rawEvent: NostrEvent) { - if (rawEvent.kind !== Kind.Text) { + if (rawEvent.kind !== (Kind.Text as number)) { throw new TypeError('kind should be 1'); } super(rawEvent); diff --git a/src/nostr/parseTextNote.test.ts b/src/nostr/parseTextNote.test.ts index a66428b..757ed2a 100644 --- a/src/nostr/parseTextNote.test.ts +++ b/src/nostr/parseTextNote.test.ts @@ -1,9 +1,8 @@ import assert from 'assert'; -import { type Event as NostrEvent } from 'nostr-tools'; import { describe, it } from 'vitest'; -import parseTextNote, { type ParsedTextNoteNode, TagReference } from '@/nostr/parseTextNote'; +import parseTextNote, { type ParsedTextNoteNode } from '@/nostr/parseTextNote'; describe('parseTextNote', () => { /* diff --git a/src/nostr/parseTextNote.ts b/src/nostr/parseTextNote.ts index a7d342b..1661036 100644 --- a/src/nostr/parseTextNote.ts +++ b/src/nostr/parseTextNote.ts @@ -1,4 +1,4 @@ -import { nip19, type Event as NostrEvent } from 'nostr-tools'; +import { nip19 } from 'nostr-tools'; import { DecodeResult } from 'nostr-tools/lib/nip19'; const { decode } = nip19; diff --git a/src/nostr/useBatchedEvents.ts b/src/nostr/useBatchedEvents.ts index 4bdb5d0..a9b70de 100644 --- a/src/nostr/useBatchedEvents.ts +++ b/src/nostr/useBatchedEvents.ts @@ -162,33 +162,33 @@ const { addTask, removeTask } = useBatch(() => ({ count += 1; sub.on('event', (event: NostrEvent & { id: string }) => { - if (event.kind === Kind.Metadata) { + if (event.kind === (Kind.Metadata as number)) { const registeredTasks = profileTasks.get(event.pubkey) ?? []; resolveTasks(registeredTasks, event); return; } - if (event.kind === Kind.Reaction) { + if (event.kind === (Kind.Reaction as number)) { // Use the last event id const id = genericEvent(event).lastTaggedEventId(); if (id != null) { const registeredTasks = reactionsTasks.get(id) ?? []; resolveTasks(registeredTasks, event); } - } else if ((event.kind as number) === 6) { + } else if (event.kind === (Kind.Repost as number)) { // Use the last event id const id = genericEvent(event).lastTaggedEventId(); if (id != null) { const registeredTasks = repostsTasks.get(id) ?? []; resolveTasks(registeredTasks, event); } - } else if (event.kind === Kind.Zap) { + } else if (event.kind === (Kind.Zap as number)) { const eTags = genericEvent(event).eTags(); eTags.forEach(([, id]) => { const registeredTasks = repostsTasks.get(id) ?? []; resolveTasks(registeredTasks, event); }); - } else if (event.kind === Kind.Contacts) { + } else if (event.kind === (Kind.Contacts as number)) { const registeredTasks = followingsTasks.get(event.pubkey) ?? []; resolveTasks(registeredTasks, event); } else if (isParameterizedReplaceableEvent(event)) { diff --git a/src/nostr/useDecrypt.ts b/src/nostr/useDecrypt.ts index 9e8f546..838c617 100644 --- a/src/nostr/useDecrypt.ts +++ b/src/nostr/useDecrypt.ts @@ -6,7 +6,9 @@ type UseDecryptProps = { encrypted: string; }; +// eslint-disable-next-line solid/reactivity const [memo, setMemo] = createRoot(() => createSignal>({})); +// eslint-disable-next-line solid/reactivity const [decrypting, setDecrypting] = createRoot(() => createSignal>({})); const useDecrypt = (propsProvider: () => UseDecryptProps | null) => { diff --git a/src/nostr/useEvent.ts b/src/nostr/useEvent.ts index dcfc909..9f88ff1 100644 --- a/src/nostr/useEvent.ts +++ b/src/nostr/useEvent.ts @@ -1,6 +1,6 @@ import { createMemo } from 'solid-js'; -import { createQuery, useQueryClient, type CreateQueryResult } from '@tanstack/solid-query'; +import { createQuery, type CreateQueryResult } from '@tanstack/solid-query'; import { Event as NostrEvent } from 'nostr-tools'; import { registerTask, BatchedEventsTask } from '@/nostr/useBatchedEvents'; diff --git a/src/nostr/useParameterizedReplaceableEvent.ts b/src/nostr/useParameterizedReplaceableEvent.ts index beba3f1..416146d 100644 --- a/src/nostr/useParameterizedReplaceableEvent.ts +++ b/src/nostr/useParameterizedReplaceableEvent.ts @@ -1,4 +1,4 @@ -import { createMemo, observable } from 'solid-js'; +import { createMemo } from 'solid-js'; import { createQuery, useQueryClient, type CreateQueryResult } from '@tanstack/solid-query'; import { Event as NostrEvent } from 'nostr-tools'; diff --git a/src/nostr/useVerification.ts b/src/nostr/useVerification.ts index cdeb9c6..6ab3a04 100644 --- a/src/nostr/useVerification.ts +++ b/src/nostr/useVerification.ts @@ -16,7 +16,7 @@ const useVerification = (propsProvider: () => UseVerificationProps | null): UseV const props = createMemo(propsProvider); const query = createQuery( () => ['useVerification', props()] as const, - ({ queryKey, signal }) => { + ({ queryKey }) => { const [, currentProps] = queryKey; if (currentProps == null) return Promise.resolve(null); const { nip05: nip05string } = currentProps; diff --git a/src/pages/Home.tsx b/src/pages/Home.tsx index 7719c4d..5ab3cd1 100644 --- a/src/pages/Home.tsx +++ b/src/pages/Home.tsx @@ -6,7 +6,6 @@ import Columns from '@/components/column/Columns'; import GlobalModal from '@/components/modal/GlobalModal'; import SideBar from '@/components/SideBar'; import useConfig from '@/core/useConfig'; -import useModalState from '@/hooks/useModalState'; import usePersistStatus from '@/hooks/usePersistStatus'; import { useMountShortcutKeys } from '@/hooks/useShortcutKeys'; import usePool from '@/nostr/usePool'; diff --git a/src/utils/ensureNonNull.ts b/src/utils/ensureNonNull.ts index 460afe0..dd06d7a 100644 --- a/src/utils/ensureNonNull.ts +++ b/src/utils/ensureNonNull.ts @@ -1,18 +1,15 @@ -// eslint-disable-next-line @typescript-eslint/no-explicit-any +/* eslint-disable @typescript-eslint/no-explicit-any */ export type TupleNonNull = { [P in keyof T]: NonNullable; }; const ensureNonNull = - // eslint-disable-next-line @typescript-eslint/no-explicit-any - - - (tuple: T) => - (f: (tupleNonNull: TupleNonNull) => R): R | null => { - if (tuple.some((e) => e == null)) { - return null; - } - return f(tuple as TupleNonNull); - }; + (tuple: T) => + (f: (tupleNonNull: TupleNonNull) => R): R | null => { + if (tuple.some((e) => e == null)) { + return null; + } + return f(tuple as TupleNonNull); + }; export default ensureNonNull; diff --git a/src/utils/ensureSchema.ts b/src/utils/ensureSchema.ts index ba2d20a..8827953 100644 --- a/src/utils/ensureSchema.ts +++ b/src/utils/ensureSchema.ts @@ -2,6 +2,7 @@ import { z } from 'zod'; const ensureSchema = (schema: z.Schema) => + // eslint-disable-next-line @typescript-eslint/no-explicit-any (value: any): value is T => schema.safeParse(value).success; diff --git a/src/utils/imageUpload.ts b/src/utils/imageUpload.ts index 87d2520..8673e68 100644 --- a/src/utils/imageUpload.ts +++ b/src/utils/imageUpload.ts @@ -36,17 +36,6 @@ export type NostrBuildResult = { }[]; }; -const toHexString = (buff: ArrayBuffer): string => { - const arr = new Array(buff.byteLength); - const view = new Int8Array(buff); - - for (let i = 0; i < view.byteLength; i += 1) { - arr[i] = view[i].toString(16).padStart(2, '0'); - } - - return arr.join(); -}; - export const uploadNostrBuild = async (blob: Blob): Promise => { const form = new FormData(); form.set('file', blob); @@ -69,27 +58,6 @@ export const uploadNostrBuild = async (blob: Blob): Promise => { return { imageUrl: result.data[0].url }; }; -export const uploadVoidCat = async (blob: Blob): Promise => { - const data = await blob.arrayBuffer(); - const digestBuffer = await window.crypto.subtle.digest('SHA-256', data); - const digest = toHexString(digestBuffer); - - const res = await fetch('https://void.cat/upload', { - method: 'POST', - headers: { - Accept: 'application/json', - 'V-Content-Type': blob.type, - 'V-Full-Digest': digest, - }, - mode: 'cors', - body: data, - }); - - if (!res.ok) throw new Error('failed to post image: status code was not 2xx'); - - return res.json(); -}; - export const uploaders = { nostrBuild: { name: 'nostr.build', diff --git a/src/utils/stripMargin.ts b/src/utils/stripMargin.ts index 5f54dd9..ab781e1 100644 --- a/src/utils/stripMargin.ts +++ b/src/utils/stripMargin.ts @@ -1,3 +1,4 @@ +// eslint-disable-next-line @typescript-eslint/no-explicit-any const stripMargin = (strings: TemplateStringsArray, ...values: any[]) => { const s = String.raw(strings, values); diff --git a/tsconfig.json b/tsconfig.json index f651c6b..916f13c 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -5,11 +5,7 @@ "module": "ESNext", "moduleResolution": "node", "resolveJsonModule": true, - "lib": [ - "dom", - "dom.iterable", - "esnext" - ], + "lib": ["dom", "dom.iterable", "esnext"], "allowSyntheticDefaultImports": true, "forceConsistentCasingInFileNames": true, "esModuleInterop": true, @@ -20,19 +16,10 @@ "isolatedModules": true, "baseUrl": ".", "paths": { - "@/*": ["src/*"], + "@/*": ["src/*"] }, "incremental": true }, - "include": [ - "vite.config.ts", - "**/*.ts", - "**/*.tsx", - "**/*.js", - "**/*.jsx", - "./.eslintrc.js" - ], - "exclude": [ - "node_modules" - ] + "include": ["vite.config.ts", "**/*.ts", "**/*.tsx", "**/*.js", "**/*.jsx", "./.eslintrc.js"], + "exclude": ["node_modules"] }