ChatGPT解决这个技术问题 Extra ChatGPT

如何检查文件是否存在于 jQuery 或纯 JavaScript 中?

如何检查我服务器上的文件是否存在于 jQuery 或纯 JavaScript 中?


S
Spiralis

使用 jQuery:

$.ajax({
    url:'http://www.example.com/somefile.ext',
    type:'HEAD',
    error: function()
    {
        //file not exists
    },
    success: function()
    {
        //file exists
    }
});

编辑:

这是检查 404 状态的代码,不使用 jQuery

function UrlExists(url)
{
    var http = new XMLHttpRequest();
    http.open('HEAD', url, false);
    http.send();
    return http.status!=404;
}

小的更改,它可以检查状态 HTTP 状态代码 200(成功),而不是。

编辑 2:由于不推荐使用同步 XMLHttpRequest,因此您可以添加这样的实用程序方法来异步执行:

function executeIfFileExist(src, callback) {
    var xhr = new XMLHttpRequest()
    xhr.onreadystatechange = function() {
        if (this.readyState === this.DONE) {
            callback()
        }
    }
    xhr.open('HEAD', src)
}

在您的纯 javascript 示例中,您应该在检查 HTTP_STATUS 之前绑定 OnReadyStateChange 事件。
示例代码是错误的,并且没有任何关于服务器上发生的事情的说明。最初的问题非常模糊,但没有理由假设在那里运行的服务器实际上将 URL 直接映射到文件系统。老实说,我不明白为什么这个答案如此受欢迎,因为它并没有真正说明如何做问题所要求的。
@Pointy 可能是因为它解决了我们其他人正在谷歌搜索的问题
@cichy - 这是否将文件加载到内存中?我正在寻找是否存在但不加载文件。
主线程上的同步 XMLHttpRequest 已被弃用,因为它会对最终用户的体验产生不利影响。如需更多帮助xhr.spec.whatwg.org(浏览器发出此警告)
M
Matthew James Davis

类似且更新的方法。

$.get(url)
    .done(function() { 
        // exists code 
    }).fail(function() { 
        // not exists code
    })

为什么这是最新的? $.ajax 如果更向后兼容,似乎更好,对吧?
$.ajax 也可以,但是不推荐使用成功/错误/完成函数,而支持 promise、done/fail/always 方法。在此处了解更多信息api.jquery.com/jQuery.ajax。我在这里使用 get 是因为我们只对简单的 get 感兴趣,但这只是 $.ajax({url:url,type:'GET'}) 的简写。
如果图像不存在,则控制台回显 404 错误。有没有办法删除它,因为我的应用程序总是期望一个图像不存在......
不可能,请参阅:stackoverflow.com/a/16379746/1981050。但是,这不应该打断您的行为。它只会产生一些无关的日志记录。
跨源问题与此无关
T
Tester

这对我有用:

function ImageExist(url) 
{
   var img = new Image();
   img.src = url;
   return img.height != 0;
}

