add the ability to prevent downloading youtube premiere initial stream.

This commit is contained in:
arabcoders 2025-06-14 00:59:57 +03:00
parent a478e8e58d
commit bb41eadde7
8 changed files with 240 additions and 153 deletions

View file

@ -274,41 +274,42 @@ If you feel like donating and appreciate my work, you can do so by donating to c
Certain configuration values can be set via environment variables, using the `-e` parameter on the docker command line, or the `environment:` section in `compose.yaml` file. Certain configuration values can be set via environment variables, using the `-e` parameter on the docker command line, or the `environment:` section in `compose.yaml` file.
| Environment Variable | Description | Default | | Environment Variable | Description | Default |
| ------------------------ | ---------------------------------------------------------------- | ---------------------------------- | | ------------------------- | ------------------------------------------------------------------ | ---------------------------------- |
| YTP_OUTPUT_TEMPLATE | The template for the filenames of the downloaded videos | `%(title)s.%(ext)s` | | YTP_OUTPUT_TEMPLATE | The template for the filenames of the downloaded videos | `%(title)s.%(ext)s` |
| YTP_DEFAULT_PRESET | The default preset to use for the download | `default` | | YTP_DEFAULT_PRESET | The default preset to use for the download | `default` |
| YTP_INSTANCE_TITLE | The title of the instance | `empty string` | | YTP_INSTANCE_TITLE | The title of the instance | `empty string` |
| YTP_FILE_LOGGING | Whether to log to file | `false` | | YTP_FILE_LOGGING | Whether to log to file | `false` |
| YTP_DOWNLOAD_PATH | Path to where the downloads will be saved | `/downloads` | | YTP_DOWNLOAD_PATH | Path to where the downloads will be saved | `/downloads` |
| YTP_MAX_WORKERS | How many works to use for downloads | `1` | | YTP_MAX_WORKERS | How many works to use for downloads | `1` |
| YTP_AUTH_USERNAME | Username for basic authentication | `empty string` | | YTP_AUTH_USERNAME | Username for basic authentication | `empty string` |
| YTP_AUTH_PASSWORD | Password for basic authentication | `empty string` | | YTP_AUTH_PASSWORD | Password for basic authentication | `empty string` |
| YTP_CONSOLE_ENABLED | Whether to enable the console | `false` | | YTP_CONSOLE_ENABLED | Whether to enable the console | `false` |
| YTP_REMOVE_FILES | Remove the actual file when clicking the remove button | `false` | | YTP_REMOVE_FILES | Remove the actual file when clicking the remove button | `false` |
| YTP_CONFIG_PATH | Path to where the config files will be stored. | `/config` | | YTP_CONFIG_PATH | Path to where the config files will be stored. | `/config` |
| YTP_TEMP_PATH | Path to where tmp files are stored. | `/tmp` | | YTP_TEMP_PATH | Path to where tmp files are stored. | `/tmp` |
| YTP_TEMP_KEEP | Whether to keep the Individual video temp directory or remove it | `false` | | YTP_TEMP_KEEP | Whether to keep the Individual video temp directory or remove it | `false` |
| YTP_KEEP_ARCHIVE | Keep history of downloaded videos | `true` | | YTP_KEEP_ARCHIVE | Keep history of downloaded videos | `true` |
| YTP_YTDL_DEBUG | Whether to turn debug logging for the internal `yt-dlp` package | `false` | | YTP_YTDL_DEBUG | Whether to turn debug logging for the internal `yt-dlp` package | `false` |
| YTP_HOST | Which IP address to bind to | `0.0.0.0` | | YTP_HOST | Which IP address to bind to | `0.0.0.0` |
| YTP_PORT | Which port to bind to | `8081` | | YTP_PORT | Which port to bind to | `8081` |
| YTP_LOG_LEVEL | Log level | `info` | | YTP_LOG_LEVEL | Log level | `info` |
| YTP_STREAMER_VCODEC | The video codec to use for in-browser streaming | `libx264` | | YTP_STREAMER_VCODEC | The video codec to use for in-browser streaming | `libx264` |
| YTP_STREAMER_ACODEC | The audio codec to use for in-browser streaming | `aac` | | YTP_STREAMER_ACODEC | The audio codec to use for in-browser streaming | `aac` |
| YTP_ACCESS_LOG | Whether to log access to the web server | `true` | | YTP_ACCESS_LOG | Whether to log access to the web server | `true` |
| YTP_DEBUG | Whether to turn on debug mode | `false` | | YTP_DEBUG | Whether to turn on debug mode | `false` |
| YTP_DEBUGPY_PORT | The port to use for the debugpy debugger | `5678` | | YTP_DEBUGPY_PORT | The port to use for the debugpy debugger | `5678` |
| YTP_SOCKET_TIMEOUT | The timeout for the yt-dlp socket connection variable | `30` | | YTP_SOCKET_TIMEOUT | The timeout for the yt-dlp socket connection variable | `30` |
| YTP_EXTRACT_INFO_TIMEOUT | The timeout for extracting video information | `70` | | YTP_EXTRACT_INFO_TIMEOUT | The timeout for extracting video information | `70` |
| YTP_DB_FILE | The path to the SQLite database file | `{config_path}/ytptube.db` | | YTP_DB_FILE | The path to the SQLite database file | `{config_path}/ytptube.db` |
| YTP_MANUAL_ARCHIVE | The path to the manual archive file | `{config_path}/manual_archive.log` | | YTP_MANUAL_ARCHIVE | The path to the manual archive file | `{config_path}/manual_archive.log` |
| YTP_UI_UPDATE_TITLE | Whether to update the title of the page with the current stats | `true` | | YTP_UI_UPDATE_TITLE | Whether to update the title of the page with the current stats | `true` |
| YTP_PIP_PACKAGES | A space separated list of pip packages to install | `empty string` | | YTP_PIP_PACKAGES | A space separated list of pip packages to install | `empty string` |
| YTP_PIP_IGNORE_UPDATES | Do not update the custom pip packages | `false` | | YTP_PIP_IGNORE_UPDATES | Do not update the custom pip packages | `false` |
| YTP_BASIC_MODE | Whether to run WebUI in basic mode | `false` | | YTP_BASIC_MODE | Whether to run WebUI in basic mode | `false` |
| YTP_PICTURES_BACKENDS | A comma separated list of pictures urls to use. | `empty string` | | YTP_PICTURES_BACKENDS | A comma separated list of pictures urls to use. | `empty string` |
| YTP_BROWSER_ENABLED | Whether to enable the file browser | `false` | | YTP_BROWSER_ENABLED | Whether to enable the file browser | `false` |
| YTP_YTDLP_AUTO_UPDATE | Whether to enable the auto update for yt-dlp | `true` | | YTP_YTDLP_AUTO_UPDATE | Whether to enable the auto update for yt-dlp | `true` |
| YTP_BASE_PATH | Set this if you are serving YTPTube from sub-folder | `/` | | YTP_BASE_PATH | Set this if you are serving YTPTube from sub-folder | `/` |
| YTP_PREVENT_LIVE_PREMIERE | Prevents the initial youtube premiere stream from being downloaded | `false` |

View file

