Skip to content
Permalink

Comparing changes

Choose two branches to see what’s changed or to start a new pull request. If you need to, you can also or learn more about diff comparisons.

Open a pull request

Create a new pull request by comparing changes across two branches. If you need to, you can also . Learn more about diff comparisons here.
base repository: modelstudioai/openwork
Failed to load repositories. Confirm that selected base ref is valid, then try again.
Loading
base: v0.1.3
Choose a base ref
...
head repository: modelstudioai/openwork
Failed to load repositories. Confirm that selected head ref is valid, then try again.
Loading
compare: v0.1.4
Choose a head ref
  • 9 commits
  • 188 files changed
  • 3 contributors

Commits on Jun 17, 2026

  1. chore(release): desktop v0.1.3 [skip ci]

    Co-authored-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com>
    DragonnZhang and github-actions[bot] authored Jun 17, 2026
    Configuration menu
    Copy the full SHA
    d5f76b0 View commit details
    Browse the repository at this point in the history

Commits on Jun 30, 2026

  1. chore(loop): bootstrap autonomous desktop-feature loop infra (#38)

    Prerequisites for the unattended desktop-feature loop:
    
    - e2e CDP harness (`bun run e2e`): launches the built Electron app with
      remote debugging, drives the real UI over the Chrome DevTools Protocol,
      and asserts on rendered state. Zero new deps (Bun's WebSocket + fetch).
      Runs against an isolated profile (config, userData, default workspace
      redirected under .e2e/) and is headless-aware (xvfb + --no-sandbox on
      Linux). Ships an app-boot smoke assertion as the template for new ones.
    - docs/loop/feature-ledger.md: cross-run ledger with a status state
      machine (proposed/in-progress/pr-open/merged/rejected/blocked).
    - docs/loop/capability-inventory.md: baseline inventory of current
      desktop capabilities to diff candidate features against.
    DragonnZhang authored Jun 30, 2026
    Configuration menu
    Copy the full SHA
    4c8ccee View commit details
    Browse the repository at this point in the history

Commits on Jul 1, 2026

  1. Add searchable filtering to the settings navigator (#40)

    * Add searchable filtering to the settings navigator
    
    The settings navigator rendered a flat, unfilterable list of 16 sections.
    Add a search box at the top that filters sections by title and description
    (case-insensitive substring), mirroring the existing session-list search
    styling — search icon, clear button, focus ring, Esc-to-clear, and a
    "No results found" empty state. This matches the searchable-settings
    affordance in comparable desktop apps.
    
    Implementation is frontend-only and reuses existing i18n keys
    (common.search, common.noResultsFound), so no locale strings change.
    
    Also:
    - LeftSidebar: emit data-testid={link.id} on nav buttons so the settings
      entry point (and other nav items) are addressable from e2e.
    - e2e/app.ts: give each launch its own profile dir (keyed on the debug
      port) and launch under setsid on headless Linux so teardown reaps the
      whole xvfb-run tree. Without this, a lingering Electron instance held
      the single-instance lock and the next assertion could never get a
      renderer target — which blocked running more than one CDP assertion.
    - e2e/assertions/settings-search.assert.ts: drives the real app over CDP
      to verify the filter narrows, shows the empty state, and restores.
    
    * Update feature ledger: settings-search PR open (#40)
    
    ---------
    
    Co-authored-by: Claude <noreply@anthropic.com>
    DragonnZhang and claude authored Jul 1, 2026
    Configuration menu
    Copy the full SHA
    36bac52 View commit details
    Browse the repository at this point in the history
  2. Add a global command palette (⌘K / Ctrl+K) (#42)

    * feat(desktop): add global command palette (⌘K / Ctrl+K)
    
    Add a keyboard-driven command palette that lets you search for and run any
    registered app action — the "run" surface that pairs with the read-only
    Keyboard Shortcuts reference. Every comparable desktop app (Claude Code
    Desktop, VS Code / Codex, Linear) ships one; OpenWork had the action
    registry, cmdk primitives, and translated labels, but nothing tied them
    together.
    
    Frontend-only. The palette lists the centralized action registry grouped by
    category, filters with cmdk's built-in fuzzy match, and dispatches the chosen
    action via the registry's execute() — exactly as if its hotkey were pressed.
    Opened with ⌘K / Ctrl+K or from the app menu. No backend / qwen-code change,
    and no new i18n keys (reuses commands.*, common.noResultsFound, and the
    existing shortcuts.action.* / shortcuts.category.* labels).
    
    - action registry: new app.commandPalette action (mod+k)
    - CommandPalette component (self-contained: registers its open handler, owns
      state, integrates with the modal stack)
    - extract ACTION_LABEL_KEYS to a shared actions/action-i18n module and reuse
      it in the Shortcuts settings page
    - AppMenu entry for discoverability
    - e2e: command-palette CDP assertion (open → filter → empty → clear → run
      Toggle Theme and assert the theme flips)
    - e2e harness: per-port isolated profile dirs so multiple assertions can each
      launch their own app instance without single-instance-lock collisions
    
    Closes #41
    
    * fix(desktop): command palette only lists runnable actions, run after close
    
    Two issues surfaced from testing the palette:
    
    - It listed context-scoped actions whose handler is disabled in the palette's
      context (e.g. "Next Search Match" / "Previous Search Match", which need an
      active in-conversation search, and the navigator/panel focus actions).
      Selecting one was a dead no-op — clicking appeared to "do nothing". The
      palette now filters to actions the registry reports as executable right now
      (new ActionRegistry.canExecute), so only runnable commands show.
    
    - It ran the selected action synchronously while the dialog was still tearing
      down, so actions that open a panel or move focus (e.g. Search) could be
      clobbered by the dialog's focus restoration. It now closes first and runs the
      action on the next tick, in the app's restored-focus context.
    
    The e2e assertion additionally verifies a known context-scoped action
    ("Next Search Match") is absent from the palette.
    
    ---------
    
    Co-authored-by: Claude <noreply@anthropic.com>
    DragonnZhang and claude authored Jul 1, 2026
    Configuration menu
    Copy the full SHA
    8741a7a View commit details
    Browse the repository at this point in the history

Commits on Jul 2, 2026

  1. Add a thinking-level (reasoning effort) picker to the chat composer (#45

    )
    
    * Add a thinking-level (reasoning effort) picker to the chat composer
    
    Adds a composer toolbar dropdown to change the per-session thinking level
    (off / low / medium / high / xhigh / max), mirroring the existing model
    picker. The thinkingLevel / onThinkingLevelChange props were already plumbed
    to FreeFormInput and persisted by both the draft and active chat pages; only
    the UI trigger was missing.
    
    Frontend-only: renders a Radix dropdown and calls the existing
    onThinkingLevelChange prop. No new i18n keys — level names/descriptions reuse
    the existing thinking.* keys and the trigger tooltip reuses settings.ai.thinking.
    
    Includes a CDP e2e assertion (e2e/assertions/thinking-level-picker.assert.ts)
    that opens the picker, asserts all six levels are listed with the active one
    marked, selects a different level, and asserts the trigger label updates.
    
    Closes #44
    
    * docs(loop): record thinking-level-picker as pr-open (#45)
    
    ---------
    
    Co-authored-by: Claude <noreply@anthropic.com>
    DragonnZhang and claude authored Jul 2, 2026
    Configuration menu
    Copy the full SHA
    26f609c View commit details
    Browse the repository at this point in the history

Commits on Jul 6, 2026

  1. Add a "Reduce motion" accessibility setting to Appearance (#51)

    * feat(desktop): add Reduce motion accessibility setting to Appearance
    
    Add a renderer-only "Reduce motion" preference to Settings → Appearance →
    Interface. When enabled the app renders inside <MotionConfig reducedMotion=
    "always"> so every motion/react component short-circuits its animations, sets
    data-reduce-motion="true" on <html> for a global CSS guard that collapses plain
    CSS animations/transitions, and persists the choice in localStorage. When
    disabled it uses reducedMotion="user", still honoring the OS
    prefers-reduced-motion setting.
    
    - New ReduceMotionProvider wired at the renderer root (main.tsx).
    - Appearance toggle reuses SettingsToggle (gains an optional testId prop).
    - data-testid on settings-navigator items for e2e navigation.
    - Two new i18n keys across all 7 locales.
    - CDP e2e assertion: e2e/assertions/reduce-motion.assert.ts.
    
    * docs(loop): mark reduce-motion pr-open (#51)
    
    ---------
    
    Co-authored-by: Claude <noreply@anthropic.com>
    DragonnZhang and claude authored Jul 6, 2026
    Configuration menu
    Copy the full SHA
    8c468e4 View commit details
    Browse the repository at this point in the history

Commits on Jul 10, 2026

  1. Add a copy-as-Markdown action to assistant/agent responses (#71)

    Assistant/agent responses had only a pop-out hover action and no way to
    copy them, even though user messages and code blocks were already
    copyable. Comparable desktop chat surfaces (Codex's much-requested
    Copy as Markdown, Claude/ChatGPT desktop) all offer a per-message copy.
    
    Extract an AssistantMessage component in ChatDisplay so it can own the
    copy button's transient copied state (mirroring the existing
    ErrorMessage extraction). The button sits next to the pop-out control,
    copies the response's raw Markdown via the Clipboard API, shows a 2s
    check state, and toasts on failure. Only shown on a settled
    (non-streaming) response. Reuses existing i18n keys (common.copy /
    common.copied / toast.copyFailed) — no new keys.
    
    Also add a backend-independent seed hook to the e2e harness so an
    assertion can pre-seed an on-disk session that the embedded
    SessionManager loads on boot, and a CDP assertion that seeds a
    user+assistant session, clicks the copy button, and asserts the exact
    response markdown reaches the clipboard and the button enters its
    copied state.
    
    Closes #70
    
    Co-authored-by: Claude <noreply@anthropic.com>
    DragonnZhang and claude authored Jul 10, 2026
    Configuration menu
    Copy the full SHA
    6a7e71b View commit details
    Browse the repository at this point in the history

Commits on Jul 13, 2026

  1. chore(sync): sync qwen-code desktop updates (#74)

    * fix(cli): Preserve mid-turn image messages (#5183)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: c593582
    Qwen-Code-Commit: 1e6b9d6
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): address git branch badge review (#5247)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: b7c0e53
    Qwen-Code-Commit: d01197c
    OpenWork-Base: 6a7e71b
    
    * feat(extensions): add i18n support for extension displayName and description (#5289)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 816639f
    Qwen-Code-Commit: b524423
    OpenWork-Base: 6a7e71b
    
    * feat(desktop): compile macOS 26+ Liquid Glass Assets.car in brand-create (#5284)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 68fced8
    Qwen-Code-Commit: f91054a
    OpenWork-Base: 6a7e71b
    
    * fix: Expand Windows ~\\ home paths and hide phantom (session) entries in the desktop session list (#5253)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 62c05c8
    Qwen-Code-Commit: 0d15e89
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): detect WebP and AVI in RIFF magic-byte sniffing (#5336)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 9e16b4c
    Qwen-Code-Commit: 5479b44
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): accept uppercase icon URL schemes (#5470)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: fc15ae6
    Qwen-Code-Commit: cf3e57f
    OpenWork-Base: 6a7e71b
    
    * fix: accept uppercase endpoint URL schemes (#5443)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 4d27240
    Qwen-Code-Commit: 26c1309
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): preserve uppercase favicon URLs (#5463)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 64cc9f6
    Qwen-Code-Commit: 172288b
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): parse NO_PROXY ports strictly (#5498)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 172288b
    Qwen-Code-Commit: 8368e7f
    OpenWork-Base: 6a7e71b
    
    * test(desktop): update blocked scheme open-url assertion (#5529)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: cfe55e9
    Qwen-Code-Commit: 0c65dbc
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): restore locale parity (#5537)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 0c65dbcaa109667828e5aa07ac935a1ef3ac6a1a
    Qwen-Code-Commit: e4fdd24
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): parse server ports strictly (#5509)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 234777c
    Qwen-Code-Commit: 2a77536
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): validate generic oauth token responses (#5511)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 2a77536
    Qwen-Code-Commit: 83f5146
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): allow double dots in bundle filenames (#5515)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 8b6ac72
    Qwen-Code-Commit: ca7638e
    OpenWork-Base: 6a7e71b
    
    * test(desktop): align interceptor packaging contract (#5531)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: d0ba853
    Qwen-Code-Commit: b117c56
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): keep sibling paths absolute (#5517)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: b117c56
    Qwen-Code-Commit: aeb0e58
    OpenWork-Base: 6a7e71b
    
    * test(desktop): enable feedback flag in permission tests (#5533)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: aeb0e58
    Qwen-Code-Commit: 19573f7
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): separate transform data output lines (#5525)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 7a4f080
    Qwen-Code-Commit: 0eb4395
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): handle Windows file mentions (#5523)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 0eb4395
    Qwen-Code-Commit: 948f782
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): consolidate path boundary checks (#5545)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: aa62576
    Qwen-Code-Commit: 71fd029
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): reject fractional transfer sizes (#5527)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 71fd029
    Qwen-Code-Commit: 0880e34
    OpenWork-Base: 6a7e71b
    
    * feat(desktop): show file preview in a resizable side panel instead of fullscreen (#5730)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 2eb3b80
    Qwen-Code-Commit: f4b591b
    OpenWork-Base: 6a7e71b
    
    * feat(memory): confirm auto-generated skills before persisting (#5616)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 87ce3f4
    Qwen-Code-Commit: 44b80da
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): reject unsafe source slugs before deletion (#5829)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: d93bec9
    Qwen-Code-Commit: 51ec7c3
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): harden remaining source path validation (#5914)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 278d806
    Qwen-Code-Commit: a12ca8d
    OpenWork-Base: 6a7e71b
    
    * feat(memory): add a git-shared team memory tier (#5886)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 94ea088
    Qwen-Code-Commit: 6734548
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): normalize source slug validation errors (#5911)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: 2776737
    Qwen-Code-Commit: 877e8ab
    OpenWork-Base: 6a7e71b
    
    * feat(desktop): voice dictation in the desktop app (#5856)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: f876f4a
    Qwen-Code-Commit: a1bcda6
    OpenWork-Base: 6a7e71b
    
    * fix(cli): switch TUI prefix ✦→◆ to fix glyph overflow on some terminals (#5974)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: c48dc32
    Qwen-Code-Commit: e92fcba
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): enforce transform_data isolation (#6285)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: adda526
    Qwen-Code-Commit: 06fc052
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): preserve glued automation history records (#6344)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: be0b074
    Qwen-Code-Commit: 47f62a4
    OpenWork-Base: 6a7e71b
    
    * fix(desktop): preserve MCP URL query suffixes (#6587)
    
    OpenWork-Sync-Mode: export
    Qwen-Code-Base: eff2a04
    Qwen-Code-Commit: 28bfadf
    OpenWork-Base: 6a7e71b
    DragonnZhang authored Jul 13, 2026
    Configuration menu
    Copy the full SHA
    383babd View commit details
    Browse the repository at this point in the history
  2. Configuration menu
    Copy the full SHA
    84cd12c View commit details
    Browse the repository at this point in the history
Loading