Page Menu
Home
Software Heritage
Search
Configure Global Search
Log In
Files
F9125572
scope.js
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Award Token
Flag For Later
Size
12 KB
Subscribers
None
scope.js
View Options
import
{
isPlainObject
,
dateTimestampInSeconds
,
getGlobalSingleton
,
SyncPromise
,
logger
,
isThenable
}
from
'@sentry/utils'
;
import
{
updateSession
}
from
'./session.js'
;
/**
* Absolute maximum number of breadcrumbs added to an event.
* The `maxBreadcrumbs` option cannot be higher than this value.
*/
var
MAX_BREADCRUMBS
=
100
;
/**
* Holds additional event information. {@link Scope.applyToEvent} will be
* called by the client before an event will be sent.
*/
class
Scope
{
/** Flag if notifying is happening. */
/** Callback for client to receive scope changes. */
/** Callback list that will be called after {@link applyToEvent}. */
/** Array of breadcrumbs. */
/** User */
/** Tags */
/** Extra */
/** Contexts */
/** Attachments */
/**
* A place to stash data which is needed at some point in the SDK's event processing pipeline but which shouldn't get
* sent to Sentry
*/
/** Fingerprint */
/** Severity */
/** Transaction Name */
/** Span */
/** Session */
/** Request Mode Session Status */
constructor
()
{
this
.
_notifyingListeners
=
false
;
this
.
_scopeListeners
=
[];
this
.
_eventProcessors
=
[];
this
.
_breadcrumbs
=
[];
this
.
_attachments
=
[];
this
.
_user
=
{};
this
.
_tags
=
{};
this
.
_extra
=
{};
this
.
_contexts
=
{};
this
.
_sdkProcessingMetadata
=
{};
}
/**
* Inherit values from the parent scope.
* @param scope to clone.
*/
static
clone
(
scope
)
{
var
newScope
=
new
Scope
();
if
(
scope
)
{
newScope
.
_breadcrumbs
=
[...
scope
.
_breadcrumbs
];
newScope
.
_tags
=
{
...
scope
.
_tags
};
newScope
.
_extra
=
{
...
scope
.
_extra
};
newScope
.
_contexts
=
{
...
scope
.
_contexts
};
newScope
.
_user
=
scope
.
_user
;
newScope
.
_level
=
scope
.
_level
;
newScope
.
_span
=
scope
.
_span
;
newScope
.
_session
=
scope
.
_session
;
newScope
.
_transactionName
=
scope
.
_transactionName
;
newScope
.
_fingerprint
=
scope
.
_fingerprint
;
newScope
.
_eventProcessors
=
[...
scope
.
_eventProcessors
];
newScope
.
_requestSession
=
scope
.
_requestSession
;
newScope
.
_attachments
=
[...
scope
.
_attachments
];
}
return
newScope
;
}
/**
* Add internal on change listener. Used for sub SDKs that need to store the scope.
* @hidden
*/
addScopeListener
(
callback
)
{
this
.
_scopeListeners
.
push
(
callback
);
}
/**
* @inheritDoc
*/
addEventProcessor
(
callback
)
{
this
.
_eventProcessors
.
push
(
callback
);
return
this
;
}
/**
* @inheritDoc
*/
setUser
(
user
)
{
this
.
_user
=
user
||
{};
if
(
this
.
_session
)
{
updateSession
(
this
.
_session
,
{
user
});
}
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
getUser
()
{
return
this
.
_user
;
}
/**
* @inheritDoc
*/
getRequestSession
()
{
return
this
.
_requestSession
;
}
/**
* @inheritDoc
*/
setRequestSession
(
requestSession
)
{
this
.
_requestSession
=
requestSession
;
return
this
;
}
/**
* @inheritDoc
*/
setTags
(
tags
)
{
this
.
_tags
=
{
...
this
.
_tags
,
...
tags
,
};
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
setTag
(
key
,
value
)
{
this
.
_tags
=
{
...
this
.
_tags
,
[
key
]
:
value
};
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
setExtras
(
extras
)
{
this
.
_extra
=
{
...
this
.
_extra
,
...
extras
,
};
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
setExtra
(
key
,
extra
)
{
this
.
_extra
=
{
...
this
.
_extra
,
[
key
]
:
extra
};
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
setFingerprint
(
fingerprint
)
{
this
.
_fingerprint
=
fingerprint
;
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
setLevel
(
level
,
)
{
this
.
_level
=
level
;
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
setTransactionName
(
name
)
{
this
.
_transactionName
=
name
;
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
setContext
(
key
,
context
)
{
if
(
context
===
null
)
{
delete
this
.
_contexts
[
key
];
}
else
{
this
.
_contexts
=
{
...
this
.
_contexts
,
[
key
]
:
context
};
}
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
setSpan
(
span
)
{
this
.
_span
=
span
;
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
getSpan
()
{
return
this
.
_span
;
}
/**
* @inheritDoc
*/
getTransaction
()
{
// Often, this span (if it exists at all) will be a transaction, but it's not guaranteed to be. Regardless, it will
// have a pointer to the currently-active transaction.
var
span
=
this
.
getSpan
();
return
span
&&
span
.
transaction
;
}
/**
* @inheritDoc
*/
setSession
(
session
)
{
if
(
!
session
)
{
delete
this
.
_session
;
}
else
{
this
.
_session
=
session
;
}
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
getSession
()
{
return
this
.
_session
;
}
/**
* @inheritDoc
*/
update
(
captureContext
)
{
if
(
!
captureContext
)
{
return
this
;
}
if
(
typeof
captureContext
===
'function'
)
{
var
updatedScope
=
(
captureContext
)(
this
);
return
updatedScope
instanceof
Scope
?
updatedScope
:
this
;
}
if
(
captureContext
instanceof
Scope
)
{
this
.
_tags
=
{
...
this
.
_tags
,
...
captureContext
.
_tags
};
this
.
_extra
=
{
...
this
.
_extra
,
...
captureContext
.
_extra
};
this
.
_contexts
=
{
...
this
.
_contexts
,
...
captureContext
.
_contexts
};
if
(
captureContext
.
_user
&&
Object
.
keys
(
captureContext
.
_user
).
length
)
{
this
.
_user
=
captureContext
.
_user
;
}
if
(
captureContext
.
_level
)
{
this
.
_level
=
captureContext
.
_level
;
}
if
(
captureContext
.
_fingerprint
)
{
this
.
_fingerprint
=
captureContext
.
_fingerprint
;
}
if
(
captureContext
.
_requestSession
)
{
this
.
_requestSession
=
captureContext
.
_requestSession
;
}
}
else
if
(
isPlainObject
(
captureContext
))
{
captureContext
=
captureContext
;
this
.
_tags
=
{
...
this
.
_tags
,
...
captureContext
.
tags
};
this
.
_extra
=
{
...
this
.
_extra
,
...
captureContext
.
extra
};
this
.
_contexts
=
{
...
this
.
_contexts
,
...
captureContext
.
contexts
};
if
(
captureContext
.
user
)
{
this
.
_user
=
captureContext
.
user
;
}
if
(
captureContext
.
level
)
{
this
.
_level
=
captureContext
.
level
;
}
if
(
captureContext
.
fingerprint
)
{
this
.
_fingerprint
=
captureContext
.
fingerprint
;
}
if
(
captureContext
.
requestSession
)
{
this
.
_requestSession
=
captureContext
.
requestSession
;
}
}
return
this
;
}
/**
* @inheritDoc
*/
clear
()
{
this
.
_breadcrumbs
=
[];
this
.
_tags
=
{};
this
.
_extra
=
{};
this
.
_user
=
{};
this
.
_contexts
=
{};
this
.
_level
=
undefined
;
this
.
_transactionName
=
undefined
;
this
.
_fingerprint
=
undefined
;
this
.
_requestSession
=
undefined
;
this
.
_span
=
undefined
;
this
.
_session
=
undefined
;
this
.
_notifyScopeListeners
();
this
.
_attachments
=
[];
return
this
;
}
/**
* @inheritDoc
*/
addBreadcrumb
(
breadcrumb
,
maxBreadcrumbs
)
{
var
maxCrumbs
=
typeof
maxBreadcrumbs
===
'number'
?
Math
.
min
(
maxBreadcrumbs
,
MAX_BREADCRUMBS
)
:
MAX_BREADCRUMBS
;
// No data has been changed, so don't notify scope listeners
if
(
maxCrumbs
<=
0
)
{
return
this
;
}
var
mergedBreadcrumb
=
{
timestamp
:
dateTimestampInSeconds
(),
...
breadcrumb
,
};
this
.
_breadcrumbs
=
[...
this
.
_breadcrumbs
,
mergedBreadcrumb
].
slice
(
-
maxCrumbs
);
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
clearBreadcrumbs
()
{
this
.
_breadcrumbs
=
[];
this
.
_notifyScopeListeners
();
return
this
;
}
/**
* @inheritDoc
*/
addAttachment
(
attachment
)
{
this
.
_attachments
.
push
(
attachment
);
return
this
;
}
/**
* @inheritDoc
*/
getAttachments
()
{
return
this
.
_attachments
;
}
/**
* @inheritDoc
*/
clearAttachments
()
{
this
.
_attachments
=
[];
return
this
;
}
/**
* Applies the current context and fingerprint to the event.
* Note that breadcrumbs will be added by the client.
* Also if the event has already breadcrumbs on it, we do not merge them.
* @param event Event
* @param hint May contain additional information about the original exception.
* @hidden
*/
applyToEvent
(
event
,
hint
=
{})
{
if
(
this
.
_extra
&&
Object
.
keys
(
this
.
_extra
).
length
)
{
event
.
extra
=
{
...
this
.
_extra
,
...
event
.
extra
};
}
if
(
this
.
_tags
&&
Object
.
keys
(
this
.
_tags
).
length
)
{
event
.
tags
=
{
...
this
.
_tags
,
...
event
.
tags
};
}
if
(
this
.
_user
&&
Object
.
keys
(
this
.
_user
).
length
)
{
event
.
user
=
{
...
this
.
_user
,
...
event
.
user
};
}
if
(
this
.
_contexts
&&
Object
.
keys
(
this
.
_contexts
).
length
)
{
event
.
contexts
=
{
...
this
.
_contexts
,
...
event
.
contexts
};
}
if
(
this
.
_level
)
{
event
.
level
=
this
.
_level
;
}
if
(
this
.
_transactionName
)
{
event
.
transaction
=
this
.
_transactionName
;
}
// We want to set the trace context for normal events only if there isn't already
// a trace context on the event. There is a product feature in place where we link
// errors with transaction and it relies on that.
if
(
this
.
_span
)
{
event
.
contexts
=
{
trace
:
this
.
_span
.
getTraceContext
(),
...
event
.
contexts
};
var
transactionName
=
this
.
_span
.
transaction
&&
this
.
_span
.
transaction
.
name
;
if
(
transactionName
)
{
event
.
tags
=
{
transaction
:
transactionName
,
...
event
.
tags
};
}
}
this
.
_applyFingerprint
(
event
);
event
.
breadcrumbs
=
[...(
event
.
breadcrumbs
||
[]),
...
this
.
_breadcrumbs
];
event
.
breadcrumbs
=
event
.
breadcrumbs
.
length
>
0
?
event
.
breadcrumbs
:
undefined
;
event
.
sdkProcessingMetadata
=
{
...
event
.
sdkProcessingMetadata
,
...
this
.
_sdkProcessingMetadata
};
return
this
.
_notifyEventProcessors
([...
getGlobalEventProcessors
(),
...
this
.
_eventProcessors
],
event
,
hint
);
}
/**
* Add data which will be accessible during event processing but won't get sent to Sentry
*/
setSDKProcessingMetadata
(
newData
)
{
this
.
_sdkProcessingMetadata
=
{
...
this
.
_sdkProcessingMetadata
,
...
newData
};
return
this
;
}
/**
* This will be called after {@link applyToEvent} is finished.
*/
_notifyEventProcessors
(
processors
,
event
,
hint
,
index
=
0
,
)
{
return
new
SyncPromise
((
resolve
,
reject
)
=>
{
var
processor
=
processors
[
index
];
if
(
event
===
null
||
typeof
processor
!==
'function'
)
{
resolve
(
event
);
}
else
{
var
result
=
processor
({
...
event
},
hint
)
;
(
typeof
__SENTRY_DEBUG__
===
'undefined'
||
__SENTRY_DEBUG__
)
&&
processor
.
id
&&
result
===
null
&&
logger
.
log
(
`Event processor "
${
processor
.
id
}
" dropped event`
);
if
(
isThenable
(
result
))
{
void
result
.
then
(
final
=>
this
.
_notifyEventProcessors
(
processors
,
final
,
hint
,
index
+
1
).
then
(
resolve
))
.
then
(
null
,
reject
);
}
else
{
void
this
.
_notifyEventProcessors
(
processors
,
result
,
hint
,
index
+
1
)
.
then
(
resolve
)
.
then
(
null
,
reject
);
}
}
});
}
/**
* This will be called on every set call.
*/
_notifyScopeListeners
()
{
// We need this check for this._notifyingListeners to be able to work on scope during updates
// If this check is not here we'll produce endless recursion when something is done with the scope
// during the callback.
if
(
!
this
.
_notifyingListeners
)
{
this
.
_notifyingListeners
=
true
;
this
.
_scopeListeners
.
forEach
(
callback
=>
{
callback
(
this
);
});
this
.
_notifyingListeners
=
false
;
}
}
/**
* Applies fingerprint from the scope to the event if there's one,
* uses message if there's one instead or get rid of empty fingerprint
*/
_applyFingerprint
(
event
)
{
// Make sure it's an array first and we actually have something in place
event
.
fingerprint
=
event
.
fingerprint
?
Array
.
isArray
(
event
.
fingerprint
)
?
event
.
fingerprint
:
[
event
.
fingerprint
]
:
[];
// If we have something on the scope, then merge it with event
if
(
this
.
_fingerprint
)
{
event
.
fingerprint
=
event
.
fingerprint
.
concat
(
this
.
_fingerprint
);
}
// If we have no data at all, remove empty array default
if
(
event
.
fingerprint
&&
!
event
.
fingerprint
.
length
)
{
delete
event
.
fingerprint
;
}
}
}
/**
* Returns the global event processors.
*/
function
getGlobalEventProcessors
()
{
return
getGlobalSingleton
(
'globalEventProcessors'
,
()
=>
[]);
}
/**
* Add a EventProcessor to be kept globally.
* @param callback EventProcessor to add
*/
function
addGlobalEventProcessor
(
callback
)
{
getGlobalEventProcessors
().
push
(
callback
);
}
export
{
Scope
,
addGlobalEventProcessor
};
//# sourceMappingURL=scope.js.map
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Sat, Jun 21, 9:04 PM (4 w, 11 h ago)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
3298403
Attached To
rDWAPPS Web applications
Event Timeline
Log In to Comment