Wekan logo

Wekan

Open source kanban board application built with Meteor

Alternative to: trello


About Versions (218)

v10.42

2026-07-27

v10.42 2026-07-27 WeKan ® release

This release fixes the following bugs:

Every popup had 10px of empty space above it that nothing asked for. Thanks to xet7.

The space above the first row of Board Settings, Board View, Member Settings, Sort Cards, Change Watch, Change Visibility and Swimlane Actions — and above the Title field of Rename Board — was much larger than the space beside it. None of it came from popup.css: peopleBody.css and translationBody.css each carried a bare .content-wrapper { margin-top: 10px }, and .content-wrapper is not a settings class at all — the only element in WeKan with that class is the scrolling body of a POPUP, so those two strays pushed the content of every popup in the app down by 10px. They are gone, and the gap that is left is 6px under the header plus the content’s 12px of padding = the same 18px the content has beside it. Change Visibility and Change Watch also lay their rows out as three left-aligned columns now — icon, name, description — with the check mark of the active row in a track of its own, so it can no longer push that row’s description out of line with the others. tests/popupSpacing.test.cjs pins both, and fails again if any stylesheet styles a popup-internal class without saying which popup.

The board bar centers its items, and the hamburger sits where its space middles. Thanks to xet7.

The second header bar centred its items inside a content box that had 7px of padding above and none below, so everything sat half that distance high — most visibly the board title, the tallest item in the row. The button groups then carried a 3px top margin, which is a shift and not centring, so they hung below the title’s centre line. The padding is symmetric now, wrapped rows are separated by row-gap instead of that margin, and the title centres on its own text rather than on a line box far taller than it. The sidebar hamburger had 2px of margin on one side and 8px on the other, which left an empty strip between it and the end of the bar; equal margins put it in the middle of the space between its divider and that edge.

Every upload threw in getFileStrategy, so no new file was mime-checked. Thanks to xet7.

From the dev-server log, on a plain attachment upload: [onAfterUpload] filename hardening failed: TypeError: Cannot read properties of undefined (reading 'gridFsFileId'). getFileStrategy read fileObj.versions[versionName].meta.gridFsFileId to decide the storage, and a freshly uploaded file has no meta on its version — only a GridFS one does — so that read threw on EVERY upload. onAfterUpload catches and logs, so the upload succeeded and looked fine while the two things that hook does were silently skipped for every new file: detecting the real mime type and correcting the stored filename from it. All three optional places are read defensively now, and the decision is unchanged where the data is there.

Migrated images show in the card view again. Thanks to S0QR2 and xet7.

Reported after upgrading from WeKan 6: an attached image is visible in board view, downloads correctly from the card, and yet the card view shows an empty white box that cannot be maximized — while cards created after the upgrade are fine. The card view does not look at the file, it looks at the flags Meteor-Files writes at upload time (if(isImage) img … else span= extension), and an attachment that came through a migration can arrive without them, and often without extension or type either. The download button worked because a download needs no flag. models/lib/attachmentKind.js is now the one place that derives the kind — from the mime type where the document has one, in any of the fields that have carried it, and from the file name where it does not; a flag the document states is believed, and the name is consulted only when no type is stated. The gallery, the “add cover” menu and the viewer all ask it, and a startup repair writes the same answer back to the documents so the REST API and the exports agree with the screen. tests/attachmentKind.test.cjs pins the rules.

and has the following developer-facing changes:

Two test-harness fixes the newest run found. Thanks to xet7.

The node suites got four assertions further and stopped in the same file: two more cpuExec expectations still spelled the qemu-wrapped command as a bare name, which cpu-exec resolves to an absolute path now. And WebKit failed 33-board-domains with “Unexpected userId after login” — the admin’s id, when the test had just switched to the non-admin: loginWithToken logged the new user in over a session that was still someone else’s, so the poll could not tell “not landed yet” from “landed on the wrong user”. It logs the previous user out first and waits for an empty session, with a 15s settle deadline for a loaded three-browser run.

cpu-exec hands qemu-user a path it can open, and its test stops assuming the machine. Thanks to xet7.

First real run of the node suites — they had never run anywhere until the “Run ALL tests” change — and cpuExec.test.cjs failed, which is what that change was for. Two real things behind it. qemu-user does not search PATH: it opens the file it is given, so a bare command name (cpu-exec --features x86_64=avx mongod …) reached qemu as a relative path that does not exist and qemu exited 1 having run nothing — on exactly the CPU this helper exists for. cpu-exec resolves the name with type -P first and hands over an absolute path; an absolute path is passed through as before. And the test asked for “no qemu” with PATH=/usr/bin:/bin, which is only true on a machine without qemu-user installed; it now builds a PATH holding exactly the tools cpu-exec uses and nothing else, so the case is the same everywhere.

Thanks to above GitHub users for their contributions and translators for their translations.