Skip to main content

Documentation Index

Fetch the complete documentation index at: https://mintlify.com/ZemerTeam/zemer-cipher/llms.txt

Use this file to discover all available pages before exploring further.

Zemer Cipher defines four exception types. Most public API methods return null rather than throwing on recoverable failures — exceptions are reserved for conditions where the caller must explicitly handle or propagate the error.
CancellationException (from Kotlin coroutines) is always rethrown unconditionally. None of the exception handlers in this library swallow cancellation, so cooperative cancellation of coroutines works correctly throughout.

CipherException

class CipherException(message: String) : Exception(message)
Package: com.zemer.cipher Thrown when the cipher WebView itself fails — for example:
  • The player JS file failed to load from the local file cache.
  • The signature or n-transform JavaScript call returned null or undefined.
  • The JS bridge reported an error from inside the player JS evaluation.
CipherDeobfuscator catches CipherException internally and returns null after a single retry attempt, so callers rarely see this exception directly. If it surfaces to a caller, it means both the initial attempt and the retry failed at the WebView JS level.

CipherRendererGoneException

class CipherRendererGoneException(message: String) : Exception(message)
Package: com.zemer.cipher Thrown when the WebView renderer process has died (OOM kill or crash) or when a JS evaluation timed out (which is treated as an equivalent renderer death since a responsive renderer answers in milliseconds). The CipherWebView instance is permanently unusable after this exception and must be discarded — per Android documentation a WebView whose renderer process is gone cannot be reused. CipherDeobfuscator catches this internally, calls RendererRecoveryPolicy.onFailure(), and returns null without a retry. A retry with a fresh CipherWebView is attempted on the next request if RendererRecoveryPolicy.shouldAttempt() permits it.

PoTokenException

class PoTokenException(message: String) : Exception(message)
Package: com.zemer.cipher.potoken Thrown by PoTokenGenerator.getWebClientPoToken() when a JavaScript-level error occurs during BotGuard token generation and the automatic retry with a fresh WebView also fails. This indicates that the BotGuard JS itself returned an error rather than the WebView being broken. Callers that receive PoTokenException should fall through to non-web YouTube clients, which do not require a PoToken.

BadWebViewException

class BadWebViewException(message: String) : Exception(message)
Package: com.zemer.cipher.potoken Thrown when the system WebView is fundamentally broken — most commonly an old Chromium version that throws a SyntaxError when parsing the BotGuard JavaScript. PoTokenGenerator catches this internally, sets an internal webViewBadImpl = true flag, and returns null for all subsequent calls on the same instance. The condition is treated as permanent for that PoTokenGenerator instance: no further BotGuard attempts are made, avoiding repeated expensive WebView loads on a device where they can never succeed.

buildExceptionForJsError

fun buildExceptionForJsError(error: String): Exception
Package: com.zemer.cipher.potoken Helper function used internally by PoTokenGenerator to map a raw JS error string to the correct exception type. Returns BadWebViewException if error contains the substring "SyntaxError", or PoTokenException for all other error strings.
error
String
required
The raw error string received from the JavaScript bridge (typically from a caught JS exception or an error callback).
Returns: BadWebViewException if the error indicates a SyntaxError (broken WebView); PoTokenException otherwise.

Exception Hierarchy Summary

ExceptionPackageThrown byCaught internally?
CipherExceptioncom.zemer.cipherCipherWebView sig/n evaluation errorsYes — CipherDeobfuscator retries once, then returns null
CipherRendererGoneExceptioncom.zemer.cipherCipherWebView renderer death or timeoutYes — CipherDeobfuscator calls onFailure(), returns null
PoTokenExceptioncom.zemer.cipher.potokenPoTokenGenerator JS errors after retryNo — propagated to caller
BadWebViewExceptioncom.zemer.cipher.potokenPoTokenGenerator on SyntaxErrorYes — sets webViewBadImpl, returns null permanently

Build docs developers (and LLMs) love