虽然其他一些答案更适合它们的功能,但我 +1 这个答案,因为它是我正在寻找的。请记住,除非您先加载内容,否则您将永远得到零!即:window.addEventListener('load', function(){
实际上,即使窗口加载,我仍然有问题。似乎图像在以某种方式缓存之前无法测量。无论如何,我在第一次加载页面时不适合我。 (即:用户以前从未见过此图像)。如果您在前一页上有图像,它可能对您有用,也许......
那是因为它设置了图像的来源并立即检查以查看尚未完成下载的图像的高度。您必须添加一个 onload 处理程序才能使其工作。出于这个确切原因,这不是一种可靠的方法。
如果添加像 stackoverflow.com/a/12355031/988591 这样的 img.onload 处理程序,为什么它不可靠?
问题询问的是文件,而不是图像!如果 URL 确实存在并且不是文件,则其高度将为 0!!
G
Gino

我用这个脚本来添加替代图像

function imgError()
{
alert('The image could not be loaded.');
}

HTML:

<img src="image.gif" onerror="imgError()" />

http://wap.w3schools.com/jsref/event_onerror.asp


太好了——不知道。如果图像不存在,您可以执行以下操作来设置保存选项:
@Ridcully 啊,但是如果替代方案失败了怎么办?那你就在无限循环中吧?
如果替代方案失败,我想服务器端(或程序员端:P)还有更多错误
在设置 alt 图像时,您始终可以将 img 标记的 OnError 设置为空,以防止无限循环。
来自未来的坏消息。这被标记为“已弃用。不适用于新网站。” developer.mozilla.org/en-US/docs/Web/HTML/Element/img
Y
YemSalat

只要您在同一个域上测试文件,这应该可以工作:

function fileExists(url) {
    if(url){
        var req = new XMLHttpRequest();
        req.open('GET', url, false);
        req.send();
        return req.status==200;
    } else {
        return false;
    }
}

请注意,此示例使用 GET 请求,除了获取标头(您只需要检查文件是否存在)之外,它还会获取整个文件。如果文件足够大,此方法可能需要一段时间才能完成。

更好的方法是将这一行: req.open('GET', url, false); 更改为 req.open('HEAD', url, false);


抱歉,这实际上与接受的答案相同。不理我。
关于非 jQuery 表单的更多详细信息可能会有所帮助
@Moob,它“实际上与接受的答案不同”,您正在发送一个 GET 请求,这与 HEAD 请求不同。
async: false,由于用户体验不佳,Firefox 30.0 及更高版本以及最近/当前版本的 Chrome 中的同步操作已被弃用。尝试使用会导致失败/错误。应使用带有回调函数的 async: true 进行异步操作。
请在继续执行进一步的 JS 之前等待响应?谢谢你。
N
Nik Sumeiko

如果您使用的是 Babel transpiler 或 Typescript 2,以下是 ES7 的方法:

async function isUrlFound(url) {
  try {
    const response = await fetch(url, {
      method: 'HEAD',
      cache: 'no-cache'
    });

    return response.status === 200;

  } catch(error) {
    // console.log(error);
    return false;
  }
}

然后在您的其他 async 范围内,您可以轻松检查 url 是否存在:

const isValidUrl = await isUrlFound('http://www.example.com/somefile.ext');

console.log(isValidUrl); // true || false

S
Shaun

尝试运行此问题的答案时,我遇到了跨域权限问题,因此我选择了:

function UrlExists(url) {
$('<img src="'+ url +'">').load(function() {
    return true;
}).bind('error', function() {
    return false;
});
}

它似乎工作得很好,希望这对某人有帮助!


我认为这将丢失布尔值,因为它们是从回调返回的,而不是 UrlExists 函数。
这行不通,您应该阅读以下内容:stackoverflow.com/questions/14220321/…
网址看起来如何? ,有扩展名还是没有扩展名?
J
Jan Turoň

由于缓存,所有其他答案都可能失败!

向服务器上的文件发出 HTTP 请求可以被浏览器的缓存拦截,然后返回缓存的响应。但同时该文件可能会在服务器上被删除,因此忽略缓存可能会返回误报结果。

正确的解决方案是创建非缓存的 HTTP HEAD 请求。 Nik Sumeiko 的回答使用 no-cache 标头,这意味着响应可以被缓存,但必须在重用之前重新验证。在这种情况下,服务器可能返回 304: Not Modified,它不是 200: OK,因此是假阴性。

为避免缓存,正确的标头是 Cache-Control: no-store

文件可以在没有 HTTP 200 响应的情况下存在

您还应该记住,可能会发生 重定向301: Moved Permanently307: Temporary Redirect308: Permanent Redirect),因此该文件可以存在于其他地方,并且可能会从不同的位置返回:取决于用途 -在这种情况下,可以选择遵循重定向而不是在这种情况下返回 false。

另请记住,如果您检查不同域上的文件是否存在并且其 CORS 策略未对您的服务器开放,则后台请求将被阻止。在这种情况下,通常会返回 403: Forbidden,这并不意味着 文件不存在,而是 文件不可用。最后但同样重要的是,同样适用于 500: Internal Server Error 响应,这意味着 HTTP 服务器无法处理请求,但文件可以通过其他方式获得,例如通过 FTP。

如果文件存在,以下代码将返回 true,如果不存在,则返回 false,如果文件不可用或重定向,则返回 undefined:

const fileExists = file =>
  fetch(file, {method: 'HEAD', cache: 'no-store'})
  .then(response => ({200: true, 404: false})[response.status])
  .catch(e => undefined);

fileExists("yourFile.html").then(yes => yes && alert("yourFile.html exists"));

// if not in the main thread...
let yourFileExists = await fileExists("yourFile.html");

现代和过时的方法

由于我们现在生活在未来,我还建议:

$.ajax() 已过时,不要在新项目中使用

XMLHttpRequest() 已过时,不要在新项目中使用

fetch() 现代方法,如果您可以自由选择,请使用它

GET/POST 方法(如 <img src...>)在这里不合适,因为它们通过下载文件浪费了网络流量(想象一下高分辨率照片和用户在连接不良的地区使用付费移动数据的场景)


很棒的代码——请注意,如果你想在主要的 android 移动浏览器上使用这种方法,只有 2022 浏览器更新可以处理它。您可能需要检查“获取”是否存在(如果需要,检测是否使用旧方法)以包含它们。请参阅caniuse.com/fetch
G
Gëzim Musliaj

我使用这个脚本来检查文件是否存在(它也处理跨源问题):

$.ajax(url, {
       method: 'GET',
       dataType: 'jsonp'
         })
   .done(function(response) { 
        // exists code 
    }).fail(function(response) { 
        // doesnt exist
    })

请注意,当被检查的文件不包含 JSON 时,会引发以下语法错误。

未捕获的 SyntaxError:意外的令牌 <


s
sashkello

对于客户端计算机,这可以通过以下方式实现:

try
{
  var myObject, f;
  myObject = new ActiveXObject("Scripting.FileSystemObject");
  f =   myObject.GetFile("C:\\img.txt");
  f.Move("E:\\jarvis\\Images\\");
}
catch(err)
{
  alert("file does not exist")
}

这是我将文件传输到特定位置并在文件不存在时显示警报的程序


如果您要使用 FileSystemObject,使用 FileExists() 方法似乎更容易。 msdn.microsoft.com/en-us/library/aa265024(v=vs.60).aspx
ActiveXObject 仅在 Internet Explorer 中可用,因此在其他浏览器中不起作用。
A
Ani Menon

用于检查文件是否存在的 JavaScript 函数:

function doesFileExist(urlToFile)
{
    var xhr = new XMLHttpRequest();
    xhr.open('HEAD', urlToFile, false);
    xhr.send();

    if (xhr.status == "404") {
        console.log("File doesn't exist");
        return false;
    } else {
        console.log("File exists");
        return true;
    }
}

这是最简单的工作答案。它也不需要异步。
J
Jim Bergman

异步调用来查看文件是否存在是更好的方法,因为它不会因为等待服务器的响应而降低用户体验。如果您在第三个参数设置为 false 的情况下调用 .open(如上面的许多示例,例如 http.open('HEAD', url, false); ),这是一个同步调用,您会在浏览器控制台中收到警告。

更好的方法是:

function fetchStatus( address ) {
  var client = new XMLHttpRequest();
  client.onload = function() {
    // in case of network errors this might not give reliable results
    returnStatus( this.status );
  }
  client.open( "HEAD", address, true );
  client.send();
}

function returnStatus( status ) {
  if ( status === 200 ) {
    console.log( 'file exists!' );
  }
  else {
    console.log( 'file does not exist! status: ' + status );
  }
}

来源:https://xhr.spec.whatwg.org/


我还使用您的方法在控制台日志中收到警告响应,知道吗?
尝试调用 .open 并将第三个参数设置为 true 以确保它异步调用它,就像这样 client.open("HEAD", address, true); @Pierre
J
Josh Harris

这是对已接受答案的改编,但我无法从答案中得到我需要的东西,并且不得不测试它是否有效,因为这是一种预感,所以我将我的解决方案放在这里。

我们需要验证本地文件是否存在,并且只允许文件(PDF)在存在时打开。如果您省略网站的 URL,浏览器将自动确定主机名 - 使其在 localhost 和服务器上工作:

$.ajax({

    url: 'YourFolderOnWebsite/' + SomeDynamicVariable + '.pdf',
    type: 'HEAD',
    error: function () {
        //file not exists
        alert('PDF does not exist');

    },
    success: function () {
        //file exists
        window.open('YourFolderOnWebsite/' + SomeDynamicVariable + '.pdf', "_blank", "fullscreen=yes");

    }
});

V
Vladimir Salguero

首先创建函数

$.UrlExists = function(url) { var http = new XMLHttpRequest(); http.open('HEAD', url, false); http.send();返回 http.status!=404; }

使用函数后如下

if($.UrlExists("urlimg")){ foto = "img1.jpg"; }else{ 照片 = "img2.jpg"; } $('').attr('src',foto);


我尝试了 here,但无法正常工作。我错过了什么?
b
blissweb

这是我从 2020 年开始工作的 Async Pure Javascript

function testFileExists(src, successFunc, failFunc) {
    var xhr = new XMLHttpRequest();
    xhr.onreadystatechange = function () {
        if (this.readyState === this.DONE) {
            if (xhr.status === 200) {
                successFunc(xhr);
            } else {
                failFunc(xhr);
            }
        }
    }
    // xhr.error = function() {
    //     failFunc(xhr);
    // }
    // xhr.onabort = function() {
    //     failFunc(xhr);
    // }
    // xhr.timeout = function() {
    //     failFunc(xhr);
    // }
    xhr.timeout = 5000;           // TIMEOUT SET TO PREFERENCE (5 SEC)
    xhr.open('HEAD', src, true);
    xhr.send(null);               // VERY IMPORTANT
}
function fileExists(xhr) {
    alert("File exists !!  Yay !!");
}
function fileNotFound(xhr) {
    alert("Cannot find the file, bummer");
}
testFileExists("test.html", fileExists, fileNotFound);

我无法强制它返回任何中止、错误或超时回调。在上面的测试中,它们中的每一个都返回了一个主状态代码 0,所以我删除了它们。你可以做实验。我将超时设置为 5 秒,因为默认值似乎非常过大。使用 Async 调用,如果没有 send() 命令,它似乎什么也做不了。


M
MadcapLaugher

您要做的就是向服务器发送一个请求,让它进行检查,然后将结果发回给您。

您尝试与哪种类型的服务器通信?您可能需要编写一个小型服务来响应请求。


t
timgavin

这并没有解决 OP 的问题,但对于从数据库返回结果的任何人:这是我使用的一个简单方法。

如果用户没有上传头像,则 avatar 字段将为 NULL,因此我将插入 img 目录中的默认头像图像。

function getAvatar(avatar) {
    if(avatar == null) {
        return '/img/avatar.jpg';
    } else {
        return '/avi/' + avatar;
    }
}

然后

<img src="' + getAvatar(data.user.avatar) + '" alt="">

A
AnhMV

它对我有用,使用 iframe 忽略浏览器显示 GET 错误消息

 var imgFrame = $('<iframe><img src="' + path + '" /></iframe>');
 if ($(imgFrame).find('img').attr('width') > 0) {
     // do something
 } else {
     // do something
 }

G
Gianlorenzo Lenza

我想要一个返回布尔值的函数,但遇到了与闭包和异步相关的问题。我这样解决了:

checkFileExistence= function (file){
    result=false;
    jQuery.ajaxSetup({async:false});
    $.get(file)
        .done(function() {
           result=true;
        })
        .fail(function() {
           result=false;
        })
    jQuery.ajaxSetup({async:true});
    return(result);
},

如果不使用 jQuery,仍然无法正确管理检测文件的存在。我尝试了上面列出的所有方法。无论文件是否存在,状态始终为 200。
A
Arash

您可以使用此命令,我将其用于我的网站。

if (File("patch").exists)
{
    //do jobe when exists
} else {
    // do jobe when dosent exist
}

谢谢


File 是什么? exists 是什么?
File 是一个模块,exists 是 bool。