如何使用节点路径将 windows 路径转换为 ​​posix 路径

How can I convert a windows path to posix path using node path

我正在 windows 上开发,但需要知道如何将 windows 路径(带有反斜杠 \)转换为带有正斜杠的 POSIX 路径(/)?

我的目标是将 C:\repos\vue-t\tests\views\index\home.vue 转换为 C:/repos/vue-t/tests/views/index/home.vue

所以我可以在我正在写入磁盘的文件的导入中使用它

const appImport = `
import Vue from "vue"
import App from '${path}'

function createApp (data) {
    const app = new Vue({
        data,
        render: h => h(App)
    })
    return app
}`

//this string is then written to the disk as a file

我不想 .replace(/\/g, '/') 字符串,而是更喜欢使用 require('path') 函数。

Slash 将 windows 反斜杠路径转换为 ​​Unix 路径

用法:

const path = require('path');
const slash = require('slash');

const str = path.join('foo', 'bar');

slash(str);
// Unix    => foo/bar
// Windows => foo/bar

有一个名为 upath 的节点包会将 windows 路径转换为 ​​unix。

upath = require('upath');

import * as upath from 'upath';

upath.toUnix(destination_path)

对于那些寻找不依赖于 Node.js

的答案的人

One Liner(无第 3 方库)

//
// one-liner
//
let convertPath = (windowsPath) => windowsPath.replace(/^\\\?\/,"").replace(/\/g,'\/').replace(/\/\/+/g,'\/')

//
// usage
//
convertPath("C:\repos\vue-t\tests\views\index\home.vue")
// >>> "C:/repos/vue-t/tests/views/index/home.vue"

//
// multi-liner (commented and compatible with really old javascript versions)
//
function convertPath(windowsPath) {
    // handle the edge-case of Window's long file names
    // See: https://docs.microsoft.com/en-us/windows/win32/fileio/naming-a-file#short-vs-long-names
    windowsPath = windowsPath.replace(/^\\\?\/,"");

    // convert the separators, valid since both \ and / can't be in a windows filename
    windowsPath = windowsPath.replace(/\/g,'\/');

    // compress any // or /// to be just /, which is a safe oper under POSIX
    // and prevents accidental errors caused by manually doing path1+path2
    windowsPath = windowsPath.replace(/\/\/+/g,'\/');

    return windowsPath;
};

// dont want the C: to be inluded? here's a one-liner for that too
let convertPath = (windowsPath) => windowsPath.replace(/^\\\?\/,"").replace(/(?:^C:)?\/g,'\/').replace(/\/\/+/g,'\/')

通常我导入库。但是,我去阅读了 slashupath 的源代码。这些功能不是特别最新,而且在我检查时非常小。事实上,这个 liner 实际上比 slash 库处理更多的情况。不是每个人都在寻找这种解决方案,但对于那些正在寻找的人来说,就是这样。巧合的是,这是所有当前答案中运行时间最快的。

鉴于所有其他答案都依赖于安装(太大或太小)第三方模块:这也可以作为相对路径(您应该使用的)的 one-liner 99.999% 的时间已经)使用 Node 的标准库 path module, and more specifically, taking advantage of its dedicated path.posix and path.win32 命名空间 properties/functions(在 Node v0.11 中引入):

const path = require("path");

// ...

const definitelyPosix = somePathString.split(path.sep).join(path.posix.sep);

这会将您的路径转换为 ​​POSIX 格式,无论您是否已经在 POSIX 兼容平台或 win32 上,都不需要任何类型的外部依赖。

const winPath = 'C:\repos\vue-t\tests\views\index\home.vue'
const posixPath = winPath.replace(/\/g, '/').slice(2)
// Now posixPath = '/repos/vue-t/tests/views/index/home.vue'

只需使用默认库作为:

const {direname, resolve, basename}= require('path').posix;

import {posix} from 'path';
const {direname, resolve, basename}= posix;

我一直在寻找类似的东西,但更通用一些,尤其是在绝对路径中包含驱动器。因此,如果您使用例如git-bash 或 WSL 通常将驱动器默认映射为来自根 / (git-bash) 或 /mnt (WSL) 的字母。所以这是一个为我完成工作的正则表达式

// For git-bash Windows drives are mounted in the root like /C/ /D/ etc.
const toGitBashPosixPath = (windowsPath) => windowsPath.replace(/^(\w):|\+/g,'/');

console.log(toGitBashPosixPath('c:\\\project\file.x')); // messy Windows path
console.log(toGitBashPosixPath('c:\project\file.x')); // regular Windows path
console.log(toGitBashPosixPath('c:/project/file.x')); // slash path acceptable by Windows
console.log(toGitBashPosixPath('project\file.x'));// relative Windows path
console.log(toGitBashPosixPath('.\project\file.x'));// another relative Windows path

// For WSL Windows drives are mounted by default next to /mnt like /mnt/C/ /mnt/D/ etc.
const toWSLPosixPath = (windowsPath) => windowsPath.replace(/^(\w):|\+/g,'/').replace(/^\//g,'/mnt/');
console.log(toWSLPosixPath('c:\project\file.x'))

希望这对某人有所帮助。

这是一个解决方案,return 以平台不可知的方式设置模块目录,它适用于 "type": "module":

const path = require('path');

const getModuleDir = (moduleName) => {
  const entry = require.resolve(moduleName);
  const entryPosix = entry.split(path.sep).join(path.posix.sep);
  return path.resolve(entryPosix.split(moduleName)[0] + moduleName);
};

解释:

假设我们需要名为 @foo/bar.

的模块的文件夹路径
  1. 使用require.resolve找到模块的入口点。这可能指向一个深深嵌套在模块中的文件:
    • 示例 posix:/home/joe/node_modules/@foo/bar/bing/baz/index.js
    • 示例 win32:C:\Users\joe\node_modules\@foo\bar\bing\baz\index.js
  2. 将所有斜杠转换为 posix 样式的正斜杠(这是 windwos 需要的)。
  3. 拆分模块名称上的 posix-friendly 路径。你得到一个包含两个项目的数组:
    • 示例 posix:["/home/joe/node_modules/", "/bing/baz/index.js"]
    • 示例 win32:["C:/Users/joe/node_modules", "/bing/baz/index.js"]
  4. 将步骤#3 中的第一部分与模块名称连接起来,这样可以方便地将其转换回 platform-specific 路径:
    • 最终结果posix:/home/joe/node_modules/@foo/bar
    • 最终结果 win32: C:\Users\joe\node_modules\@foo\bar

注意: 如果包嵌套在另一个包的 node_modules 文件夹中,这也将起作用。例如,第 1 步可能 return 这样的路径:

/home/joe/node_modules/some-package/node_modules/@foo/bar/bing/baz/index.js

此脚本仍然有效。