fix: using ?get=basic was not displaying web-folders correctly

Massimo Melina committed Jun 30, 2024 at 22:55 UTC c7e5772c0b99164c749a5cba12cec05d3c2f20f8
3 files changed +13 -11
src/api.get_file_list.ts
+7 -9
@@ -1,7 +1,9 @@
1 // This file is part of HFS - Copyright 2021-2023, Massimo Melina <a@rejetto.com> - License https://www.gnu.org/licenses/gpl-3.0.txt
2
3 -import { applyParentToChild, getNodeName, hasPermission, masksCouldGivePermission, nodeIsDirectory,
4 - statusCodeForMissingPerm, urlToNode, VfsNode, walkNode } from './vfs'
3 +import {
4 + applyParentToChild, getNodeName, hasDefaultFile, hasPermission, masksCouldGivePermission, nodeIsDirectory,
5 + statusCodeForMissingPerm, urlToNode, VfsNode, walkNode
6 +} from './vfs'
7 import { ApiError, ApiHandler } from './apiMiddleware'
8 import { stat } from 'fs/promises'
9 import { mapPlugins } from './plugins'
@@ -25,8 +27,8 @@ export const get_file_list: ApiHandler = async ({ uri='/', offset, limit, search
27 admin &&= ctxAdminAccess(ctx) // validate 'admin' flag
28 if (dirTraversal(search))
29 return fail(HTTP_FOOL)
28 - if (await hasDefaultFile(node) || !await nodeIsDirectory(node)) // in case of files without permission, we are provided with the frontend, and the location is the file itself
29 - // so we first check if you have a permission problem, to tell frontend to show login, otherwise we fallback to method_not_allowed, as it's proper for files.
30 + if (await hasDefaultFile(node, ctx) || !await nodeIsDirectory(node)) // in case of files without permission, we are provided with the frontend, and the location is the file itself
31 + // so, we first check if you have a permission problem, to tell frontend to show login, otherwise we fall back to method_not_allowed, as it's proper for files.
32 return fail(statusCodeForMissingPerm(node, 'can_read', ctx) ? undefined : HTTP_METHOD_NOT_ALLOWED)
33 if (!admin && statusCodeForMissingPerm(node, 'can_list', ctx))
34 return fail()
@@ -99,10 +101,6 @@ export const get_file_list: ApiHandler = async ({ uri='/', offset, limit, search
101 }
102 }
103
102 - async function hasDefaultFile(node: VfsNode) {
103 - return node.default && await urlToNode(node.default, ctx, node)
104 - }
105 -
104 async function nodeToDirEntry(ctx: Koa.Context, node: VfsNode): Promise<DirEntry | null> {
105 const { source, url } = node
106 const name = getNodeName(node)
@@ -127,7 +125,7 @@ export const get_file_list: ApiHandler = async ({ uri='/', offset, limit, search
125 s: isFolder ? undefined : st?.size,
126 p: (pr + pl + pd + pa) || undefined,
127 comment: await getCommentFor(source),
130 - web: await hasDefaultFile(node) ? true : undefined,
128 + web: await hasDefaultFile(node, ctx) ? true : undefined,
129 }
130 }
131 catch {
src/basicWeb.ts
+2 -2
@@ -2,7 +2,7 @@ import { getCurrentUsername, setLoggedIn } from './auth'
2 import { HTTP_UNAUTHORIZED } from './cross-const'
3 import Koa from 'koa'
4 import { defineConfig } from './config'
5 -import { getNodeName, nodeIsDirectory, VfsNode, walkNode } from './vfs'
5 +import { getNodeName, hasDefaultFile, nodeIsDirectory, VfsNode, walkNode } from './vfs'
6 import { asyncGeneratorToReadable, Dict, filterMapGenerator, pathEncode } from './misc'
7 import _ from 'lodash'
8 import { title } from './adminApis'
@@ -36,7 +36,7 @@ export function basicWeb(ctx: Koa.Context, node: VfsNode) {
36 const stream = asyncGeneratorToReadable(filterMapGenerator(walker, async el => {
37 const isFolder = await nodeIsDirectory(el)
38 const name = getNodeName(el) + (isFolder ? '/' : '')
39 - return `<li>${a(pathEncode(name) + (isFolder ? force : ''), name)}\n`
39 + return `<li>${a(pathEncode(name) + (isFolder && !await hasDefaultFile(el, ctx) ? force : ''), name)}\n`
40 }))
41 ctx.body = stream
42 stream.push(`<title>${title.get()}</title><body>`)
src/vfs.ts
+4
@@ -199,6 +199,10 @@ export async function nodeIsDirectory(node: VfsNode) {
199 return isFolder
200 }
201
202 +export async function hasDefaultFile(node: VfsNode, ctx: Koa.Context) {
203 + return node.default && await urlToNode(node.default, ctx, node) || undefined
204 +}
205 +
206 export function nodeIsLink(node: VfsNode) {
207 return node.url
208 }