* feat: add `Notification.getHistory()` static method (macOS)
Add `Notification.getHistory()` which returns a `Promise<Notification[]>`
of all delivered notifications still present in Notification Center.
Each returned Notification is a live object connected to the corresponding
delivered notification — interaction events (click, reply, action, close)
will fire on these objects, enabling apps to re-attach event handlers after
a restart.
Key implementation details:
- Queries UNUserNotificationCenter's getDeliveredNotifications API
- Creates live Notification objects with populated id, groupId, title,
subtitle, and body properties from what macOS provides
- Registers each object with the presenter via Restore() so the
NotificationCenterDelegate routes events correctly
- Restored notifications use is_restored_ flag to prevent removal from
Notification Center when the JS object is garbage collected
- Requires code-signed builds (unsigned builds resolve with empty array)
Co-Authored-By: Claude <svc-devxp-claude@slack-corp.com>
* test: fix typecheck
* fix: avoid dangling presenter pointer in GetHistory callback
* fix: document show() behavior
Notifications returned by getHistory() now set is_restored_ so that Dismiss() skips removal from Notification Center on GC. Calling show() on a restored notification removes the original from NC and posts a new one.
* fix: address code review feedback
* test: fix oxfmt linting
* docs: update docs/api/notification.md
Co-authored-by: Erick Zhao <erick@hotmail.ca>
---------
Co-authored-by: Claude <svc-devxp-claude@slack-corp.com>
Co-authored-by: Erick Zhao <erick@hotmail.ca>
* refactor: MessageChannel does not need to extend EventEmitter
Added in f66d4c7 but never used.
Apparently added as a copy-paste side effect when adding better interface
info into the lib types, eg extends/implements.
* refactor: ShareMenu does not need to extend EventEmitter
Added in f66d4c7 but never used.
Apparently added as a copy-paste side effect when adding better interface
info into the lib types, eg extends/implements.
* refactor: migrate electron::api::GlobalShortcut to cppgc
* refactor: lazy-create electron::api::GlobalShortcut
copy the lazy-create idom used by electron::api::Screen
* refactor: use gin::WeakCellFactory in GlobalCallbacks
* fix: make a copy of `callback` before running it
safeguard against the callback changing the map, invalidating `cb`
* chore: reduce unnecessary diffs with main
* fixup! refactor: use gin::WeakCellFactory in GlobalCallbacks
fix: must Trace() the weak cell factory
* fix: destruction order
- Setup isolate dispose observer to run destruction sequences
and remove self persistent reference
- Skip NOTREACHED check during destruction, it can happen
as a result of plaform listeners scheduling callbacks when Unregister is invoked.
- Fix the order of unregistration in GlobalShortcut::Unregister
- Add GlobalShortcut::UnregisterAllInternal to avoid any callsites
that can re-enter V8
* fix: crash during gc from incorrect cppgc object headers
* chore: update patches
* chore: cleanup
* chore: fix lint
---------
Co-authored-by: deepak1556 <hop2deep@gmail.com>
* build: add oxfmt for code formatting and import sorting
Adds oxfmt as a devDependency alongside oxlint and wires it into the
lint pipeline. The .oxfmtrc.json config matches Electron's current JS
style (single quotes, semicolons, 2-space indent, trailing commas off,
printWidth 100) and configures sortImports with custom groups that
mirror the import/order pathGroups previously enforced by ESLint:
@electron/internal, @electron/*, and {electron,electron/**} each get
their own ordered group ahead of external modules.
- `yarn lint:fmt` runs `oxfmt --check` over JS/TS sources and is
chained into `yarn lint` so CI enforces it automatically.
- `yarn format` runs `oxfmt --write` for local fix-up.
- lint-staged invokes `oxfmt --write` on staged .js/.ts/.mjs/.cjs
files before oxlint, so formatting is applied at commit time.
The next commit applies the formatter to the existing codebase so the
check actually passes.
* chore: apply oxfmt formatting to JS and TS sources
Runs `yarn format` across lib/, spec/, script/, build/, default_app/,
and npm/ to bring the codebase in line with the .oxfmtrc.json settings
added in the previous commit. This is a pure formatting pass: import
statements are sorted into the groups defined by the config, method
chains longer than printWidth are broken, single-quoted strings
containing apostrophes are switched to double quotes, and a handful of
single-statement `if` bodies are re-wrapped and get braces added by
`oxlint --fix` to satisfy the `curly: multi-line` rule.
No behavior changes.
* fix: remove Electron links from default help menu
* fix: remove help menu entirely from default menu
* fix: move Electron help menu links to default app
* docs: update default menu items list in menu.md
Consolidates the root .eslintrc.json and five nested configs (build,
script, docs, default_app, spec) into a single .oxlintrc.json at the
repo root. script/lint.js now shells out to the oxlint binary from
node_modules/.bin instead of using the ESLint Node API, and emits
GitHub Actions annotations directly via --format=github in CI
(replacing the deleted eslint-stylish problem matcher).
Oxlint has no markdown processor, so the ESLint-based lint of JS code
blocks in docs/**/*.md is replaced with an inline regex check for bare
Node.js builtin imports. This preserves the rule docs/.eslintrc.json
was originally added for in #42113; the rest of the standard ruleset on
docs code blocks was already being enforced in parallel by
lint-roller-markdown-standard.
The frameNamesToWindow map was a holdover from the BrowserWindowProxy
IPC shim. Since nativeWindowOpen became the only code path, Blink's
FrameTree::FindOrCreateFrameForNavigation resolves named window targets
directly in the renderer, scoped to the opener's browsing context
group. When a matching named window exists, Blink navigates it without
ever sending a CreateNewWindow IPC to the browser, so this map was
never consulted in the legitimate same-opener case.
The only time the map found a match was when two unrelated renderers
happened to use the same target name, in which case openGuestWindow
would short-circuit before consuming the guest WebContents that
Chromium had already created for the new window, leaking it.
Adds a test verifying Blink handles same-opener named-target reuse
end-to-end without any browser-side tracking.
* feat: add copyVideoFrameAt and saveVideoFrameAs Method on Webcontent
chore: change the description of savevideoframe api
chore: add the description of the restrictive elements for using the APIs.
move to webframemain
fixed mediaPlayerAction to kSaveVideoFrameAs
Update spec/api-web-frame-main-spec.ts
Co-authored-by: John Kleinschmidt <kleinschmidtorama@gmail.com>
Update spec/api-web-frame-main-spec.ts
Co-authored-by: John Kleinschmidt <kleinschmidtorama@gmail.com>
fixed clipboard tests for video frame copying
fixed test for copying video frame to clipboard. check video loaded before copy video frame in test.
chore: try non-proprietary video format
Revert "chore: try non-proprietary video format"
This reverts commit ef085f88a1af53b6408a7af695cc60b8681398cf.
fix: format video as file url
* test: skip webFrameMain.copyVideoFrameAt on win32 CI due Chromium DCHECK
The sender-mismatch check in invokeInWebContents and invokeInWebFrameMain
used a negative condition (`type === 'frame' && sender !== expected`),
which only rejected mismatched frame senders and accepted anything else.
Invert to a positive check so only the exact expected frame can resolve
the reply — matches the guard style used elsewhere in lib/browser/.
PowerMonitor registered OS-level callbacks (HWND UserData and
WTS/suspend notifications on Windows, shutdown handler and lock-screen
observer on macOS) but never cleaned them up in its destructor. The JS
layer also only held the native object in a closure-local variable,
allowing GC to reclaim it while those registrations still referenced
freed memory.
Retain the native PowerMonitor at module level in power-monitor.ts so
it cannot be garbage-collected. Add DestroyPlatformSpecificMonitors()
to properly tear down OS registrations on destruction: on Windows,
unregister WTS and suspend notifications, clear GWLP_USERDATA, and
destroy the HWND; on macOS, remove the emitter from the global
MacLockMonitor and reset the Browser shutdown handler.
* feat: webFrameMain.fromFrameToken
* refactor: return null instead of undefined
* docs: mention renderer webFrame property
* chore: undo null->undefined in wfm.fromId api
this will be updated in another pr
fix: window.open popups are always resizable
Closes https://github.com/electron/electron/issues/43591.
Per current WHATWG spec, the `window.open` API should always
create a resizable popup window. This change updates the
`parseFeaturesString` function to ensure that windows opened
with `window.open` are always resizable, regardless of the
`resizable` feature string.
* feat: add menu item role `palette` and `header`
* adds comments
* refactors new role items to new item types
* docs: custom type
* docs: note types only available on mac 14+
---------
Co-authored-by: Samuel Maddock <smaddock@slack-corp.com>
* feat: enable innerWidth and innerHeight for window open
* update comment for added special innerWidth and innerHeight
* update 100 min spec requirement handling
* update testing to include getContentSize
* update macOS min requirement handling
* adjust refactored consts
* update const values from nativewindowviews
* feat: add support for associating a Menu with a WebFrameMain
This allows certain OS level features to activate such as Writing Tools, Autofill.. and Services.
There appears to be a bug in macOS where the responder chain isn't traversed if the menu is not popped up using an event, as such we spoof a fake mouse event at the write coordinates in the right window and use that to open the menu.
* build: fix build on non-mac
* build: oops missed a header
* fix: safely handle optional T* by checking nullptr too
* build: fix gn check and build errors
* docs: suggested changes
* feat: default `frame` to `window.webContents.mainFrame` when possible
* fix: avoid deref nullptr view
* Revert "feat: default `frame` to `window.webContents.mainFrame` when possible"
This reverts commit 2e88836819.
* fix: lint
* Remove redundant scoped objects
This code, including the comments, matches almost exactly the behavior of this argument to the function.
* Add ScopedPumpMessagesInPrivateModes patch
* More null pointer safety
---------
Co-authored-by: clavin <clavin@electronjs.org>
* feat: Working navigationHistory.restore with just title/url
* feat: Restore page state, too
* chore: Docs, lint, tests
* Implement feedback
* More magic
* Make _awaitNextLoad truly private
* Implement API group feedback
* One more round of feedback
* feat: ServiceWorkerMain
* refactor: disconnect remote
* handle version_info_ nullptr case
* initiate finish request when possible and enumerate errors
* explicit name for test method
* oops
* fix: wait for redundant version to stop before destroying
* docs: clarify when undefined is returned
* chore: remove extra semicolons