11import { ScriptType , detectScriptType } from '../utils/detectScriptType' ;
2+ import { isInternalOrigin } from '../utils/isInternalOrigin' ;
23
34import { bridgeMessenger } from './internal/bridge' ;
5+ import { CallbackOptions , Messenger } from './internal/createMessenger' ;
46import { extensionMessenger } from './internal/extension' ;
57import { tabMessenger } from './internal/tab' ;
68import { windowMessenger } from './internal/window' ;
@@ -19,6 +21,34 @@ type InitializeMessengerArgs = {
1921 connect : ScriptType ;
2022} ;
2123
24+ /**
25+ * Wraps a messenger to validate that all incoming messages originate from
26+ * extension URLs. This prevents cross-origin message handler bypass attacks
27+ * where malicious websites attempt to send messages to privileged handlers.
28+ */
29+ function withOriginValidation ( messenger : Messenger ) : Messenger {
30+ return {
31+ ...messenger ,
32+ reply < TPayload , TResponse > (
33+ topic : string ,
34+ callback : (
35+ payload : TPayload ,
36+ options : CallbackOptions ,
37+ ) => Promise < TResponse > ,
38+ ) {
39+ return messenger . reply < TPayload , TResponse > (
40+ topic ,
41+ async ( payload , options ) => {
42+ if ( ! isInternalOrigin ( options . sender , `messenger:${ topic } ` ) ) {
43+ return { error : 'Invalid origin' } as TResponse ;
44+ }
45+ return callback ( payload , options ) ;
46+ } ,
47+ ) ;
48+ } ,
49+ } ;
50+ }
51+
2252export function initializeMessenger ( { connect } : InitializeMessengerArgs ) {
2353 const source = detectScriptType ( ) ;
2454 const connections = [
@@ -31,5 +61,13 @@ export function initializeMessenger({ connect }: InitializeMessengerArgs) {
3161 `No messenger found for connection ${ source } <-> ${ connect } .` ,
3262 ) ;
3363
34- return messengersForConnection [ connection ] ;
64+ const messenger = messengersForConnection [ connection ] ;
65+
66+ // When background expects messages from popup, enforce origin validation
67+ // to prevent cross-origin message handler bypass attacks
68+ if ( source === 'background' && connect === 'popup' ) {
69+ return withOriginValidation ( messenger ) ;
70+ }
71+
72+ return messenger ;
3573}
0 commit comments