{"record":{"id":"3831c1780c5a7e11","repo":"laurent22/joplin","slug":"could-not-get-lastmodified-date-for-resource-js","errorCode":null,"errorMessage":"Could not get lastModified date for resource: ${JSON.stringify(resource)}","messagePattern":"Could not get lastModified date for resource: (.+?)","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/lib/file-api-driver-webdav.js","lineNumber":77,"sourceCode":"\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tlet lastModifiedString = null;\n\n\t\ttry {\n\t\t\tlastModifiedString = this.api().resourcePropByName(resource, 'string', 'd:getlastmodified');\n\t\t} catch (error) {\n\t\t\tif (error.code === 'stringNotFound') {\n\t\t\t\t// OK - the logic to handle this is below\n\t\t\t} else {\n\t\t\t\tthrow error;\n\t\t\t}\n\t\t}\n\n\t\t// Note: Not all WebDAV servers return a getlastmodified date (eg. Seafile, which doesn't return the\n\t\t// property for folders) so we can only throw an error if it's a file.\n\t\tif (!lastModifiedString && !isDir) throw new Error(`Could not get lastModified date for resource: ${JSON.stringify(resource)}`);\n\t\tconst lastModifiedDate = lastModifiedString ? new Date(lastModifiedString) : new Date();\n\t\tif (isNaN(lastModifiedDate.getTime())) throw new Error(`Invalid date: ${lastModifiedString}`);\n\n\t\treturn {\n\t\t\tpath: path,\n\t\t\tupdated_time: lastModifiedDate.getTime(),\n\t\t\tisDir: isDir,\n\t\t};\n\t}\n\n\tasync setTimestamp() {\n\t\tthrow new Error('Not implemented'); // Not needed anymore\n\t}\n\n\tasync delta(path, options) {\n\t\tconst getDirStats = async path => {\n\t\t\tconst result = await this.list(path, { includeDirs: false });\n\t\t\treturn result.items;","sourceCodeStart":59,"sourceCodeEnd":95,"githubUrl":"https://github.com/laurent22/joplin/blob/2654b33620775080d1d59c552259d41e33dad3d2/packages/lib/file-api-driver-webdav.js#L59-L95","documentation":"Thrown by statFromResource_() when a WebDAV file resource has no d:getlastmodified property. The driver tolerates missing dates for directories (some servers like Seafile omit them) but requires one for files, since without it the sync timestamp comparison is impossible.","triggerScenarios":"stat() or list() on a WebDAV server that does not return the getlastmodified property for a file element — non-compliant server or a resource type the server treats specially.","commonSituations":"Seafile or other non-conformant WebDAV implementation; a virtual/special file (e.g. an alias or shortcut) that the server exposes without standard properties; server bug after an update; custom WebDAV gateway (e.g. to S3) that strips properties.","solutions":["Switch to a more standards-compliant WebDAV server or enable its full property support (Nextcloud/ownCloud recommended).","Update the WebDAV server to a version that emits getlastmodified for all files.","If stuck on a non-compliant server, patch the driver to fall back to the current time and accept weaker timestamp accuracy.","Verify the resource is actually a file and not a virtual entry exposed by the server."],"exampleFix":"// before\nif (!lastModifiedString && !isDir) throw new Error(`Could not get lastModified date for resource: ${JSON.stringify(resource)}`);\n// after - warn and degrade gracefully for non-conformant servers\nif (!lastModifiedString && !isDir) {\n  logger.warn('WebDAV server omitted getlastmodified; using current time:', resource);\n  lastModifiedString = new Date().toString();\n}","handlingStrategy":"fallback","validationCode":"// Pre-validate server compliance by statting a known file via PROPFIND.\nconst probe = await fetch(`${baseUrl}/.joplin-test`, { method: 'PROPFIND', headers: { Depth: '0', ...auth } });\nconst body = await probe.text();\nif (!body.includes('getlastmodified')) {\n  throw new Error('WebDAV server does not return getlastmodified; pick another server.');\n}","typeGuard":"function resourceHasLastModified(resource: any): boolean {\n  return !!resource && !!(resource?.['d:getlastmodified'] ?? resource?.['D:getlastmodified']);\n}","tryCatchPattern":"try {\n  return await driver.stat(path);\n} catch (e) {\n  if (/Could not get lastModified/.test(e.message)) {\n    logger.warn('Non-compliant WebDAV; degrading timestamp accuracy for', path);\n    return { path, updated_time: Date.now(), isDir: false };\n  }\n  throw e;\n}","preventionTips":["Choose a standards-compliant WebDAV server that emits getlastmodified for files.","Keep the WebDAV server updated.","If stuck on a non-compliant server, patch the driver to degrade gracefully.","Test the server with a PROPFIND probe before relying on it for sync."],"tags":["webdav","sync","propfind","timestamp","config"],"backgroundTag":null,"analyzedSha":"2654b33620775080d1d59c552259d41e33dad3d2","analyzedAt":"2026-08-12T14:26:46.263Z","schemaVersion":2},"datasetVersion":"2026-08-12T23:17:12.415Z"}