* desktop: fix crash in SimpleX address screen when there is no profile
* desktop: close SimpleX address screen when there is no profile
* desktop: rerun address screen self-close when its modal is reused or the stack changes
* desktop: close SimpleX address screen only when it is the top modal
* plans: correct address no-profile crash triggers and fix description
* plans: correct address no-profile crash fix description and verification
* plans: tighten address no-profile crash wording
* plans: add self-destruct trigger to address no-profile crash
* plans: qualify self-destruct trigger on desktop
* plans: drop desktop-only title from address no-profile crash
* plans: no connected mobile, not no mobile
* spec, product: document isLastModal and address screen without profile
* plans, spec, product: plan sections, address row spec, GAP-08 and GAP-09
* spec, product, plans: fix GAP-08/09 wording, table placement, ModalManager line
* spec, product: GAP-08/09 accuracy, gap count, clickable ModalManager location
* product, plans: GAP-09 at the level the code supports; qualify picker auto-open
* spec, product, plans: fix GAP-09 locations, stale line links, wording
* spec, product, plans: update plain-text line numbers; GAP-09 read wording
* plans: name the picker auto-open condition
* spec, plans: wording; security note
* plans: self-destruct did not crash on Android master; not a trigger
* plans: self-destruct path possible but unconfirmed; Android recovers silently
* spec, product, plans: drop GAP-09 and unrelated line refreshes
* plan: Android self-destruct path confirmed in logcat
* desktop: close Chat preferences screen when there is no profile, as the address screen does
* ci: use default registries for empty variables
* ci: drop package publish tags
* ci: record releases in simplex-chat-libs
* ci: skip recorded versions in publish plan
* nodejs: raise default test timeout for migrations
* nodejs: print download progress without console.error
* nodejs: use the default timeout in migrating core tests
* ci: drop dlltool from nodejs libs release
* nodejs: download libsimplex into the user cache
* nodejs: load libsimplex at runtime per backend
* support bot: select db backend with --db
* python: match backend switch error text
* nodejs: download prebuilt add-on at runtime
* ci: build nodejs add-on for libs release
* calculator bot: load libs and add-on in image
* support bot: document add-on override
* nodejs: keep worker test output free of colors
* nodejs: verify sha-256 of downloaded assets
* python: pin core libs release with sha-256
* ci: add packages release script
* ci: release nodejs add-on and open release PR
* ci: publish packages after release PR
* nodejs: keep npm from building the add-on
* calculator bot: build the add-on in the image
* ci: merge package release workflows
* ci: open release PR when publishing fails
* ci: build the add-on with node-addon-api only
* ci: skip publishing in a called packages workflow
* ci: update package release actions to Node 24
* nodejs: fix receive test timeout
* ci: test packages on pull requests
* nodejs: reuse the database in the close stress test
* ci: keep failed package tests from hanging
* ci: skip preset server tests
* ci: plan package builds from the changes
* ci: test packages with a given libsimplex
* ci: test packages with libsimplex of core changes
* ui: show unicode characters in address as unicode markers
* defence in depth for links in messages (they are non-clickable from parser)
---------
Current code does not have this problem, as markdown parser rejects such links, and they are not clickable - it is needed for new markdown file viewer - this way unicode links in markdown show with unicode sequences instead of look-alike letters.
* core: release core library to simplex-chat-libs every time cabal version changes
* implement
* test build
* update libs release
* test library release
* create release commit, so the date is correct
* rework to create release in advance in maybe-release job
* remove test build
* move postgresql job back
* test build
* remove test build
---------
Co-authored-by: Evgeny @ SimpleX Chat <259188159+evgeny-simplex@users.noreply.github.com>
* rfc: invite member of one group to another group
* update
* update
* implement
* version
* update
* do not show error if contact was removed when joining group
---------
Co-authored-by: Evgeny @ SimpleX Chat <259188159+evgeny-simplex@users.noreply.github.com>
* ios: delete temp data from storage view
The temp folder is the XFTP agent work directory and holds scratch
files for received-file encryption and roster transfers, so deleting it
under a running chat breaks those writes mid-flight. The button is only
enabled while chat is stopped, the same precondition core deleteStorage
relies on, and the row says how to stop chat.
* ios: show delete temp data alert over settings sheet
AlertManager presents from ContentView, which is behind the settings
sheet, so the confirmation never appeared. The alert now also warns
that interrupted transfers never complete and that videos in unsent
drafts, which live in the temp folder, are lost, and the caption names
the screen where chat is stopped.
* ios: say unsent draft videos are sent without the file
A draft video whose converted file was deleted from the temp folder is
still sent, as a preview with no file, so "lost" understated it.
---------
Co-authored-by: Evgeny Poberezkin <evgeny@poberezkin.com>
* android: recognise passphrase fields as passwords for password managers
Passphrase fields used a hand-rolled VisualTransformation lambda, so Compose never
marked them as password fields: the autofill structure carried no hints and no
password inputType, and password managers could not identify them. The raw
passphrase was also exposed through the CopyText/ACTION_COPY accessibility action.
PassphraseField now declares an autofill content type and uses
PasswordVisualTransformation, which sets the password semantics Compose derives
that flag from.
Fields that create a passphrase declare NewPassword. Where no field would carry
plain password (first-time setup, hidden profile password) they declare both, as
managers do not recognise a form whose every field is newPassword. On the change
form the current-passphrase field supplies password, so the new fields declare
only newPassword - adding password there leaves the manager unable to tell which
field holds the new value and suppresses the save prompt.
* android: do not offer to save hidden profile passwords
Hidden profile password fields no longer declare an autofill content type.
Compose commits the autofill session, which shows the password manager's
save prompt, only after the last field with a content type leaves the
screen, so these fields never trigger it. A saved entry would reveal that
the hidden profile exists.
Rewrite the plan to match the code.
* android, desktop: storage breakdown in developer options
Port of the iOS Storage screen (#5529): lists each top-level entry of the app's data, config and temp folders with its recursive size, so it is possible to see what takes space.
* android, desktop: simplify storage view
Use DefaultProgressView, drop the bold total and redundant absoluteFile, and do not follow top-level symlinks (matches iOS; avoids counting the Android lib link).
* android, desktop: storage view: do not crash on names the JVM cannot convert to Path
Under a non-UTF-8 locale on Linux, File.toPath() throws InvalidPathException for a non-ASCII top-level name (e.g. a received file decrypted into tmpDir); log it and show 0 bytes. Also correct plan wording.
* android, desktop: storage view: fold path conversion into treeSize, use produceState
Also correct plan wording (du per-directory overhead, unlistable roots, Windows junctions).
* android, desktop: storage view: open as card screen like other settings screens
* android, desktop: storage view: list top-level entries as Path to keep their exact names
File.listFiles + toPath loses names that are not valid in the JVM file-name encoding (non-ASCII under a C locale, invalid UTF-8), so those entries showed 0 bytes. Files.newDirectoryStream keeps the raw bytes.
* android, desktop: storage view: normalize root paths before dropping nested roots
A root spelled with .. (e.g. XDG_DATA_HOME=/x/data/../tmp) compared as nested in another root and its size was shown nowhere.
* android, desktop: document storage view in spec and product docs
* android, desktop: storage view: single catch when listing a root
* android, desktop: do not log file paths in storage view
The walk's IOException messages contain the full path, which in tmpDir can be a received file's original name.
---------
Co-authored-by: Evgeny Poberezkin <evgeny@poberezkin.com>
The core allocates every chat_* response with malloc and passes ownership to
the caller, as iOS does in API.swift. Both JNI bindings copied the bytes into a
Java string and dropped the pointer, so every command, event and file read
leaked its whole response into the C allocator - invisible to both the JVM and
the Haskell heap profiler.
Desktop frees in decode_to_utf8_string, the funnel every entry point already
goes through. Android has no such funnel because NewStringUTF is called inline,
so decode_and_free is added and the call sites routed through it. chatReadFile
frees directly on both.
Co-authored-by: Evgeny Poberezkin <evgeny@poberezkin.com>
* core: group fixes/improvements
* Large messages dropped by relays and hosts (the same 15602 limit was applied, without accounting for forwarding header)
* Members below v18 did not receive forwarded messages or history in p2p groups.
* Join confirmations near the size limit could fail.
* SMP servers are limited to 2 host names each.
* simplify
* remove legacy forwarding and history support
* only restrict p2p groups
---------
Co-authored-by: Evgeny @ SimpleX Chat <259188159+evgeny-simplex@users.noreply.github.com>
* android: create new keystore keys in StrongBox
* android: show keystore key storage level
* ui: save keystore key before marking it stored
* android: show keystore storage level in the footer text instead of a separate row
* android: return keystore storage label, drop enum
---------
Co-authored-by: Narasimha-sc <166327228+Narasimha-sc@users.noreply.github.com>
* core, ui: remove database backups after key changes
* ui: delete database backups on chat start without delaying encryption marker reset
Keeping encryptionStartedAt set until chat start made DatabaseErrorView show
"The attempt to change database passphrase was not completed" with a Restore
button after every successful passphrase change when the passphrase is not
stored. Restore the marker handling from master and delete backups
unconditionally after chat starts.
* another flag
---------
Co-authored-by: Evgeny @ SimpleX Chat <259188159+evgeny-simplex@users.noreply.github.com>
Co-authored-by: Narasimha-sc <166327228+Narasimha-sc@users.noreply.github.com>