Commit Graph

1252 Commits

Author SHA1 Message Date
kolaente dd0b82f00a fix(task): use DOMParser in task glance tooltip description preview
Replace innerHTML on a detached element with DOMParser for extracting
plain text from task descriptions.
2026-02-09 11:01:38 +01:00
Frederick [Bot] 3c2977b126 chore(i18n): update translations via Crowdin 2026-02-09 01:16:51 +00:00
kolaente e90cb2631d fix(auth): remove unnecessary fields from JWT token payloads
Remove email, name, emailRemindersEnabled, and isLocalUser from user JWT
claims, and isLocalUser from link share JWT claims. These fields are never
used from the token - the backend always fetches the full user from the
database by ID, and the frontend fetches user data from the /user API
endpoint immediately after login.

Also simplify GetUserFromClaims to only extract id and username, and
remove the now-unnecessary email override in the frontend's
refreshUserInfo.
2026-02-08 21:30:07 +01:00
kolaente eb369cf3ee fix: handle attachment upload errors with user-visible notifications 2026-02-08 15:48:04 +01:00
kolaente 7256a14194 fix: format attachment upload error messages as readable strings 2026-02-08 15:48:04 +01:00
kolaente cdca790325 fix: guard against undefined route.name in auth layout check
route.name can be undefined during initial route resolution or for
unnamed routes. Without this guard, AUTH_ROUTE_NAMES.has() would
return false and the authenticated layout could flash briefly.
2026-02-06 10:58:50 +01:00
kolaente e9a6abfe44 refactor: extract auth route names into shared constant
Move the list of authentication route names (login, register, password
reset, openid, link-share) into a shared constant in
src/constants/authRouteNames.ts. Use it in both App.vue (layout gate)
and router/index.ts (auth redirect guard) to keep them in sync.
2026-02-06 10:58:50 +01:00
kolaente 5d9f62cc93 fix: prevent auth layout swap while still on login/register route
The v-if in App.vue switches to the authenticated layout (navbar +
sidebar) as soon as authStore.authUser becomes truthy. But Vue's
reactivity flush runs before the await continuation in submit(), so
the layout swaps while the route is still /login, causing the login
form to flash inside the authenticated shell for ~250ms.

