diff --git a/.env.example b/.env.example index 9b0ba49ac3..db9ca41195 100644 --- a/.env.example +++ b/.env.example @@ -8,7 +8,7 @@ NUXT_CLOUDFLARE_ACCOUNT_ID= NUXT_CLOUDFLARE_NAMESPACE_ID= NUXT_CLOUDFLARE_API_TOKEN= -# 'cloudflare' | 'fs' +# 'cloudflare' | 'vercel' | 'fs' NUXT_STORAGE_DRIVER= NUXT_STORAGE_FS_BASE= diff --git a/.github/workflows/docker.yml b/.github/workflows/docker.yml index dfb53d373c..601ec79f10 100644 --- a/.github/workflows/docker.yml +++ b/.github/workflows/docker.yml @@ -17,17 +17,17 @@ jobs: uses: actions/checkout@v4 - name: Docker meta id: metal - uses: docker/metadata-action@v4 + uses: docker/metadata-action@v5 with: images: | ghcr.io/${{ github.repository }} - name: Set up QEMU - uses: docker/setup-qemu-action@v2 + uses: docker/setup-qemu-action@v3 - name: Set up Docker Buildx - uses: docker/setup-buildx-action@v2 + uses: docker/setup-buildx-action@v3 - name: Login to GitHub Container Registry if: github.event_name != 'pull_request' - uses: docker/login-action@v2 + uses: docker/login-action@v3 with: registry: ghcr.io username: ${{ github.actor }} diff --git a/.vscode/settings.json b/.vscode/settings.json index 4b6c677a74..beffb480fe 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -6,7 +6,7 @@ "unstorage" ], "editor.codeActionsOnSave": { - "source.fixAll.eslint": true + "source.fixAll.eslint": "explicit" }, "editor.formatOnSave": false, "files.associations": { diff --git a/README.md b/README.md index 4e36aadd9d..5076d2ae81 100644 --- a/README.md +++ b/README.md @@ -28,7 +28,42 @@ If you want to contribute to the parent project, check out [its repo](https://gi The crab team maintains a deployment at: -- 🦀 Production: [elk.bumscode.com](https://elk.bumscode.com) +- 🦀 Production: [crab.bumscode.com](https://crab.bumscode.com) + +### Self-Host Docker Deployment + +In order to host Elk yourself you can use the provided Dockerfile to build a container with elk. Be aware, that Elk only loads properly if the connection is done via SSL/TLS. The Docker container itself does not provide any SSL/TLS handling. You'll have to add this bit yourself. +One could put Elk behind popular reverse proxies with SSL Handling like Traefik, NGINX etc. + +1. checkout source ```git clone https://github.com/elk-zone/elk.git``` +1. got into new source dir: ```cd elk``` +1. build Docker image: ```docker build .``` +1. create local storage directory for settings: ```mkdir elk-storage``` +1. adjust permissions of storage dir: ```sudo chown 911:911 ./elk-storage``` +1. start container: ```docker-compose up -d``` + +> [!NOTE] +> The provided Dockerfile creates a container which will eventually run Elk as non-root user and create a persistent named Docker volume upon first start (if that volume does not yet exist). This volume is always created with root permission. Failing to change the permissions of ```/elk/data``` inside this volume to UID:GID 911 (as specified for Elk in the Dockerfile) will prevent Elk from storing it's config for user accounts. You either have to fix the permission in the created named volume, or mount a directory with the correct permission to ```/elk/data``` into the container. + + +### Ecosystem + +These are known deployments using Elk as an alternative Web client for Mastodon servers or as a base for other projects in the fediverse: + +- [elk.fedified.com](https://elk.fedified.com) - Use Elk to log into any compatible instance +- [elk.me.uk](https://elk.me.uk) - Use Elk to log into any compatible instance, hosted on Google Cloud Run with no Cloudflare proxy +- [elk.h4.io](https://elk.h4.io) - Use Elk for the `h4.io` Server +- [elk.universeodon.com](https://elk.universeodon.com) - Use Elk for the Universeodon Server +- [elk.vmst.io](https://elk.vmst.io) - Use Elk for the `vmst.io` Server +- [elk.hostux.social](https://elk.hostux.social) - Use Elk for the `hostux.social` Server +- [elk.cupoftea.social](https://elk.cupoftea.social) - Use Elk for the `cupoftea.social` Server +- [elk.aus.social](https://elk.aus.social) - Use Elk for the `aus.social` Server +- [elk.mstdn.ca](https://elk.mstdn.ca) - Use Elk for the `mstdn.ca` Server +- [elk.mastodonapp.uk](https://elk.mastodonapp.uk) - Use Elk for the `mastodonapp.uk` Server +- [elk.bolha.us](https://elk.bolha.us) - Use Elk for the `bolha.us` Server + +> **Note**: Community deployments are **NOT** maintained by the Elk team. It may not be synced with Elk's source code. Please do your own research about the host servers before using them. + ## 💖 Sponsors diff --git a/app.vue b/app.vue index 3ce0a9516e..89c1fa0e4d 100644 --- a/app.vue +++ b/app.vue @@ -5,9 +5,11 @@ provideGlobalCommands() const route = useRoute() if (process.server && !route.path.startsWith('/settings')) { + const url = useRequestURL() + useHead({ meta: [ - { property: 'og:url', content: `https://elk.zone${route.path}` }, + { property: 'og:url', content: `${url.origin}${route.path}` }, ], }) } diff --git a/components/account/AccountFollowButton.vue b/components/account/AccountFollowButton.vue index bb7cc240d4..36916a7d56 100644 --- a/components/account/AccountFollowButton.vue +++ b/components/account/AccountFollowButton.vue @@ -19,7 +19,7 @@ const { client } = $(useMasto()) async function unblock() { relationship!.blocking = false try { - const newRel = await client.v1.accounts.unblock(account.id) + const newRel = await client.v1.accounts.$select(account.id).unblock() Object.assign(relationship!, newRel) } catch (err) { @@ -32,7 +32,7 @@ async function unblock() { async function unmute() { relationship!.muting = false try { - const newRel = await client.v1.accounts.unmute(account.id) + const newRel = await client.v1.accounts.$select(account.id).unmute() Object.assign(relationship!, newRel) } catch (err) { diff --git a/components/account/AccountFollowRequestButton.vue b/components/account/AccountFollowRequestButton.vue index 61cab91839..2c60a76084 100644 --- a/components/account/AccountFollowRequestButton.vue +++ b/components/account/AccountFollowRequestButton.vue @@ -12,7 +12,7 @@ async function authorizeFollowRequest() { relationship!.requestedBy = false relationship!.followedBy = true try { - const newRel = await client.v1.followRequests.authorize(account.id) + const newRel = await client.v1.followRequests.$select(account.id).authorize() Object.assign(relationship!, newRel) } catch (err) { @@ -25,7 +25,7 @@ async function authorizeFollowRequest() { async function rejectFollowRequest() { relationship!.requestedBy = false try { - const newRel = await client.v1.followRequests.reject(account.id) + const newRel = await client.v1.followRequests.$select(account.id).reject() Object.assign(relationship!, newRel) } catch (err) { diff --git a/components/account/AccountHeader.vue b/components/account/AccountHeader.vue index 85d2cfe5f1..c97cf369ba 100644 --- a/components/account/AccountHeader.vue +++ b/components/account/AccountHeader.vue @@ -53,7 +53,7 @@ function previewAvatar() { async function toggleNotifications() { relationship!.notifying = !relationship?.notifying try { - const newRel = await client.v1.accounts.follow(account.id, { notify: relationship?.notifying }) + const newRel = await client.v1.accounts.$select(account.id).follow({ notify: relationship?.notifying }) Object.assign(relationship!, newRel) } catch { @@ -97,7 +97,7 @@ async function editNote(event: Event) { if (relationship.note?.trim() === newNote.trim()) return - const newNoteApiResult = await client.v1.accounts.createNote(account.id, { comment: newNote }) + const newNoteApiResult = await client.v1.accounts.$select(account.id).note.create({ comment: newNote }) relationship.note = newNoteApiResult.note personalNoteDraft.value = relationship.note ?? '' } diff --git a/components/account/AccountLockIndicator.vue b/components/account/AccountLockIndicator.vue index 7384be535e..4d6cb26325 100644 --- a/components/account/AccountLockIndicator.vue +++ b/components/account/AccountLockIndicator.vue @@ -2,6 +2,8 @@ defineProps<{ showLabel?: boolean }>() + +const { t } = useI18n() diff --git a/components/account/AccountMoreButton.vue b/components/account/AccountMoreButton.vue index 5c524e9a52..eb78d16e3d 100644 --- a/components/account/AccountMoreButton.vue +++ b/components/account/AccountMoreButton.vue @@ -26,14 +26,15 @@ function shareAccount() { async function toggleReblogs() { if (!relationship!.showingReblogs && await openConfirmDialog({ - title: t('confirm.show_reblogs.title', [account.acct]), + title: t('confirm.show_reblogs.title'), + description: t('confirm.show_reblogs.description', [account.acct]), confirm: t('confirm.show_reblogs.confirm'), cancel: t('confirm.show_reblogs.cancel'), }) !== 'confirm') return const showingReblogs = !relationship?.showingReblogs - relationship = await client.v1.accounts.follow(account.id, { reblogs: showingReblogs }) + relationship = await client.v1.accounts.$select(account.id).follow({ reblogs: showingReblogs }) } async function addUserNote() { @@ -44,7 +45,7 @@ async function removeUserNote() { if (!relationship!.note || relationship!.note.length === 0) return - const newNote = await client.v1.accounts.createNote(account.id, { comment: '' }) + const newNote = await client.v1.accounts.$select(account.id).note.create({ comment: '' }) relationship!.note = newNote.note emit('removeNote') } diff --git a/components/account/AccountPaginator.vue b/components/account/AccountPaginator.vue index 86bcccb89d..0445439d12 100644 --- a/components/account/AccountPaginator.vue +++ b/components/account/AccountPaginator.vue @@ -1,8 +1,8 @@ diff --git a/components/timeline/TimelineDomainBlocks.vue b/components/timeline/TimelineDomainBlocks.vue index 0763e8ec19..a4dfcf205f 100644 --- a/components/timeline/TimelineDomainBlocks.vue +++ b/components/timeline/TimelineDomainBlocks.vue @@ -3,7 +3,7 @@ const { client } = $(useMasto()) const paginator = client.v1.domainBlocks.list() async function unblock(domain: string) { - await client.v1.domainBlocks.unblock(domain) + await client.v1.domainBlocks.remove({ domain }) } diff --git a/components/timeline/TimelineHome.vue b/components/timeline/TimelineHome.vue index 957937948c..905335d347 100644 --- a/components/timeline/TimelineHome.vue +++ b/components/timeline/TimelineHome.vue @@ -1,8 +1,8 @@