Path: blob/trunk/py/selenium/webdriver/common/bidi/storage.py
1864 views
# Licensed to the Software Freedom Conservancy (SFC) under one1# or more contributor license agreements. See the NOTICE file2# distributed with this work for additional information3# regarding copyright ownership. The SFC licenses this file4# to you under the Apache License, Version 2.0 (the5# "License"); you may not use this file except in compliance6# with the License. You may obtain a copy of the License at7#8# http://www.apache.org/licenses/LICENSE-2.09#10# Unless required by applicable law or agreed to in writing,11# software distributed under the License is distributed on an12# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY13# KIND, either express or implied. See the License for the14# specific language governing permissions and limitations15# under the License.1617from typing import Any, Optional, Union1819from selenium.webdriver.common.bidi.common import command_builder202122class SameSite:23"""Represents the possible same site values for cookies."""2425STRICT = "strict"26LAX = "lax"27NONE = "none"28DEFAULT = "default"293031class BytesValue:32"""Represents a bytes value."""3334TYPE_BASE64 = "base64"35TYPE_STRING = "string"3637def __init__(self, type: str, value: str):38self.type = type39self.value = value4041def to_dict(self) -> dict:42"""Converts the BytesValue to a dictionary.4344Returns:45-------46Dict: A dictionary representation of the BytesValue.47"""48return {"type": self.type, "value": self.value}495051class Cookie:52"""Represents a cookie."""5354def __init__(55self,56name: str,57value: BytesValue,58domain: str,59path: Optional[str] = None,60size: Optional[int] = None,61http_only: Optional[bool] = None,62secure: Optional[bool] = None,63same_site: Optional[str] = None,64expiry: Optional[int] = None,65):66self.name = name67self.value = value68self.domain = domain69self.path = path70self.size = size71self.http_only = http_only72self.secure = secure73self.same_site = same_site74self.expiry = expiry7576@classmethod77def from_dict(cls, data: dict) -> "Cookie":78"""Creates a Cookie instance from a dictionary.7980Parameters:81-----------82data: A dictionary containing the cookie information.8384Returns:85-------86Cookie: A new instance of Cookie.87"""88# Validation for empty strings89name = data.get("name")90if not name:91raise ValueError("name is required and cannot be empty")92domain = data.get("domain")93if not domain:94raise ValueError("domain is required and cannot be empty")9596value = BytesValue(data.get("value", {}).get("type"), data.get("value", {}).get("value"))97return cls(98name=str(name),99value=value,100domain=str(domain),101path=data.get("path"),102size=data.get("size"),103http_only=data.get("httpOnly"),104secure=data.get("secure"),105same_site=data.get("sameSite"),106expiry=data.get("expiry"),107)108109110class CookieFilter:111"""Represents a filter for cookies."""112113def __init__(114self,115name: Optional[str] = None,116value: Optional[BytesValue] = None,117domain: Optional[str] = None,118path: Optional[str] = None,119size: Optional[int] = None,120http_only: Optional[bool] = None,121secure: Optional[bool] = None,122same_site: Optional[str] = None,123expiry: Optional[int] = None,124):125self.name = name126self.value = value127self.domain = domain128self.path = path129self.size = size130self.http_only = http_only131self.secure = secure132self.same_site = same_site133self.expiry = expiry134135def to_dict(self) -> dict[str, Any]:136"""Converts the CookieFilter to a dictionary.137138Returns:139-------140Dict: A dictionary representation of the CookieFilter.141"""142result: dict[str, Any] = {}143if self.name is not None:144result["name"] = self.name145if self.value is not None:146result["value"] = self.value.to_dict()147if self.domain is not None:148result["domain"] = self.domain149if self.path is not None:150result["path"] = self.path151if self.size is not None:152result["size"] = self.size153if self.http_only is not None:154result["httpOnly"] = self.http_only155if self.secure is not None:156result["secure"] = self.secure157if self.same_site is not None:158result["sameSite"] = self.same_site159if self.expiry is not None:160result["expiry"] = self.expiry161return result162163164class PartitionKey:165"""Represents a storage partition key."""166167def __init__(self, user_context: Optional[str] = None, source_origin: Optional[str] = None):168self.user_context = user_context169self.source_origin = source_origin170171@classmethod172def from_dict(cls, data: dict) -> "PartitionKey":173"""Creates a PartitionKey instance from a dictionary.174175Parameters:176-----------177data: A dictionary containing the partition key information.178179Returns:180-------181PartitionKey: A new instance of PartitionKey.182"""183return cls(184user_context=data.get("userContext"),185source_origin=data.get("sourceOrigin"),186)187188189class BrowsingContextPartitionDescriptor:190"""Represents a browsing context partition descriptor."""191192def __init__(self, context: str):193self.type = "context"194self.context = context195196def to_dict(self) -> dict:197"""Converts the BrowsingContextPartitionDescriptor to a dictionary.198199Returns:200-------201Dict: A dictionary representation of the BrowsingContextPartitionDescriptor.202"""203return {"type": self.type, "context": self.context}204205206class StorageKeyPartitionDescriptor:207"""Represents a storage key partition descriptor."""208209def __init__(self, user_context: Optional[str] = None, source_origin: Optional[str] = None):210self.type = "storageKey"211self.user_context = user_context212self.source_origin = source_origin213214def to_dict(self) -> dict:215"""Converts the StorageKeyPartitionDescriptor to a dictionary.216217Returns:218-------219Dict: A dictionary representation of the StorageKeyPartitionDescriptor.220"""221result = {"type": self.type}222if self.user_context is not None:223result["userContext"] = self.user_context224if self.source_origin is not None:225result["sourceOrigin"] = self.source_origin226return result227228229class PartialCookie:230"""Represents a partial cookie for setting."""231232def __init__(233self,234name: str,235value: BytesValue,236domain: str,237path: Optional[str] = None,238http_only: Optional[bool] = None,239secure: Optional[bool] = None,240same_site: Optional[str] = None,241expiry: Optional[int] = None,242):243self.name = name244self.value = value245self.domain = domain246self.path = path247self.http_only = http_only248self.secure = secure249self.same_site = same_site250self.expiry = expiry251252def to_dict(self) -> dict[str, Any]:253"""Converts the PartialCookie to a dictionary.254255Returns:256-------257Dict: A dictionary representation of the PartialCookie.258"""259result: dict[str, Any] = {260"name": self.name,261"value": self.value.to_dict(),262"domain": self.domain,263}264if self.path is not None:265result["path"] = self.path266if self.http_only is not None:267result["httpOnly"] = self.http_only268if self.secure is not None:269result["secure"] = self.secure270if self.same_site is not None:271result["sameSite"] = self.same_site272if self.expiry is not None:273result["expiry"] = self.expiry274return result275276277class GetCookiesResult:278"""Represents the result of a getCookies command."""279280def __init__(self, cookies: list[Cookie], partition_key: PartitionKey):281self.cookies = cookies282self.partition_key = partition_key283284@classmethod285def from_dict(cls, data: dict) -> "GetCookiesResult":286"""Creates a GetCookiesResult instance from a dictionary.287288Parameters:289-----------290data: A dictionary containing the get cookies result information.291292Returns:293-------294GetCookiesResult: A new instance of GetCookiesResult.295"""296cookies = [Cookie.from_dict(cookie) for cookie in data.get("cookies", [])]297partition_key = PartitionKey.from_dict(data.get("partitionKey", {}))298return cls(cookies=cookies, partition_key=partition_key)299300301class SetCookieResult:302"""Represents the result of a setCookie command."""303304def __init__(self, partition_key: PartitionKey):305self.partition_key = partition_key306307@classmethod308def from_dict(cls, data: dict) -> "SetCookieResult":309"""Creates a SetCookieResult instance from a dictionary.310311Parameters:312-----------313data: A dictionary containing the set cookie result information.314315Returns:316-------317SetCookieResult: A new instance of SetCookieResult.318"""319partition_key = PartitionKey.from_dict(data.get("partitionKey", {}))320return cls(partition_key=partition_key)321322323class DeleteCookiesResult:324"""Represents the result of a deleteCookies command."""325326def __init__(self, partition_key: PartitionKey):327self.partition_key = partition_key328329@classmethod330def from_dict(cls, data: dict) -> "DeleteCookiesResult":331"""Creates a DeleteCookiesResult instance from a dictionary.332333Parameters:334-----------335data: A dictionary containing the delete cookies result information.336337Returns:338-------339DeleteCookiesResult: A new instance of DeleteCookiesResult.340"""341partition_key = PartitionKey.from_dict(data.get("partitionKey", {}))342return cls(partition_key=partition_key)343344345class Storage:346"""BiDi implementation of the storage module."""347348def __init__(self, conn):349self.conn = conn350351def get_cookies(352self,353filter: Optional[CookieFilter] = None,354partition: Optional[Union[BrowsingContextPartitionDescriptor, StorageKeyPartitionDescriptor]] = None,355) -> GetCookiesResult:356"""Retrieves cookies that match the given parameters.357358Parameters:359-----------360filter: Optional filter to match cookies.361partition: Optional partition descriptor.362363Returns:364-------365GetCookiesResult: The result of the get cookies command.366"""367params = {}368if filter is not None:369params["filter"] = filter.to_dict()370if partition is not None:371params["partition"] = partition.to_dict()372373result = self.conn.execute(command_builder("storage.getCookies", params))374return GetCookiesResult.from_dict(result)375376def set_cookie(377self,378cookie: PartialCookie,379partition: Optional[Union[BrowsingContextPartitionDescriptor, StorageKeyPartitionDescriptor]] = None,380) -> SetCookieResult:381"""Sets a cookie in the browser.382383Parameters:384-----------385cookie: The cookie to set.386partition: Optional partition descriptor.387388Returns:389-------390SetCookieResult: The result of the set cookie command.391"""392params = {"cookie": cookie.to_dict()}393if partition is not None:394params["partition"] = partition.to_dict()395396result = self.conn.execute(command_builder("storage.setCookie", params))397return SetCookieResult.from_dict(result)398399def delete_cookies(400self,401filter: Optional[CookieFilter] = None,402partition: Optional[Union[BrowsingContextPartitionDescriptor, StorageKeyPartitionDescriptor]] = None,403) -> DeleteCookiesResult:404"""Deletes cookies that match the given parameters.405406Parameters:407-----------408filter: Optional filter to match cookies to delete.409partition: Optional partition descriptor.410411Returns:412-------413DeleteCookiesResult: The result of the delete cookies command.414"""415params = {}416if filter is not None:417params["filter"] = filter.to_dict()418if partition is not None:419params["partition"] = partition.to_dict()420421result = self.conn.execute(command_builder("storage.deleteCookies", params))422return DeleteCookiesResult.from_dict(result)423424425