Fix by adding a route check: don't show the authenticated layout while
the current route is an auth page (login, register, password reset,
openid). The NoAuthWrapper stays visible until redirectIfSaved()
navigates away, then the authenticated layout renders cleanly.
2026-02-06 10:58:50 +01:00
kolaente 0e2ea5c42a fix: avoid clearing saved redirect in onBeforeMount to prevent race with submit
When Login.vue re-mounts inside the authenticated layout after a
successful login, its onBeforeMount hook fires again. If it calls
redirectIfSaved(), it clears the saved route from localStorage before
the submit() handler's redirectIfSaved() can use it, causing a redirect
to home instead of the saved route. Use router.push({name: 'home'})
directly since the only purpose here is to redirect already-authenticated
users away from the login page.
2026-02-06 10:58:50 +01:00
kolaente dcff454755 fix: redirect immediately after registration to prevent form flash in app shell 2026-02-06 10:58:50 +01:00
kolaente 8bccf21a81 fix: redirect immediately after login to prevent form flash in app shell 2026-02-06 10:58:50 +01:00
kolaente 77b8403c24 fix: iterate past rejected middle matches in matchDateAtBoundary()
When the first regex match is a rejected middle-of-text date, continue
searching for subsequent matches instead of returning null. This fixes
cases like "The 9/11 Report due 10/12" where 9/11 is rejected but
10/12 at the end should still be parsed.
2026-02-06 10:57:50 +01:00
kolaente 3f0bf71d30 fix: allow middle-of-text dates when followed by time expressions (#2195)
Reworked matchDateAtBoundary() to use a single regex pass instead of
two-pass start/end anchoring. Middle-of-text matches are now accepted
when followed by a time expression (at/@ prefix), so inputs like
"meeting 9/11 at 10:00" still parse correctly while "The 9/11 Report"
is rejected.
2026-02-06 10:57:50 +01:00
kolaente cee258edc3 refactor: remove unnecessary comment from getDateFromText() 2026-02-06 10:57:50 +01:00
kolaente 61448bb028 refactor: remove unnecessary flags parameter from matchDateAtBoundary() 2026-02-06 10:57:50 +01:00
kolaente c544886524 test: add positive boundary tests for date parsing (#2195) 2026-02-06 10:57:50 +01:00
kolaente 829b10bfd2 test: add dot-separated middle-of-text date false positive test (#2195) 2026-02-06 10:57:50 +01:00
kolaente a82efa01b5 fix: restrict numeric date regex matching to text boundaries (#2195) 2026-02-06 10:57:50 +01:00
kolaente 1013305fc6 feat: add matchDateAtBoundary() helper for position-aware date matching (#2195) 2026-02-06 10:57:50 +01:00
kolaente e9b10e67f3 test: add failing tests for middle-of-text date false positives (#2195) 2026-02-06 10:57:50 +01:00
kolaente b741c2d891 fix: add touch CSS properties to list view for mobile drag-and-drop
Adds user-select, touch-action, and webkit-touch-callout CSS to the list
view's draggable task items, matching what KanbanCard.vue already has.

Without these properties, the browser's native long-press text selection
fires before SortableJS's 1-second touch delay expires, preventing drag
from ever starting on mobile devices.

Ref: https://community.vikunja.io/t/missing-positioning-option-in-list-view/4278
2026-02-05 23:51:38 +01:00
Frederick [Bot] 1ddb4f1438 chore(i18n): update translations via Crowdin 2026-02-03 01:15:10 +00:00
Frederick [Bot] 2becfcc597 chore(i18n): update translations via Crowdin 2026-01-31 01:08:04 +00:00
rhclayto cf029cef0c
feat: add option to send Basic Auth header with webhook requests (#2137)
Resolves https://github.com/go-vikunja/vikunja/issues/2136
Docs PR: https://github.com/go-vikunja/website/pull/284
2026-01-30 15:07:31 +01:00
Frederick [Bot] f7503c0bfe chore(i18n): update translations via Crowdin 2026-01-29 01:11:11 +00:00
kolaente e4b99dd31f
fix(nav): show shared sub-projects in sidebar when the parent is inaccessible (#2176)
Fixes #2175
2026-01-28 16:09:46 +00:00
kolaente e5da54e58a fix(editor): prevent crash when exiting edit mode in tiptap
Use v-show instead of v-if for EditorToolbar and BubbleMenu to avoid
a race condition between Vue's DOM reconciliation and tiptap's internal
DOM manipulation during unmount. This fixes the "Cannot read properties
of null (reading 'insertBefore')" error that occurred when saving a
task description.

Adds regression test to verify the fix.

Upstream issue: https://github.com/ueberdosis/tiptap/issues/7342
Fixes: https://github.com/go-vikunja/vikunja/issues/1770
2026-01-27 14:03:02 +01:00
renovate[bot] 662f3a1ea8
chore(deps): update dev-dependencies (major) (#1375) 2026-01-25 21:54:47 +01:00
kolaente ff01f8e859
feat(api-tokens): support title and scopes query parameters (#2143)
This allows external integrations to link directly to the API token creation page with pre-selected title and permission scopes. URLs can now use `?title=Name&scopes=group:perm,group:perm` format to pre-populate the form.

Example URL:
```
/user/settings/api-tokens?title=My%20Integration&scopes=tasks:create,tasks:delete,projects:read_all
```
2026-01-24 18:08:23 +00:00
kolaente 1731b03c22
fix(editor): prevent file upload overlay when dragging text from editor (#2148)
Fixes the file upload overlay incorrectly appearing when dragging text from within the TipTap description editor to outside of it.

Fixes #1663
2026-01-24 18:41:42 +01:00
kolaente acbb06e337
feat(frontend): preserve Gantt date range when switching views (#2141)
Adds a `viewFilters` Pinia store that stores query params per view ID to sync Gantt filters to the store whenever they change. This persists the custom date ranges when switching between views.

Fixes #2124
2026-01-24 13:12:35 +01:00
kolaente 131f78277d feat(quick add magic): add more test cases 2026-01-24 00:00:46 +01:00
kolaente 8419794b65
fix(quick-add-magic): prevent parsing partial keywords in words (#2140)
- Fixed date parser incorrectly extracting date components from within
words
- "Renovation - 2nd Floor Bath" no longer becomes "Reation - Floor Bath"
with a due date of November 2nd

## Changes
- `getMonthFromText` now requires word boundaries, preventing "nov" from
matching inside "Renovation" or "mar" inside "Remark"
- `getDayFromText` now only matches ordinals when followed by
end-of-string, time expressions, or month names, preventing "2nd Floor"
from being parsed as a date

Resolves
https://community.vikunja.io/t/quick-add-magic-unintended-date-parsing/4259
2026-01-23 22:23:42 +00:00
kolaente c11ea4c87f fix(unsplash): add utm parameters to author links
Resolves https://github.com/go-vikunja/vikunja/issues/2127
2026-01-23 11:58:34 +01:00
kolaente e96c20def9 fix(project): error `can't access property "isArchived", V.value is null` when opening list view of some projects 2026-01-14 22:05:35 +01:00
kolaente 948a73f3b9 fix(task): done button styling 2026-01-14 21:56:24 +01:00
kolaente e702785cf8
fix(filter): correct filter autocomplete for project names with spaces (#2012)
Filter expressions with multi-word values (such as project names with
spaces) are now automatically quoted to preserve them correctly as
single tokens in the filter syntax.

Fixes #2010

🐰 A filter's journey, refined with care,
Multi-word values now wear quotes fair,
Offsets aligned by the rabbit's precision,
Autocomplete flows with mathematical vision,
From comma to space, each boundary divine! 
2026-01-10 22:18:34 +01:00
kolaente c0ba7210f3 chore: remove redundant is-danger class 2026-01-10 21:59:06 +01:00
kolaente 4f9681bde8 chore(form): add autocomplete attributes to a few fields 2026-01-10 21:59:06 +01:00
kolaente a8f10a6e15 fix(register): explicitely check for username valid === true 2026-01-10 21:59:06 +01:00
kolaente edebed151a chore(team): add disabled prop to NewTeam checkbox 2026-01-10 21:59:06 +01:00
kolaente f06e272225 test(frontend): add test for @keyup.enter forwarding in FormField
Verify that @keyup.enter modifier is properly forwarded to the inner
input element and only triggers for Enter key, not other keys.
2026-01-10 21:59:06 +01:00
kolaente e4e2bd33c3 refactor(frontend): simplify event handlers in Register.vue
Replace arrow function wrappers with direct expressions and ternary
no-ops with short-circuit evaluation for cleaner, more readable code.
2026-01-10 21:59:06 +01:00
kolaente 483ddc728d test(frontend): verify FormField generates unique IDs across instances
Mount multiple FormField components within the same Vue app to properly
test that useId() generates unique IDs for each instance. This validates
that labels correctly link to their respective inputs.
2026-01-10 21:59:06 +01:00
kolaente 8f0c7d504b test(frontend): add regression test for FormField $attrs event forwarding
Verify that FormField forwards $attrs event listeners (onKeyup, onFocusout)
to its inner input element. This ensures migrated templates using
@keyup.enter and @focusout continue to work correctly.
2026-01-10 21:59:06 +01:00
kolaente 182b0b63d1 fix(frontend): preserve numeric type in FormField v-model
When modelValue is a number, emit the value as a number instead of
coercing to string. This prevents subtle type bugs when using
FormField with numeric v-model bindings.
2026-01-10 21:59:06 +01:00
kolaente 4ee29f9972 refactor(frontend): use FormField scoped slot id for select elements
Update FormField usages with slotted select elements to use the
exposed id from the scoped slot, ensuring label-input association
works correctly.
2026-01-10 21:59:06 +01:00
kolaente ac2f14945b feat(frontend): expose id via scoped slot in FormField
When using FormField with custom slot content, the slotted element
needs access to the generated inputId to ensure the label's for
attribute matches the input's id. This exposes the id via the
default slot: <template #default="{ id }">
2026-01-10 21:59:06 +01:00
kolaente 5ca600506b fix(frontend): expose focus method on FormField component
Components using FormField with a ref need to call .focus() on it.
Without exposing the method, these calls would fail since the ref
points to the component instance, not the underlying input element.
2026-01-10 21:59:06 +01:00
kolaente fb8ee82b98 fix(frontend): restore loading state on FormField migrations
Add loading prop to FormField usages where is-loading class was
accidentally removed during migration.
2026-01-10 21:59:06 +01:00