@ -18,6 +18,7 @@ from .config import Config
from .DataStore import DataStore from .DataStore import DataStore
from .Download import Download from .Download import Download
from .Events import EventBus, Events from .Events import EventBus, Events
from .Events import info as event_info
from .Events import warning as event_warning from .Events import warning as event_warning
from .ItemDTO import Item, ItemDTO from .ItemDTO import Item, ItemDTO
from .Presets import Presets from .Presets import Presets
@ -239,6 +240,7 @@ class DownloadQueue(metaclass=Singleton):
options: dict = {} options: dict = {}
error: str | None = None error: str | None = None
live_in: str | None = None live_in: str | None = None
is_premiere: bool = bool(entry.get("is_premiere", False))
# check if the video is live stream. # check if the video is live stream.
if "live_status" in entry and "is_upcoming" == entry.get("live_status"): if "live_status" in entry and "is_upcoming" == entry.get("live_status"):
@ -246,7 +248,7 @@ class DownloadQueue(metaclass=Singleton):
live_in = formatdate(entry.get("release_timestamp"), usegmt=True) live_in = formatdate(entry.get("release_timestamp"), usegmt=True)
item.extras.update({"live_in": live_in}) item.extras.update({"live_in": live_in})
else: else:
error = "Live stream not yet started. And no date is set." error = f"No start time is set for {'premiere' if is_premiere else 'live stream'}."
else: else:
error = entry.get("msg") error = entry.get("msg")
@ -274,7 +276,7 @@ class DownloadQueue(metaclass=Singleton):
is_live = bool(entry.get("is_live") or live_in or entry.get("live_status") in live_status) is_live = bool(entry.get("is_live") or live_in or entry.get("live_status") in live_status)
try: try:
download_dir = calc_download_path(base_path=self.config.download_path, folder=item.folder) download_dir: str = calc_download_path(base_path=self.config.download_path, folder=item.folder)
except Exception as e: except Exception as e:
LOG.exception(e) LOG.exception(e)
return {"status": "error", "msg": str(e)} return {"status": "error", "msg": str(e)}
@ -287,6 +289,14 @@ class DownloadQueue(metaclass=Singleton):
if isinstance(key, str) and key.startswith("playlist") and entry.get(key): if isinstance(key, str) and key.startswith("playlist") and entry.get(key):
item.extras[key] = entry.get(key) item.extras[key] = entry.get(key)
item.extras["duration"] = entry.get("duration", item.extras.get("duration"))
if not item.extras.get("live_in") and live_in:
item.extras["live_in"] = live_in
if not item.extras.get("live_in") and is_premiere:
item.extras["is_premiere"] = is_premiere
dl = ItemDTO( dl = ItemDTO(
id=str(entry.get("id")), id=str(entry.get("id")),
title=str(entry.get("title")), title=str(entry.get("title")),
@ -310,18 +320,20 @@ class DownloadQueue(metaclass=Singleton):
try: try:
dlInfo: Download = Download(info=dl, info_dict=entry, logs=logs) dlInfo: Download = Download(info=dl, info_dict=entry, logs=logs)
text_logs = "" text_logs: str = ""
if filtered_logs := extract_ytdlp_logs(logs): if filtered_logs := extract_ytdlp_logs(logs):
text_logs = f" Logs: {', '.join(filtered_logs)}" text_logs = f" Logs: {', '.join(filtered_logs)}"
if live_in or "is_upcoming" == entry.get("live_status"): if live_in or "is_upcoming" == entry.get("live_status"):
NotifyEvent = Events.COMPLETED NotifyEvent = Events.COMPLETED
dlInfo.info.status = "not_live" dlInfo.info.status = "not_live"
dlInfo.info.msg = "Stream is not live yet." + text_logs dlInfo.info.msg = (
itemDownload = self.done.put(dlInfo) f"{'Premiere video' if is_premiere else 'Live Stream' } is not available yet." + text_logs
)
itemDownload: Download = self.done.put(dlInfo)
elif len(entry.get("formats", [])) < 1: elif len(entry.get("formats", [])) < 1:
availability = entry.get("availability", "public") availability: str = entry.get("availability", "public")
msg = "No formats found." msg: str = "No formats found."
if availability and availability not in ("public",): if availability and availability not in ("public",):
msg += f" Availability is set for '{availability}'." msg += f" Availability is set for '{availability}'."
@ -329,7 +341,27 @@ class DownloadQueue(metaclass=Singleton):
dlInfo.info.status = "error" dlInfo.info.status = "error"
itemDownload = self.done.put(dlInfo) itemDownload = self.done.put(dlInfo)
NotifyEvent = Events.COMPLETED NotifyEvent = Events.COMPLETED
await self._notify.emit(Events.LOG_WARNING, data=event_warning(msg)) await self._notify.emit(Events.LOG_WARNING, data=event_warning(f"No formats found for '{dl.title}'."))
elif is_premiere and self.config.prevent_live_premiere:
dlInfo.info.error = (
f"Premiering right now. Delaying download by '{300+dl.extras.get('duration',0)}' seconds."
)
_live_in = live_in or item.extras.get("live_in", None)
if _live_in:
starts_in = parsedate_to_datetime(live_in)
starts_in = starts_in.replace(tzinfo=UTC) if starts_in.tzinfo is None else starts_in.astimezone(UTC)
starts_in = starts_in + timedelta(minutes=5, seconds=dl.extras.get("duration", 0))
dlInfo.info.error += f" Starts in {starts_in.isoformat()}."
dlInfo.info.status = "not_live"
itemDownload = self.done.put(dlInfo)
NotifyEvent = Events.COMPLETED
await self._notify.emit(
Events.LOG_INFO,
data=event_info(
f"'{dl.title}' is premiering. Download delayed by '{300+dl.extras.get('duration')}'s."
),
)
else: else:
NotifyEvent = Events.ADDED NotifyEvent = Events.ADDED
itemDownload = self.queue.put(dlInfo) itemDownload = self.queue.put(dlInfo)
@ -470,12 +502,10 @@ class DownloadQueue(metaclass=Singleton):
if not entry: if not entry:
return {"status": "error", "msg": "Unable to extract info." + "\n".join(logs)} return {"status": "error", "msg": "Unable to extract info." + "\n".join(logs)}
if not item.requeued: if not item.requeued and (condition := Conditions.get_instance().match(info=entry)):
condition = Conditions.get_instance().match(info=entry) already.pop()
if condition is not None: LOG.info(f"Condition '{condition.name}' matched for '{item.url}'.")
already.pop() return await self.add(item=item.new_with(requeued=True, cli=condition.cli), already=already)
LOG.info(f"Condition '{condition}' matched for '{item.url}'.")
return await self.add(item=item.new_with(requeued=True, cli=condition.cli), already=already)
end_time = time.perf_counter() - started end_time = time.perf_counter() - started
LOG.debug(f"extract_info: for 'URL: {item.url}' is done in '{end_time:.3f}'. Length: '{len(entry)}/keys'.") LOG.debug(f"extract_info: for 'URL: {item.url}' is done in '{end_time:.3f}'. Length: '{len(entry)}/keys'.")
@ -833,32 +863,44 @@ class DownloadQueue(metaclass=Singleton):
if self.is_paused() or self.done.empty(): if self.is_paused() or self.done.empty():
return return
LOG.debug("Checking for live stream items in the history queue.") LOG.debug("Checking history queue for queued live stream links.")
time_now = datetime.now(tz=UTC) time_now = datetime.now(tz=UTC)
status = ["not_live", "is_upcoming", "is_live"] status: list[str] = ["not_live", "is_upcoming", "is_live"]
for id, item in list(self.done.items()): for id, item in list(self.done.items()):
if item.info.status not in status: if item.info.status not in status:
continue continue
item_ref = f"{id=} {item.info.id=} {item.info.title=}" item_ref: str = f"{id=} {item.info.id=} {item.info.title=}"
if not item.is_live: if not item.is_live:
LOG.debug(f"Item '{item_ref}' is not a live stream.") LOG.debug(f"Item '{item_ref}' is not a live stream.")
continue continue
if not item.info.live_in: live_in: str | None = item.info.live_in or item.info.extras.get("live_in", None)
if not live_in:
LOG.debug(f"Item '{item_ref}' marked as live stream, but no date is set.") LOG.debug(f"Item '{item_ref}' marked as live stream, but no date is set.")
continue continue
starts_in = parsedate_to_datetime(item.info.live_in) starts_in = parsedate_to_datetime(live_in)
starts_in = starts_in.replace(tzinfo=UTC) if starts_in.tzinfo is None else starts_in.astimezone(UTC) starts_in = starts_in.replace(tzinfo=UTC) if starts_in.tzinfo is None else starts_in.astimezone(UTC)
if time_now < (starts_in + timedelta(minutes=1)): if time_now < (starts_in + timedelta(minutes=1)):
LOG.debug(f"Item '{item_ref}' is not yet live. will start in '{dt_delta(starts_in-time_now)}'.") LOG.debug(f"Item '{item_ref}' is not yet live. will start in '{dt_delta(starts_in-time_now)}'.")
continue continue
duration: int | None = item.info.extras.get("duration", None)
is_premiere: bool = item.info.extras.get("is_premiere", False)
if is_premiere and duration and self.config.prevent_live_premiere:
premiere_ends: datetime = starts_in + timedelta(minutes=5, seconds=duration)
if time_now < premiere_ends:
LOG.debug(
f"Item '{item_ref}' is premiering and download is delayed by '{300+duration}' seconds. Will start at '{premiere_ends.isoformat()}'"
)
continue
LOG.info(f"Re-queuing item '{item_ref} {item.info.extras=}' for download.") LOG.info(f"Re-queuing item '{item_ref} {item.info.extras=}' for download.")
try: try:
@ -868,17 +910,18 @@ class DownloadQueue(metaclass=Singleton):
continue continue
try: try:
info = item.info await self.add(
new_queue = Item( item=Item(
url=info.url, url=item.info.url,
preset=info.preset, preset=item.info.preset,
folder=info.folder, folder=item.info.folder,
cookies=info.cookies, cookies=item.info.cookies,
template=info.template, template=item.info.template,
cli=item.info.cli, cli=item.info.cli,
extras=item.info.extras, extras=item.info.extras,
)
) )
await self.add(item=new_queue)
except Exception as e: except Exception as e:
LOG.error(f"Failed to re-queue item '{item_ref}'. {e!s}") self.done.put(item)
LOG.exception(e) LOG.exception(e)
LOG.error(f"Failed to re-queue item '{item_ref}'. {e!s}")

View file

@ -17,6 +17,7 @@ from typing import TypeVar
import yt_dlp import yt_dlp
from Crypto.Cipher import AES from Crypto.Cipher import AES
from yt_dlp.utils import match_str
from .LogWrapper import LogWrapper from .LogWrapper import LogWrapper
@ -59,7 +60,8 @@ FILES_TYPE: list = [
{"rx": re.compile(r"\.(nfo|json|jpg|torrent|\.info\.json)$", re.IGNORECASE), "type": "metadata"}, {"rx": re.compile(r"\.(nfo|json|jpg|torrent|\.info\.json)$", re.IGNORECASE), "type": "metadata"},
] ]
DATETIME_PATTERN = re.compile(r"^(\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}(?:\.\d+)?(?:[+-]\d{2}:\d{2}))\s?") TAG_REGEX: re.Pattern[str] = re.compile(r"%{([^:}]+)(?::([^}]*))?}c")
DT_PATTERN: re.Pattern[str] = re.compile(r"^(\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}(?:\.\d+)?(?:[+-]\d{2}:\d{2}))\s?")
T = TypeVar("T") T = TypeVar("T")
@ -204,6 +206,10 @@ def extract_info(
if not data: if not data:
return data return data
data["is_premiere"] = match_str("media_type=video & duration & is_live", data)
if not data["is_premiere"]:
data["is_premiere"] = "video" == data.get("media_type") and "is_upcoming" == data.get("live_status")
return yt_dlp.YoutubeDL.sanitize_info(data) if sanitize_info else data return yt_dlp.YoutubeDL.sanitize_info(data) if sanitize_info else data
@ -963,7 +969,7 @@ async def read_logfile(file: Path, offset: int = 0, limit: int = 50) -> dict:
for line in lines[-(offset + limit) : -offset] if offset else lines[-limit:]: for line in lines[-(offset + limit) : -offset] if offset else lines[-limit:]:
line_bytes = line if isinstance(line, bytes) else line.encode() line_bytes = line if isinstance(line, bytes) else line.encode()
msg = line.decode(errors="replace") msg = line.decode(errors="replace")
dt_match = DATETIME_PATTERN.match(msg) dt_match = DT_PATTERN.match(msg)
result.append( result.append(
{ {
"id": sha256(line_bytes).hexdigest(), "id": sha256(line_bytes).hexdigest(),
@ -1005,7 +1011,7 @@ async def tail_log(file: Path, emitter: callable, sleep_time: float = 0.5):
continue continue
msg = line.decode(errors="replace") msg = line.decode(errors="replace")
dt_match = DATETIME_PATTERN.match(msg) dt_match = DT_PATTERN.match(msg)
await emitter( await emitter(
{ {
@ -1228,3 +1234,25 @@ def load_modules(root_path: Path, directory: Path):
importlib.import_module(full_name) importlib.import_module(full_name)
except ImportError as e: except ImportError as e:
LOG.error(f"Failed to import module '{full_name}': {e}") LOG.error(f"Failed to import module '{full_name}': {e}")
def parse_tags(text: str) -> tuple[str, dict[str, str | bool]]:
"""
Parse tags from a string formatted with %{tag_name[:value]}c.
Args:
text (str): The input string containing tags.
Returns:
tuple[str, dict[str, str | bool]]: A tuple containing the string with tags removed and a dictionary of tags.
"""
tags: dict[str, str | bool] = {}
def replacer(match: re.Match) -> str:
name = match.group(1)
value = match.group(2)
tags[name] = value if value is not None else True
return ""
return TAG_REGEX.sub(replacer, text).strip(), tags

View file

@ -158,6 +158,9 @@ class Config:
is_native: bool = False is_native: bool = False
"Is the application running in webview." "Is the application running in webview."
prevent_live_premiere: bool = False
"""Prevent downloading of the initial premiere live broadcast."""
pictures_backends: list[str] = [ pictures_backends: list[str] = [
"https://unsplash.it/1920/1080?random", "https://unsplash.it/1920/1080?random",
"https://picsum.photos/1920/1080", "https://picsum.photos/1920/1080",
@ -209,6 +212,7 @@ class Config:
"console_enabled", "console_enabled",
"browser_enabled", "browser_enabled",
"ytdlp_auto_update", "ytdlp_auto_update",
"prevent_premiere_live",
) )
"The variables that are booleans." "The variables that are booleans."

View file

@ -537,6 +537,9 @@ const setIcon = item => {
if (!item.filename) { if (!item.filename) {
return 'fa-solid fa-exclamation' return 'fa-solid fa-exclamation'
} }
if (item.extras?.is_premiere) {
return 'fa-solid fa-star'
}
return item.is_live ? 'fa-solid fa-globe' : 'fa-solid fa-circle-check' return item.is_live ? 'fa-solid fa-globe' : 'fa-solid fa-circle-check'
} }
@ -549,7 +552,7 @@ const setIcon = item => {
} }
if ('not_live' === item.status) { if ('not_live' === item.status) {
return 'fa-solid fa-headset' return item.extras?.is_premiere ? 'fa-solid fa-star' : 'fa-solid fa-headset'
} }
return 'fa-solid fa-circle' return 'fa-solid fa-circle'
@ -579,6 +582,11 @@ const setStatus = item => {
if (!item.filename) { if (!item.filename) {
return 'Skipped?' return 'Skipped?'
} }
if (item.extras?.is_premiere) {
return 'Premiere'
}
return item.is_live ? 'Live Ended' : 'Completed' return item.is_live ? 'Live Ended' : 'Completed'
} }
@ -591,6 +599,9 @@ const setStatus = item => {
} }
if ('not_live' === item.status) { if ('not_live' === item.status) {
if (item.extras?.is_premiere){
return 'Premiere'
}
return display_style.value === 'cards' ? 'Live Stream' : 'Live' return display_style.value === 'cards' ? 'Live Stream' : 'Live'
} }

View file

@ -32,7 +32,7 @@
<hr class="navbar-divider"> <hr class="navbar-divider">
</template> </template>
<div class="notification-list"> <div class="notification-list">
<div v-for="n in store.notifications" :key="n.id" class="navbar-item is-flex is-align-items-start" <div v-for="n in store.notifications" :key="n.id" class="pr-1 pl-1 navbar-item is-flex is-align-items-start"
:class="['notification-item', 'notification-' + n.level]"> :class="['notification-item', 'notification-' + n.level]">
<div class="is-flex-grow-1"> <div class="is-flex-grow-1">
<p class="is-size-7 mb-1 notification-message" :class="{ expanded: expandedId === n.id }" <p class="is-size-7 mb-1 notification-message" :class="{ expanded: expandedId === n.id }"

View file

@ -12,7 +12,7 @@
"web-types": "./web-types.json", "web-types": "./web-types.json",
"dependencies": { "dependencies": {
"@pinia/nuxt": "^0.11.1", "@pinia/nuxt": "^0.11.1",
"@sentry/nuxt": "^9.28.1", "@sentry/nuxt": "^9.29.0",
"@vueuse/core": "^13.3.0", "@vueuse/core": "^13.3.0",
"@vueuse/nuxt": "^13.3.0", "@vueuse/nuxt": "^13.3.0",
"@xterm/addon-fit": "^0.10.0", "@xterm/addon-fit": "^0.10.0",

View file

@ -12,8 +12,8 @@ importers:
specifier: ^0.11.1 specifier: ^0.11.1
version: 0.11.1(magicast@0.3.5)(pinia@3.0.3(typescript@5.8.3)(vue@3.5.16(typescript@5.8.3))) version: 0.11.1(magicast@0.3.5)(pinia@3.0.3(typescript@5.8.3)(vue@3.5.16(typescript@5.8.3)))
'@sentry/nuxt': '@sentry/nuxt':
specifier: ^9.28.1 specifier: ^9.29.0
version: 9.28.1(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.34.0)(magicast@0.3.5)(nuxt@3.17.5(@parcel/watcher@2.5.1)(@types/node@24.0.1)(db0@0.3.2)(ioredis@5.6.1)(magicast@0.3.5)(rollup@4.43.0)(terser@5.42.0)(typescript@5.8.3)(vite@6.3.5(@types/node@24.0.1)(jiti@2.4.2)(terser@5.42.0)(yaml@2.8.0))(yaml@2.8.0))(pinia@3.0.3(typescript@5.8.3)(vue@3.5.16(typescript@5.8.3)))(rollup@4.43.0)(vue@3.5.16(typescript@5.8.3)) version: 9.29.0(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.34.0)(magicast@0.3.5)(nuxt@3.17.5(@parcel/watcher@2.5.1)(@types/node@24.0.1)(db0@0.3.2)(ioredis@5.6.1)(magicast@0.3.5)(rollup@4.43.0)(terser@5.42.0)(typescript@5.8.3)(vite@6.3.5(@types/node@24.0.1)(jiti@2.4.2)(terser@5.42.0)(yaml@2.8.0))(yaml@2.8.0))(pinia@3.0.3(typescript@5.8.3)(vue@3.5.16(typescript@5.8.3)))(rollup@4.43.0)(vue@3.5.16(typescript@5.8.3))
'@vueuse/core': '@vueuse/core':
specifier: ^13.3.0 specifier: ^13.3.0
version: 13.3.0(vue@3.5.16(typescript@5.8.3)) version: 13.3.0(vue@3.5.16(typescript@5.8.3))
@ -1066,40 +1066,40 @@ packages:
cpu: [x64] cpu: [x64]
os: [win32] os: [win32]
'@sentry-internal/browser-utils@9.28.1': '@sentry-internal/browser-utils@9.29.0':
resolution: {integrity: sha512-P/FEZkT7UqTw9P/2n/Y4Aa1OtGP6dnCvyqzPPkjiRdVa7Ep7S5ElBJloGv7077TLLBtAfCsEUVRlM1F6/jQoaA==} resolution: {integrity: sha512-Wp6UJCDVV2KVK+TG8GwdLZyDy4GtUYDmVhGMpHKPS3G/Qgpf36cY/XHwChwaHZ5P9Bk1sjS9Ok698J59S8L2nw==}
engines: {node: '>=18'} engines: {node: '>=18'}
'@sentry-internal/feedback@9.28.1': '@sentry-internal/feedback@9.29.0':
resolution: {integrity: sha512-HOk/c26D3nlClO/xEefev8fIJzRA621PFQvNFPu/y0Z5HujEqSmIsrff0cXszPPYD95h4Mwk63E0ZYdspdeXcw==} resolution: {integrity: sha512-ADvetGrtr+RfYcQKrQxah4fHs/xDJ/VjbStVMSuaNllzwWPYNkWIGFE6YjQ7wZszj0DQIu5/H+B6lZKsFYk4xw==}
engines: {node: '>=18'} engines: {node: '>=18'}
'@sentry-internal/replay-canvas@9.28.1': '@sentry-internal/replay-canvas@9.29.0':
resolution: {integrity: sha512-RtkogfcIpXLFCyV8CTnXmVTH2QauT/KwmUAXBbeOz3rRWsM19yjN1moHrsjxn7OdjTv+D4qWSCA8Ka1aKSpr7g==} resolution: {integrity: sha512-TrQYhSAVPhyenvu0fNkon7BznFibu1mzS5bCudxhgOWajZluUVrXcbp8Q3WZ3R+AogrcgA3Vy6aumP/+fMKdwg==}
engines: {node: '>=18'} engines: {node: '>=18'}
'@sentry-internal/replay@9.28.1': '@sentry-internal/replay@9.29.0':
resolution: {integrity: sha512-Tv9pkfAX+1bmhxF42TL0c4uTiK2+rp5LMYEPdz6JBfpfvG/Z1unPGsuB7fQmHYKyfHBQJmi92DZV+smljm7w/g==} resolution: {integrity: sha512-we/1JPRje8sNowQCyogOV1OYWuDOP/3XmDi48XoFG2HB0XMl2HfL5LI8AvgAvC/5nrqVAAo4ktbjoVLm1fb7rg==}
engines: {node: '>=18'} engines: {node: '>=18'}
'@sentry/babel-plugin-component-annotate@3.2.4': '@sentry/babel-plugin-component-annotate@3.2.4':
resolution: {integrity: sha512-yBzRn3GEUSv1RPtE4xB4LnuH74ZxtdoRJ5cmQ9i6mzlmGDxlrnKuvem5++AolZTE9oJqAD3Tx2rd1PqmpWnLoA==} resolution: {integrity: sha512-yBzRn3GEUSv1RPtE4xB4LnuH74ZxtdoRJ5cmQ9i6mzlmGDxlrnKuvem5++AolZTE9oJqAD3Tx2rd1PqmpWnLoA==}
engines: {node: '>= 14'} engines: {node: '>= 14'}
'@sentry/babel-plugin-component-annotate@3.4.0': '@sentry/babel-plugin-component-annotate@3.5.0':
resolution: {integrity: sha512-tSzfc3aE7m0PM0Aj7HBDet5llH9AB9oc+tBQ8AvOqUSnWodLrNCuWeQszJ7mIBovD3figgCU3h0cvI6U5cDtsg==} resolution: {integrity: sha512-s2go8w03CDHbF9luFGtBHKJp4cSpsQzNVqgIa9Pfa4wnjipvrK6CxVT4icpLA3YO6kg5u622Yoa5GF3cJdippw==}
engines: {node: '>= 14'} engines: {node: '>= 14'}
'@sentry/browser@9.28.1': '@sentry/browser@9.29.0':
resolution: {integrity: sha512-XAS46iQSq8lXTnv9udQP025JTf3PwSVRE9ePJVQhx25QBWxedqGhEOv5qqX9b1Ijf8KiZYXXhBWMQxBBXVzUaw==} resolution: {integrity: sha512-+GFX/yb+rh6V1fSgTYM6ttAgledl2aUR3T3Rg86HNuegbdX8ym6lOtUOIZ0j9jPK015HR47KIPyIZVZZJ7Rj9g==}
engines: {node: '>=18'} engines: {node: '>=18'}
'@sentry/bundler-plugin-core@3.2.4': '@sentry/bundler-plugin-core@3.2.4':
resolution: {integrity: sha512-YMj9XW5W2JA89EeweE7CPKLDz245LBsI1JhCmqpt/bjSvmsSIAAPsLYnvIJBS3LQFm0OhtG8NB54PTi96dAcMA==} resolution: {integrity: sha512-YMj9XW5W2JA89EeweE7CPKLDz245LBsI1JhCmqpt/bjSvmsSIAAPsLYnvIJBS3LQFm0OhtG8NB54PTi96dAcMA==}
engines: {node: '>= 14'} engines: {node: '>= 14'}
'@sentry/bundler-plugin-core@3.4.0': '@sentry/bundler-plugin-core@3.5.0':
resolution: {integrity: sha512-X1Q41AsQ6xcT6hB4wYmBDBukndKM/inT4IsR7pdKLi7ICpX2Qq6lisamBAEPCgEvnLpazSFguaiC0uiwMKAdqw==} resolution: {integrity: sha512-zDzPrhJqAAy2VzV4g540qAZH4qxzisstK2+NIJPZUUKztWRWUV2cMHsyUtdctYgloGkLyGpZJBE3RE6dmP/xqQ==}
engines: {node: '>= 14'} engines: {node: '>= 14'}
'@sentry/cli-darwin@2.42.2': '@sentry/cli-darwin@2.42.2':
@ -1148,22 +1148,22 @@ packages:
engines: {node: '>= 10'} engines: {node: '>= 10'}
hasBin: true hasBin: true
'@sentry/core@9.28.1': '@sentry/core@9.29.0':
resolution: {integrity: sha512-6q59r/71MeE+4StkvwdKAAyhBBNpWcii0HeiWBZ3l1gaFYQlb6bChjZJRZmxSzF5dnvkdF4duQbAC3JmjeIbPA==} resolution: {integrity: sha512-wDyNe45PM+RCGtUn1tK7LzJ08ksv8i8KRUHrst7lsinEfRm83YH+wbWrPmwkVNEngUZvYkHwGLbNXM7xgFUuDQ==}
engines: {node: '>=18'} engines: {node: '>=18'}
'@sentry/node@9.28.1': '@sentry/node@9.29.0':
resolution: {integrity: sha512-1bC8ywFPs1EIKzRlUhLoreTR/fUU45O+ezVNvOu0I6JURMwjyC8uT23f0Xkiolx4WjKZXER+d0el3HojPaYkYw==} resolution: {integrity: sha512-oABipgC/fClRuvyMeK43rigv9F+OAaoR84UaMKB7aPXN6iz634wBRVsaoZAwiR3xLL+R7MafEPPA/s9XqlG7ag==}
engines: {node: '>=18'} engines: {node: '>=18'}
'@sentry/nuxt@9.28.1': '@sentry/nuxt@9.29.0':
resolution: {integrity: sha512-+QhmFywTq5BL9tK7Yq7j6o6/B31l2fAn/ZULmIlJLAlgnKsexVS/Dbhlbal/deMi0tLLQPxbEtOtZ86PbQpKdg==} resolution: {integrity: sha512-bstQwiqgB6n4/23NYDb8pl7B7wICSJaZoIbTjAhceiog1yVtdQZsQa8iRyCwDpdzU7NyOhfCT1ECQ98EdwDJog==}
engines: {node: '>=18.19.1'} engines: {node: '>=18.19.1'}
peerDependencies: peerDependencies:
nuxt: '>=3.7.0 || 4.x' nuxt: '>=3.7.0 || 4.x'
'@sentry/opentelemetry@9.28.1': '@sentry/opentelemetry@9.29.0':
resolution: {integrity: sha512-1xxriB2diNSlNpkMosdgIKzPOPwAiyFg7XgEWKpLtDYWj7WVbLNyLkUWriFr4JgU40uZp3LW+sGgnshA48/zQQ==} resolution: {integrity: sha512-QTUmre8i5+832RjzQW+g8IQ3UmBe5fbQXGbCF5hQ0UNuHle9r3Z8UZcIff5W8tm5AXMxPqvptTnDEZUUXHgBiA==}
engines: {node: '>=18'} engines: {node: '>=18'}
peerDependencies: peerDependencies:
'@opentelemetry/api': ^1.9.0 '@opentelemetry/api': ^1.9.0
@ -1173,8 +1173,8 @@ packages:
'@opentelemetry/sdk-trace-base': ^1.30.1 || ^2.0.0 '@opentelemetry/sdk-trace-base': ^1.30.1 || ^2.0.0
'@opentelemetry/semantic-conventions': ^1.34.0 '@opentelemetry/semantic-conventions': ^1.34.0
'@sentry/rollup-plugin@3.4.0': '@sentry/rollup-plugin@3.5.0':
resolution: {integrity: sha512-oqDcjV+aaTZZ7oOadk90KlShOYfKEEQsvbZtzHl7HPHNt5kmtTaQyWphPIDt2Z9OCK8QF5T8GLsr1MCOXJ6vqA==} resolution: {integrity: sha512-aMPCvdNMkv//LZYjYCJsEcNiNiaQFinBO75+9NJVEe1OrKNdGqDi3hky2ll7zuY+xozEtZCZcUKJJz/aAYAS8A==}
engines: {node: '>= 14'} engines: {node: '>= 14'}
peerDependencies: peerDependencies:
rollup: '>=3.2.0' rollup: '>=3.2.0'
@ -1183,8 +1183,8 @@ packages:
resolution: {integrity: sha512-ZRn5TLlq5xtwKOqaWP+XqS1PYVfbBCgsbMk7wW2Ly6EgF9wYePvtLqKgYnE3hwPg2LpBnRPR2ti1ohlUkR+wXA==} resolution: {integrity: sha512-ZRn5TLlq5xtwKOqaWP+XqS1PYVfbBCgsbMk7wW2Ly6EgF9wYePvtLqKgYnE3hwPg2LpBnRPR2ti1ohlUkR+wXA==}
engines: {node: '>= 14'} engines: {node: '>= 14'}
'@sentry/vue@9.28.1': '@sentry/vue@9.29.0':
resolution: {integrity: sha512-o6b2rQpbEjvNgyUDd7dVjjKwFfembf0ltd4MW78F2CoAYMS/YkHAum/iZ/5wOB4pYhutPbeDDZf0s6aM5KCOZQ==} resolution: {integrity: sha512-wwKHgW2RFpn91UQuClYiI6Tt8VkQ36dGxiVT8l98uGC0uPXzwz40ikdBgnOMt3qwbRZX8ziEXHjjTtAxdETe3w==}
engines: {node: '>=18'} engines: {node: '>=18'}
peerDependencies: peerDependencies:
pinia: 2.x || 3.x pinia: 2.x || 3.x
@ -1595,8 +1595,8 @@ packages:
caniuse-api@3.0.0: caniuse-api@3.0.0:
resolution: {integrity: sha512-bsTwuIg/BZZK/vreVTYYbSWoe2F+71P7K5QGEX+pT250DZbfU1MQ5prOKpPR+LL6uWKK3KMwMCAS74QB3Um1uw==} resolution: {integrity: sha512-bsTwuIg/BZZK/vreVTYYbSWoe2F+71P7K5QGEX+pT250DZbfU1MQ5prOKpPR+LL6uWKK3KMwMCAS74QB3Um1uw==}
caniuse-lite@1.0.30001722: caniuse-lite@1.0.30001723:
resolution: {integrity: sha512-DCQHBBZtiK6JVkAGw7drvAMK0Q0POD/xZvEmDp6baiMMP6QXXk9HpD6mNYBZWhOPG6LvIDb82ITqtWjhDckHCA==} resolution: {integrity: sha512-1R/elMjtehrFejxwmexeXAtae5UO9iSyFn6G/I806CYC/BLyyBk1EPhrKBkWhy6wM6Xnm47dSJQec+tLJ39WHw==}
chokidar@3.6.0: chokidar@3.6.0:
resolution: {integrity: sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw==} resolution: {integrity: sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw==}
@ -2337,8 +2337,8 @@ packages:
image-meta@0.2.1: image-meta@0.2.1:
resolution: {integrity: sha512-K6acvFaelNxx8wc2VjbIzXKDVB0Khs0QT35U6NkGfTdCmjLNcO2945m7RFNR9/RPVFm48hq7QPzK8uGH18HCGw==} resolution: {integrity: sha512-K6acvFaelNxx8wc2VjbIzXKDVB0Khs0QT35U6NkGfTdCmjLNcO2945m7RFNR9/RPVFm48hq7QPzK8uGH18HCGw==}
import-in-the-middle@1.14.0: import-in-the-middle@1.14.2:
resolution: {integrity: sha512-g5zLT0HaztRJWysayWYiUq/7E5H825QIiecMD2pI5QO7Wzr847l6GDvPvmZaDIdrDtS2w7qRczywxiK6SL5vRw==} resolution: {integrity: sha512-5tCuY9BV8ujfOpwtAGgsTx9CGUapcFMEEyByLv1B+v2+6DhAcw+Zr0nhQT7uwaZ7DiourxFEscghOR8e1aPLQw==}
impound@1.0.0: impound@1.0.0:
resolution: {integrity: sha512-8lAJ+1Arw2sMaZ9HE2ZmL5zOcMnt18s6+7Xqgq2aUVy4P1nlzAyPtzCDxsk51KVFwHEEdc6OWvUyqwHwhRYaug==} resolution: {integrity: sha512-8lAJ+1Arw2sMaZ9HE2ZmL5zOcMnt18s6+7Xqgq2aUVy4P1nlzAyPtzCDxsk51KVFwHEEdc6OWvUyqwHwhRYaug==}
@ -4090,8 +4090,8 @@ packages:
resolution: {integrity: sha512-zK7YHHz4ZXpW89AHXUPbQVGKI7uvkd3hzusTdotCg1UxyaVtg0zFJSTfW/Dq5f7OBBVnq6cZIaC8Ti4hb6dtCA==} resolution: {integrity: sha512-zK7YHHz4ZXpW89AHXUPbQVGKI7uvkd3hzusTdotCg1UxyaVtg0zFJSTfW/Dq5f7OBBVnq6cZIaC8Ti4hb6dtCA==}
engines: {node: '>= 14'} engines: {node: '>= 14'}
zod@3.25.63: zod@3.25.64:
resolution: {integrity: sha512-3ttCkqhtpncYXfP0f6dsyabbYV/nEUW+Xlu89jiXbTBifUfjaSqXOG6JnQPLtqt87n7KAmnMqcjay6c0Wq0Vbw==} resolution: {integrity: sha512-hbP9FpSZf7pkS7hRVUrOjhwKJNyampPgtXKc3AN6DsWtoHsg2Sb4SQaS4Tcay380zSwd2VPo9G9180emBACp5g==}
snapshots: snapshots:
@ -4532,7 +4532,7 @@ snapshots:
unixify: 1.0.0 unixify: 1.0.0
urlpattern-polyfill: 8.0.2 urlpattern-polyfill: 8.0.2
yargs: 17.7.2 yargs: 17.7.2
zod: 3.25.63 zod: 3.25.64
transitivePeerDependencies: transitivePeerDependencies:
- encoding - encoding
- rollup - rollup
@ -4966,7 +4966,7 @@ snapshots:
'@opentelemetry/api': 1.9.0 '@opentelemetry/api': 1.9.0
'@opentelemetry/api-logs': 0.57.2 '@opentelemetry/api-logs': 0.57.2
'@types/shimmer': 1.2.0 '@types/shimmer': 1.2.0
import-in-the-middle: 1.14.0 import-in-the-middle: 1.14.2
require-in-the-middle: 7.5.2 require-in-the-middle: 7.5.2
semver: 7.7.2 semver: 7.7.2
shimmer: 1.2.1 shimmer: 1.2.1
@ -5264,35 +5264,35 @@ snapshots:
'@rollup/rollup-win32-x64-msvc@4.43.0': '@rollup/rollup-win32-x64-msvc@4.43.0':
optional: true optional: true
'@sentry-internal/browser-utils@9.28.1': '@sentry-internal/browser-utils@9.29.0':
dependencies: dependencies:
'@sentry/core': 9.28.1 '@sentry/core': 9.29.0
'@sentry-internal/feedback@9.28.1': '@sentry-internal/feedback@9.29.0':
dependencies: dependencies:
'@sentry/core': 9.28.1 '@sentry/core': 9.29.0
'@sentry-internal/replay-canvas@9.28.1': '@sentry-internal/replay-canvas@9.29.0':
dependencies: dependencies:
'@sentry-internal/replay': 9.28.1 '@sentry-internal/replay': 9.29.0
'@sentry/core': 9.28.1 '@sentry/core': 9.29.0
'@sentry-internal/replay@9.28.1': '@sentry-internal/replay@9.29.0':
dependencies: dependencies:
'@sentry-internal/browser-utils': 9.28.1 '@sentry-internal/browser-utils': 9.29.0
'@sentry/core': 9.28.1 '@sentry/core': 9.29.0
'@sentry/babel-plugin-component-annotate@3.2.4': {} '@sentry/babel-plugin-component-annotate@3.2.4': {}
'@sentry/babel-plugin-component-annotate@3.4.0': {} '@sentry/babel-plugin-component-annotate@3.5.0': {}
'@sentry/browser@9.28.1': '@sentry/browser@9.29.0':
dependencies: dependencies:
'@sentry-internal/browser-utils': 9.28.1 '@sentry-internal/browser-utils': 9.29.0
'@sentry-internal/feedback': 9.28.1 '@sentry-internal/feedback': 9.29.0
'@sentry-internal/replay': 9.28.1 '@sentry-internal/replay': 9.29.0
'@sentry-internal/replay-canvas': 9.28.1 '@sentry-internal/replay-canvas': 9.29.0
'@sentry/core': 9.28.1 '@sentry/core': 9.29.0
'@sentry/bundler-plugin-core@3.2.4': '@sentry/bundler-plugin-core@3.2.4':
dependencies: dependencies:
@ -5308,10 +5308,10 @@ snapshots:
- encoding - encoding
- supports-color - supports-color
'@sentry/bundler-plugin-core@3.4.0': '@sentry/bundler-plugin-core@3.5.0':
dependencies: dependencies:
'@babel/core': 7.27.4 '@babel/core': 7.27.4
'@sentry/babel-plugin-component-annotate': 3.4.0 '@sentry/babel-plugin-component-annotate': 3.5.0
'@sentry/cli': 2.42.2 '@sentry/cli': 2.42.2
dotenv: 16.5.0 dotenv: 16.5.0
find-up: 5.0.0 find-up: 5.0.0
@ -5362,9 +5362,9 @@ snapshots:
- encoding - encoding
- supports-color - supports-color
'@sentry/core@9.28.1': {} '@sentry/core@9.29.0': {}
'@sentry/node@9.28.1': '@sentry/node@9.29.0':
dependencies: dependencies:
'@opentelemetry/api': 1.9.0 '@opentelemetry/api': 1.9.0
'@opentelemetry/context-async-hooks': 1.30.1(@opentelemetry/api@1.9.0) '@opentelemetry/context-async-hooks': 1.30.1(@opentelemetry/api@1.9.0)
@ -5396,23 +5396,23 @@ snapshots:
'@opentelemetry/sdk-trace-base': 1.30.1(@opentelemetry/api@1.9.0) '@opentelemetry/sdk-trace-base': 1.30.1(@opentelemetry/api@1.9.0)
'@opentelemetry/semantic-conventions': 1.34.0 '@opentelemetry/semantic-conventions': 1.34.0
'@prisma/instrumentation': 6.8.2(@opentelemetry/api@1.9.0) '@prisma/instrumentation': 6.8.2(@opentelemetry/api@1.9.0)
'@sentry/core': 9.28.1 '@sentry/core': 9.29.0
'@sentry/opentelemetry': 9.28.1(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.34.0) '@sentry/opentelemetry': 9.29.0(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.34.0)
import-in-the-middle: 1.14.0 import-in-the-middle: 1.14.2
minimatch: 9.0.5 minimatch: 9.0.5
transitivePeerDependencies: transitivePeerDependencies:
- supports-color - supports-color
'@sentry/nuxt@9.28.1(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.34.0)(magicast@0.3.5)(nuxt@3.17.5(@parcel/watcher@2.5.1)(@types/node@24.0.1)(db0@0.3.2)(ioredis@5.6.1)(magicast@0.3.5)(rollup@4.43.0)(terser@5.42.0)(typescript@5.8.3)(vite@6.3.5(@types/node@24.0.1)(jiti@2.4.2)(terser@5.42.0)(yaml@2.8.0))(yaml@2.8.0))(pinia@3.0.3(typescript@5.8.3)(vue@3.5.16(typescript@5.8.3)))(rollup@4.43.0)(vue@3.5.16(typescript@5.8.3))': '@sentry/nuxt@9.29.0(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.34.0)(magicast@0.3.5)(nuxt@3.17.5(@parcel/watcher@2.5.1)(@types/node@24.0.1)(db0@0.3.2)(ioredis@5.6.1)(magicast@0.3.5)(rollup@4.43.0)(terser@5.42.0)(typescript@5.8.3)(vite@6.3.5(@types/node@24.0.1)(jiti@2.4.2)(terser@5.42.0)(yaml@2.8.0))(yaml@2.8.0))(pinia@3.0.3(typescript@5.8.3)(vue@3.5.16(typescript@5.8.3)))(rollup@4.43.0)(vue@3.5.16(typescript@5.8.3))':
dependencies: dependencies:
'@nuxt/kit': 3.17.5(magicast@0.3.5) '@nuxt/kit': 3.17.5(magicast@0.3.5)
'@sentry/browser': 9.28.1 '@sentry/browser': 9.29.0
'@sentry/core': 9.28.1 '@sentry/core': 9.29.0
'@sentry/node': 9.28.1 '@sentry/node': 9.29.0
'@sentry/opentelemetry': 9.28.1(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.34.0) '@sentry/opentelemetry': 9.29.0(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.34.0)
'@sentry/rollup-plugin': 3.4.0(rollup@4.43.0) '@sentry/rollup-plugin': 3.5.0(rollup@4.43.0)
'@sentry/vite-plugin': 3.2.4 '@sentry/vite-plugin': 3.2.4
'@sentry/vue': 9.28.1(pinia@3.0.3(typescript@5.8.3)(vue@3.5.16(typescript@5.8.3)))(vue@3.5.16(typescript@5.8.3)) '@sentry/vue': 9.29.0(pinia@3.0.3(typescript@5.8.3)(vue@3.5.16(typescript@5.8.3)))(vue@3.5.16(typescript@5.8.3))
nuxt: 3.17.5(@parcel/watcher@2.5.1)(@types/node@24.0.1)(db0@0.3.2)(ioredis@5.6.1)(magicast@0.3.5)(rollup@4.43.0)(terser@5.42.0)(typescript@5.8.3)(vite@6.3.5(@types/node@24.0.1)(jiti@2.4.2)(terser@5.42.0)(yaml@2.8.0))(yaml@2.8.0) nuxt: 3.17.5(@parcel/watcher@2.5.1)(@types/node@24.0.1)(db0@0.3.2)(ioredis@5.6.1)(magicast@0.3.5)(rollup@4.43.0)(terser@5.42.0)(typescript@5.8.3)(vite@6.3.5(@types/node@24.0.1)(jiti@2.4.2)(terser@5.42.0)(yaml@2.8.0))(yaml@2.8.0)
transitivePeerDependencies: transitivePeerDependencies:
- '@opentelemetry/api' - '@opentelemetry/api'
@ -5428,7 +5428,7 @@ snapshots:
- supports-color - supports-color
- vue - vue
'@sentry/opentelemetry@9.28.1(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.34.0)': '@sentry/opentelemetry@9.29.0(@opentelemetry/api@1.9.0)(@opentelemetry/context-async-hooks@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/core@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/instrumentation@0.57.2(@opentelemetry/api@1.9.0))(@opentelemetry/sdk-trace-base@1.30.1(@opentelemetry/api@1.9.0))(@opentelemetry/semantic-conventions@1.34.0)':
dependencies: dependencies:
'@opentelemetry/api': 1.9.0 '@opentelemetry/api': 1.9.0
'@opentelemetry/context-async-hooks': 1.30.1(@opentelemetry/api@1.9.0) '@opentelemetry/context-async-hooks': 1.30.1(@opentelemetry/api@1.9.0)
@ -5436,11 +5436,11 @@ snapshots:
'@opentelemetry/instrumentation': 0.57.2(@opentelemetry/api@1.9.0) '@opentelemetry/instrumentation': 0.57.2(@opentelemetry/api@1.9.0)
'@opentelemetry/sdk-trace-base': 1.30.1(@opentelemetry/api@1.9.0) '@opentelemetry/sdk-trace-base': 1.30.1(@opentelemetry/api@1.9.0)
'@opentelemetry/semantic-conventions': 1.34.0 '@opentelemetry/semantic-conventions': 1.34.0
'@sentry/core': 9.28.1 '@sentry/core': 9.29.0
'@sentry/rollup-plugin@3.4.0(rollup@4.43.0)': '@sentry/rollup-plugin@3.5.0(rollup@4.43.0)':
dependencies: dependencies:
'@sentry/bundler-plugin-core': 3.4.0 '@sentry/bundler-plugin-core': 3.5.0
rollup: 4.43.0 rollup: 4.43.0
unplugin: 1.0.1 unplugin: 1.0.1
transitivePeerDependencies: transitivePeerDependencies:
@ -5455,10 +5455,10 @@ snapshots:
- encoding - encoding
- supports-color - supports-color
'@sentry/vue@9.28.1(pinia@3.0.3(typescript@5.8.3)(vue@3.5.16(typescript@5.8.3)))(vue@3.5.16(typescript@5.8.3))': '@sentry/vue@9.29.0(pinia@3.0.3(typescript@5.8.3)(vue@3.5.16(typescript@5.8.3)))(vue@3.5.16(typescript@5.8.3))':
dependencies: dependencies:
'@sentry/browser': 9.28.1 '@sentry/browser': 9.29.0
'@sentry/core': 9.28.1 '@sentry/core': 9.29.0
vue: 3.5.16(typescript@5.8.3) vue: 3.5.16(typescript@5.8.3)
optionalDependencies: optionalDependencies:
pinia: 3.0.3(typescript@5.8.3)(vue@3.5.16(typescript@5.8.3)) pinia: 3.0.3(typescript@5.8.3)(vue@3.5.16(typescript@5.8.3))
@ -5864,7 +5864,7 @@ snapshots:
autoprefixer@10.4.21(postcss@8.5.5): autoprefixer@10.4.21(postcss@8.5.5):
dependencies: dependencies:
browserslist: 4.25.0 browserslist: 4.25.0
caniuse-lite: 1.0.30001722 caniuse-lite: 1.0.30001723
fraction.js: 4.3.7 fraction.js: 4.3.7
normalize-range: 0.1.2 normalize-range: 0.1.2
picocolors: 1.1.1 picocolors: 1.1.1
@ -5900,7 +5900,7 @@ snapshots:
browserslist@4.25.0: browserslist@4.25.0:
dependencies: dependencies:
caniuse-lite: 1.0.30001722 caniuse-lite: 1.0.30001723
electron-to-chromium: 1.5.167 electron-to-chromium: 1.5.167
node-releases: 2.0.19 node-releases: 2.0.19
update-browserslist-db: 1.1.3(browserslist@4.25.0) update-browserslist-db: 1.1.3(browserslist@4.25.0)
@ -5956,11 +5956,11 @@ snapshots:
caniuse-api@3.0.0: caniuse-api@3.0.0:
dependencies: dependencies:
browserslist: 4.25.0 browserslist: 4.25.0
caniuse-lite: 1.0.30001722 caniuse-lite: 1.0.30001723
lodash.memoize: 4.1.2 lodash.memoize: 4.1.2
lodash.uniq: 4.5.0 lodash.uniq: 4.5.0
caniuse-lite@1.0.30001722: {} caniuse-lite@1.0.30001723: {}
chokidar@3.6.0: chokidar@3.6.0:
dependencies: dependencies:
@ -6708,7 +6708,7 @@ snapshots:
image-meta@0.2.1: {} image-meta@0.2.1: {}
import-in-the-middle@1.14.0: import-in-the-middle@1.14.2:
dependencies: dependencies:
acorn: 8.15.0 acorn: 8.15.0
acorn-import-attributes: 1.9.5(acorn@8.15.0) acorn-import-attributes: 1.9.5(acorn@8.15.0)
@ -8592,4 +8592,4 @@ snapshots:
compress-commons: 6.0.2 compress-commons: 6.0.2
readable-stream: 4.7.0 readable-stream: 4.7.0
zod@3.25.63: {} zod@3.25.64: {}