You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Next.js自定义服务器下移动端二维码扫描HTTPS环境异常排查

二维码扫描功能在Next.js自定义HTTPS服务器移动端失效的解决方案

问题背景

二维码扫描桌面端正常,移动端无法使用;React.js HTTPS环境下功能正常,但自定义服务器的Next.js HTTPS环境下失效,移动端调试报错:无法访问媒体设备:NotAllowedError 由于用户拒绝权限请求,无法访问设备。

解决步骤

1. 完善Next.js HTTPS服务器配置

自定义HTTPS服务器必须确保证书被移动端信任,否则浏览器会默认拒绝摄像头权限:

  • 生成自签名证书后,在移动端设备手动安装并信任该证书(iOS:设置→通用→VPN与设备管理;Android:设置→安全→加密与凭据→安装证书)
  • 服务器代码中补充必要配置,避免证书验证异常:
const https = require('https');
const fs = require('fs');
const next = require('next');

const dev = process.env.NODE_ENV !== 'production';
const app = next({ dev });
const handle = app.getRequestHandler();

// 替换为你的证书路径
const options = {
  key: fs.readFileSync('./localhost-key.pem'),
  cert: fs.readFileSync('./localhost.pem'),
  rejectUnauthorized: false,
  requestCert: false
};

app.prepare().then(() => {
  https.createServer(options, (req, res) => {
    handle(req, res);
  }).listen(3000, () => {
    console.log('> Ready on https://localhost:3000');
  });
});

2. 优化摄像头权限处理

移动端对权限请求的逻辑更严格,需主动处理权限状态:

import React, { useState, useEffect } from 'react';
import { QrReader } from 'react-qr-reader';

const Home = () => {
    const [data, setData] = useState('No result');
    const [permissionStatus, setPermissionStatus] = useState(null);

    useEffect(() => {
        const requestCameraPermission = async () => {
            try {
                const stream = await navigator.mediaDevices.getUserMedia({ video: { facingMode: 'environment' } });
                stream.getTracks().forEach(track => track.stop());
                setPermissionStatus('granted');
            } catch (err) {
                setPermissionStatus('denied');
                console.error('摄像头权限请求失败:', err);
            }
        };
        requestCameraPermission();
    }, []);

    if (permissionStatus === 'denied') {
        return <p>请在浏览器设置中开启摄像头权限后重试</p>;
    }

    if (permissionStatus === null) {
        return <p>正在请求摄像头权限...</p>;
    }

    return (
        <>
            <QrReader
                constraints={{ facingMode: 'environment' }} // 指定使用后置摄像头
                onResult={(result, error) => {
                    result && setData(result.text);
                    error && console.info(error);
                }}
                style={{ width: '100%' }}
            />
            <p>{data}</p>
        </>
    );
};

export default Home;

3. 兼容性与版本检查

  • 升级react-qr-reader到最新版本,修复已知移动端兼容问题:
npm update react-qr-reader
  • 避免在iframe中嵌入扫描组件,部分移动端浏览器会限制iframe的设备访问权限
  • 确保站点使用标准HTTPS端口(443),非标准端口可能触发移动端浏览器的安全限制

内容的提问来源于stack exchange,提问作者Ming

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.25 23:24:37