如何在文本框中的客户端验证 youtube url

How to validate youtube url in client side in text box

我必须创建一个文本框,它只允许您管 url 视频。

为了在服务器端处理验证,我使用 below code

$rx = '~
    ^(?:https?://)?              # Optional protocol
     (?:www\.)?                  # Optional subdomain
     (?:youtube\.com|youtu\.be)  # Mandatory domain name
     /watch\?v=([^&]+)           # URI with video id as capture group 1
     ~x';

$has_match = preg_match($rx, $url, $matches);

我一直在寻找用于客户端验证的相同解决方案。我找到了 <input type="url"> here,但它似乎只适用于 html5 浏览器。

是否可以对文本框进行客户端验证,以便与所有浏览器兼容?

谢谢

转义正则表达式中存在的所有正斜杠,然后将修改后的正则表达式放在 / 定界符内,没有任何空格或注释行,并且您不需要添加 x 修饰符。

var re = /^(?:https?:\/\/)?(?:www\.)?(?:youtube\.com|youtu\.be)\/watch\?v=([^&]+)/m;

这是验证 youtube 的代码 url-

function validateYouTubeUrl()
{
    var url = $('#youTubeUrl').val();
        if (url != undefined || url != '') {
            var regExp = /^.*(youtu.be\/|v\/|u\/\w\/|embed\/|watch\?v=|\&v=|\?v=)([^#\&\?]*).*/;
            var match = url.match(regExp);
            if (match && match[2].length == 11) {
                // Do anything for being valid
                // if need to change the url to embed url then use below line
                $('#ytplayerSide').attr('src', 'https://www.youtube.com/embed/' + match[2] + '?autoplay=0');
            }
            else {
                // Do anything for not being valid
            }
        }
}

Fiddle Url: https://jsfiddle.net/cpjushnn/12/

查看这个工作示例:

function matchYoutubeUrl(url) {
    var p = /^(?:https?:\/\/)?(?:m\.|www\.)?(?:youtu\.be\/|youtube\.com\/(?:embed\/|v\/|watch\?v=|watch\?.+&v=))((\w|-){11})(?:\S+)?$/;
    if(url.match(p)){
        return url.match(p)[1];
    }
    return false;
}

已更新 Fiddle:http://jsfiddle.net/3ouq9u3v/13/

结合这里的答案和一些修改,我想出了这个正则表达式:

^(?:https?:\/\/)?(?:m\.|www\.)?(?:youtu\.be\/|youtube\.com\/(?:embed\/|v\/|watch\?v=|watch\?.+&v=))((\w|-){11})(\?\S*)?$

这将匹配任何格式,但如果 id 超过 11 个字符,则会不匹配。还可以添加带有“?”的开始视频标签部分在最后。

大家可以粘贴测试一下into this

再次更新。 (又是 18/Mar/2022) 据我所知,到目前为止我已经确定了 6 种情况(我编造了这些名称):

正常Url

  1. https://www.youtube.com/watch?v=12345678901

分享Url

  1. https://youtu.be/12345678901

分享Url与开始时间

  1. https://youtu.be/12345678901?t=6

手机浏览器url

  1. https://m.youtube.com/watch?v=12345678901&list=RD12345678901&start_radio=1

长url

  1. https://www.youtube.com/watch?v=12345678901&list=RD12345678901&start_radio=1&rv=smKgVuS

长 url 开始时间

  1. https://www.youtube.com/watch?v=12345678901&list=RD12345678901&start_radio=1&rv=12345678901&t=38

我最初根据 Jitendras 的回答提供了一个扩展的答案,因为它似乎有一些差距。例如,较短的共享 url 例如 https://youtu.be/abcdefgh_ij 如果你在末尾添加字符,Jitendras 没有捕捉到它。此外,如果用户在错误已存在时删除了文本字段中的值,则该值不会被删除。

但是,我假设原始发布者实际上想在 iframe 嵌入中使用 URL,而此处的 none 答案将适用于此。嵌入的url格式不同,需要处理

下面是我正在做的事情,以获取用户输入、验证它、将其替换为格式正确的可嵌入 url,然后将其分配给 iframe 以在 UI 上显示。

注意:下面将处理以上所有内容,但不会显示以上所有内容。即它将格式化开始时间 url 以嵌入它,但您将丢失开始时间。但我相信您可以进行一些定制。

可能对某人有好处....

function validateVideoLinkTitle() {

    document.getElementById('TitleImageUrl').value = null;
    document.getElementById('TitleImageValidationField').value = null;
    document.getElementById('CardDynamicImage').src = '/images/cardimage.png';

    var ArticleTitleVideoField = document.getElementById("ArticleTitleVideoField");
    var VideoLinkText = ArticleTitleVideoField.value;
    var ArticleTitleVideoValidation = document.getElementById("ArticleTitleVideoValidation");
    var ArticleTitleImageSizeValidation = document.getElementById("ArticleTitleImageSizeValidation");
    ArticleTitleImageSizeValidation.style.display = 'none';
    var ArticleTitleImageTypeValidation = document.getElementById("ArticleTitleImageTypeValidation");
    ArticleTitleImageTypeValidation.style.display = 'none';
    var CardDynamicImageDiv = document.getElementById("CardDynamicImageDiv");
    CardDynamicImageDiv.style.display = 'none';
    var CardDynamicVideoDiv = document.getElementById("CardDynamicVideoDiv");
    CardDynamicVideoDiv.style.display = 'block';

    var urlType = 0;

    if ((VideoLinkText.includes("watch?v=") || VideoLinkText.includes("https://m.youtube") || VideoLinkText.includes("watch?app=desktop&v=")) && !VideoLinkText == "") {
        urlType = 1;
    } else if ((VideoLinkText.includes("embed") && !VideoLinkText == "")) {
        urlType = 2;
    } else if ((VideoLinkText.includes("tu.be") && !VideoLinkText == "")) {
        urlType = 3;
    }
    console.log('title urlType:' + urlType);

    switch (urlType) {
        case 1:
            var endOfString = VideoLinkText.split(/=(.*)/)[1];
            var stringLength = endOfString.length;
            console.log('title stringLength 1: ' + stringLength);

            var p = /^(?:https?:\/\/)?(?:m\.|www\.)?(?:youtu\.be\/|youtube\.com\/(?:embed\/|v\/|watch\?v=|watch\?.+&v=))((\w|-){11})(?:\S+)?$/;
            if (!VideoLinkText.match(p)) {
                ArticleTitleVideoValidation.style.display = 'block';
                $("#TitleImageValidationField").val("");
                document.getElementById('CardDynamicVideo').src = '';
                CardDynamicImageDiv.style.display = 'block';
                CardDynamicVideoDiv.style.display = 'none';
            } else {
                ArticleTitleVideoValidation.style.display = 'none';
                $("#TitleImageValidationField").val("Ok");
                console.log("title VideoLinkText 1: " + VideoLinkText)
                var processedUrl = titleProcessVideoUrl(VideoLinkText, true);
                document.getElementById('CardDynamicVideo').src = processedUrl;
                $("#ArticleTitleVideoField").val(processedUrl);
            }

            if (stringLength > 11) {
                ArticleTitleVideoValidation.style.display = 'block';
                $("#TitleImageValidationField").val("");
                document.getElementById('CardDynamicVideo').src = '';
                CardDynamicImageDiv.style.display = 'block';
                CardDynamicVideoDiv.style.display = 'none';
            }
            break;
        case 2:
            var endOfString = VideoLinkText.split('/')[4];
            var p = /^(?:https?:\/\/)?(?:m\.|www\.)?(?:youtu\.be\/|youtube\.com\/(?:embed\/|v\/|watch\?v=|watch\?.+&v=))((\w|-){11})(?:\S+)?$/;

            if (VideoLinkText.includes("https://www.") && VideoLinkText.match(p)) {
                stringLength = endOfString.length;
                console.log('title stringLength 2: ' + stringLength);
            } else {
                VideoLinkText = titleProcessVideoUrl(VideoLinkText, true);
                if (VideoLinkText.match(p)) {
                    var endOfString = VideoLinkText.split('/')[4];
                    stringLength = endOfString.length;
                    console.log("new VideoLinkText: " + VideoLinkText)
                }
            }
            console.log('title stringLength 3: ' + stringLength);

            if (!VideoLinkText.match(p)) {
                console.log('VideoLinkText !match(p): ' + VideoLinkText);
                ArticleTitleVideoValidation.style.display = 'block';
                $("#TitleImageValidationField").val("");
                document.getElementById('CardDynamicVideo').src = '';
                CardDynamicImageDiv.style.display = 'block';
                CardDynamicVideoDiv.style.display = 'none';
            } else {
                ArticleTitleVideoValidation.style.display = 'none';
                $("#TitleImageValidationField").val("Ok");
                console.log("title VideoLinkText 2: " + VideoLinkText)
                var processedUrl = titleProcessVideoUrl(VideoLinkText, true);
                document.getElementById('CardDynamicVideo').src = processedUrl;
                $("#ArticleTitleVideoField").val(processedUrl);
            }

            if (stringLength > 11) {
                console.log('stringLength > 11 if block');
                ArticleTitleVideoValidation.style.display = 'block';
                $("#TitleImageValidationField").val("");
                document.getElementById('CardDynamicVideo').src = '';
                CardDynamicImageDiv.style.display = 'block';
                CardDynamicVideoDiv.style.display = 'none';
            }
            break;
        case 3:
            var endOfString = VideoLinkText.split('/')[3];
            var p = /^(?:https?:\/\/)?(?:m\.|www\.)?(?:youtu\.be\/|youtube\.com\/(?:embed\/|v\/|watch\?v=|watch\?.+&v=))((\w|-){11})(?:\S+)?$/;

            if (VideoLinkText.includes("https://youtu.be/") && VideoLinkText.match(p)) {
                stringLength = endOfString.length;
                console.log('title stringLength 4: ' + stringLength);
            } else {
                VideoLinkText = titleProcessVideoUrl(VideoLinkText, true);
                if (VideoLinkText.match(p)) {
                    var endOfString = VideoLinkText.split('/')[3];
                    stringLength = endOfString.length;
                    console.log("new VideoLinkText: " + VideoLinkText)
                }
            }
            console.log('title stringLength 5: ' + stringLength);
            if (!VideoLinkText.match(p)) {
                console.log('VideoLinkText !match(p) 1: ' + VideoLinkText);
                ArticleTitleVideoValidation.style.display = 'block';
                $("#TitleImageValidationField").val("");
                document.getElementById('CardDynamicVideo').src = '';
                CardDynamicImageDiv.style.display = 'block';
                CardDynamicVideoDiv.style.display = 'none';
            } else {
                ArticleTitleVideoValidation.style.display = 'none';
                $("#TitleImageValidationField").val("Ok");
                document.getElementById('CardDynamicVideo').src = VideoLinkText;
                console.log("title VideoLinkText 3: " + VideoLinkText)
                var processedUrl = titleProcessVideoUrl(VideoLinkText, false);
                document.getElementById('CardDynamicVideo').src = processedUrl;
                $("#ArticleTitleVideoField").val(processedUrl);
            }

            if (stringLength > 11) {
                console.log('stringLength > 11 if block 1');
                ArticleTitleVideoValidation.style.display = 'block';
                $("#TitleImageValidationField").val("");
                document.getElementById('CardDynamicVideo').src = '';
                CardDynamicImageDiv.style.display = 'block';
                CardDynamicVideoDiv.style.display = 'none';
            }
            break;
        default:
            console.log('title default');
            var p = /^(?:https?:\/\/)?(?:m\.|www\.)?(?:youtu\.be\/|youtube\.com\/(?:embed\/|v\/|watch\?v=|watch\?.+&v=))((\w|-){11})(?:\S+)?$/;
            if (!VideoLinkText.match(p) && !VideoLinkText == "") {
                console.log('VideoLinkText !match(p) 2: ' + VideoLinkText);
                ArticleTitleVideoValidation.style.display = 'block';
                $("#TitleImageValidationField").val("");
                document.getElementById('CardDynamicVideo').src = '';
                CardDynamicImageDiv.style.display = 'block';
                CardDynamicVideoDiv.style.display = 'none';
            } else {
                ArticleTitleVideoValidation.style.display = 'none';
                $("#TitleImageValidationField").val("");
                var CardDynamicImageDiv = document.getElementById("CardDynamicImageDiv");
                CardDynamicImageDiv.style.display = 'block';
                var CardDynamicVideoDiv = document.getElementById("CardDynamicVideoDiv");
                CardDynamicVideoDiv.style.display = 'none';
            }
    }
}

...

function titleProcessVideoUrl(rawUrl, notShortSharingUrl) {

    if (notShortSharingUrl) {

        console.log('rawUrl 1: ' + rawUrl)

        if (!rawUrl.includes("https://") && rawUrl.includes("http://")) {
            rawUrl = rawUrl.replace('http://', 'https://')
            console.log('rawUrl 2: ' + rawUrl)
        } else if (!rawUrl.includes("https://") && rawUrl.includes("www.") && !rawUrl.includes("youtu.be")) {
            rawUrl = rawUrl.replace('www.', 'https://www.')
            console.log('rawUrl 3: ' + rawUrl)
        } else if (rawUrl.includes("https://") && !rawUrl.includes("www.") && !rawUrl.includes("youtu.be")) {
            rawUrl = rawUrl.replace('https://', 'https://www.')
            console.log('rawUrl 4: ' + rawUrl)
        } else if (rawUrl.includes("youtube.com/") && !rawUrl.includes("https://") && !rawUrl.includes("http://")) {
            rawUrl = rawUrl.replace('youtube.com/', 'https://www.youtube.com/')
            console.log('rawUrl 5: ' + rawUrl)
        } else if (rawUrl.includes("youtu.be/") && !rawUrl.includes("https://") && !rawUrl.includes("http://") && !rawUrl.includes("www.")) {
            rawUrl = rawUrl.replace('youtu.be/', 'https://youtu.be/')
            console.log('rawUrl 6: ' + rawUrl)
        } else if (rawUrl.includes("youtu.be/") && !rawUrl.includes("https://") && rawUrl.includes("http://")) {
            rawUrl = rawUrl.replace('http://', 'https://')
            console.log('rawUrl 7: ' + rawUrl)
        } else if (rawUrl.includes("https://") && rawUrl.includes("www.youtu.be/")) {
            rawUrl = rawUrl.replace('www.youtu.be/', 'youtu.be/')
            console.log('rawUrl 8: ' + rawUrl)
        } else if (!rawUrl.includes("https://") && rawUrl.includes("www.youtu.be/")) {
            rawUrl = rawUrl.replace('www.youtu.be/', 'https://youtu.be/')
            console.log('rawUrl 9: ' + rawUrl)
        }

        console.log('rawUrl 10: ' + rawUrl)

        var processed = rawUrl.replace('watch?v=', 'embed/')
        if (processed.includes("https://m.youtube")) {
            processed = rawUrl.replace('m.youtube', 'www.youtube');
            if (processed.includes("&list=")) {
                processed = processed.split('&list=')[0];
                return processed;
                console.log('title Processed 1: ' + processed);
            }
        } else if (processed.includes("watch?app=desktop&v=")) {
            processed = rawUrl.replace('watch?app=desktop&v=', 'embed/');
            if (processed.includes("&list=")) {
                processed = processed.split('&list=')[0];
                return processed;
                console.log('title Processed 1a: ' + processed);
            }
        } else if (processed.includes("&list=")) {
            processed = processed.split('&list=')[0];
            return processed;
            console.log('title Processed 1b: ' + processed);
        }
        console.log('title Processed 2: ' + processed);
        return processed;
    } else {
        console.log('rawUrl 1:' + rawUrl)
        if (!rawUrl.includes("https://") && rawUrl.includes("http://")) {
            rawUrl = rawUrl.replace('http://', 'https://')
            console.log('rawUrl 2:' + rawUrl)
        } else if (!rawUrl.includes("https://") && rawUrl.includes("www.")) {
            rawUrl = rawUrl.replace('www.', 'https://www.')
            console.log('rawUrl 3:' + rawUrl)
        }
        console.log('rawUrl 4:' + rawUrl)
        var processed = rawUrl.replace('https://youtu.be/', 'https://www.youtube.com/embed/')
        if (processed.includes("?t=")) {
            processed = processed.split('?t=')[0];
            return processed;
        }

        console.log('title Processed 3: ' + processed);
        return processed;
    }

注1:我知道上面的内容并不漂亮。我还没有时间整理它并摆脱所有 'ifs',但希望它能提供足够的上下文以供使用

注意 2: 请注意您用于测试的视频。 YouTube 不允许嵌入带有受版权保护的背景音乐的视频,它们将显示为不可用。