NanmiCoder/MediaCrawler · error · ValueError
[DouYinLogin.begin] Invalid Login Type Currently only suppor
Error message
[DouYinLogin.begin] Invalid Login Type Currently only supported qrcode or phone or cookie ...
What it means
ValueError from DouYinLogin.begin when config.LOGIN_TYPE is not exactly 'qrcode', 'phone', or 'cookie'. After popping up the login dialog the method dispatches on the global config string; an unknown value raises before login proceeds. (Notably this happens after popup_login_dialog, so a browser page is already open when it fires.)
Source
Thrown at media_platform/douyin/login.py:70
async def begin(self):
"""
Start login douyin website
The verification accuracy of the slider verification is not very good... If there are no special requirements, it is recommended not to use Douyin login, or use cookie login
"""
# popup login dialog
await self.popup_login_dialog()
# select login type
if config.LOGIN_TYPE == "qrcode":
await self.login_by_qrcode()
elif config.LOGIN_TYPE == "phone":
await self.login_by_mobile()
elif config.LOGIN_TYPE == "cookie":
await self.login_by_cookies()
else:
raise ValueError("[DouYinLogin.begin] Invalid Login Type Currently only supported qrcode or phone or cookie ...")
# If the page redirects to the slider verification page, need to slide again
await asyncio.sleep(6)
current_page_title = await self.context_page.title()
if "验证码中间页" in current_page_title:
await self.check_page_display_slider(move_step=3, slider_level="hard")
# check login state
utils.logger.info(f"[DouYinLogin.begin] login finished then check login state ...")
try:
await self.check_login_state()
except RetryError:
utils.logger.info("[DouYinLogin.begin] login failed please confirm ...")
sys.exit()
# wait for redirect
wait_redirect_seconds = 5
utils.logger.info(f"[DouYinLogin.begin] Login successful then wait for {wait_redirect_seconds} seconds redirect ...")View on GitHub (pinned to d6f7c5bb90)
Solutions
- Set LOGIN_TYPE to exactly one of 'qrcode', 'phone', 'cookie' (lowercase, no surrounding whitespace).
- For headless automation use 'cookie' login with a fresh cookie string; qrcode requires manual scanning.
- Assert the allowed value early at startup, before any Playwright browser is launched.
Example fix
# before config.LOGIN_TYPE = 'Cookie' # after config.LOGIN_TYPE = 'cookie'
Defensive patterns
Strategy: validation
Validate before calling
from config import config
assert config.LOGIN_TYPE in {'qrcode', 'phone', 'cookie'}, f'bad LOGIN_TYPE: {config.LOGIN_TYPE!r}' Type guard
def is_valid_login_type(t: str) -> bool:
return t in {'qrcode', 'phone', 'cookie'} Try / catch
try:
await DouYinLogin(...).begin()
except ValueError as e:
if 'Invalid Login Type' in str(e):
raise SystemExit('set LOGIN_TYPE to qrcode, phone, or cookie in config') from e Prevention
- Exact lowercase values only; watch for trailing spaces from .env parsing
- Validate before launching the browser — the error fires after the dialog pops up otherwise
- Use cookie login for automated environments
When it happens
Trigger: LOGIN_TYPE set to 'qrcode ' (trailing space), 'SMS', 'account', or empty in config/base_config.py or an environment override; CI injecting a different LOGIN_TYPE than expected.
Common situations: Hand-editing the sample config and guessing values; values read from .env files retaining quotes; case-sensitive literals copied from tutorials.
Related errors
- [BilibiliLogin.begin] Invalid Login Type Currently only supp
- Unknown cache type: {cache_type}
- Unsupported database type: {db_type}
- Invalid media platform: {platform!r}. Supported: {supported}
- Unable to parse video ID from URL: {url}
AI-assisted analysis of NanmiCoder/MediaCrawler@d6f7c5bb90 (2026-08-15).
Data as JSON: /api/errors/146e282dd73987aa.
Report an issue: GitHub.