utils.ts 4.0 KB
Newer Older
fxy060608's avatar
fxy060608 已提交
1
import fs from 'fs'
fxy060608's avatar
fxy060608 已提交
2 3
import os from 'os'
import path from 'path'
fxy060608's avatar
fxy060608 已提交
4
import colors from 'picocolors'
fxy060608's avatar
fxy060608 已提交
5
import { camelize, capitalize } from '@vue/shared'
fxy060608's avatar
fxy060608 已提交
6
export { default as hash } from 'hash-sum'
fxy060608's avatar
fxy060608 已提交
7
import { EXTNAME_TS_RE, PAGE_EXTNAME, PAGE_EXTNAME_APP } from './constants'
fxy060608's avatar
fxy060608 已提交
8

9 10 11 12 13 14
import {
  NodeTypes,
  ElementNode,
  RootNode,
  TemplateChildNode,
} from '@vue/compiler-core'
fxy060608's avatar
fxy060608 已提交
15
import { ParserPlugin } from '@babel/parser'
fxy060608's avatar
fxy060608 已提交
16
import { getPlatformDir } from './platform'
fxy060608's avatar
fxy060608 已提交
17

fxy060608's avatar
fxy060608 已提交
18 19
export const version = require('../package.json').version

fxy060608's avatar
fxy060608 已提交
20 21 22 23 24
export let isRunningWithYarnPnp: boolean
try {
  isRunningWithYarnPnp = Boolean(require('pnpapi'))
} catch {}

25
export const isWindows = os.platform() === 'win32'
fxy060608's avatar
fxy060608 已提交
26
export function normalizePath(id: string): string {
27
  return isWindows ? id.replace(/\\/g, '/') : id
fxy060608's avatar
fxy060608 已提交
28
}
fxy060608's avatar
fxy060608 已提交
29

雪洛's avatar
雪洛 已提交
30
export function checkElementNodeTag(
31
  node: RootNode | TemplateChildNode | null | undefined,
雪洛's avatar
雪洛 已提交
32 33
  tag: string
): node is ElementNode {
34
  return !!node && node.type === NodeTypes.ELEMENT && node.tag === tag
雪洛's avatar
雪洛 已提交
35 36
}

fxy060608's avatar
fxy060608 已提交
37 38 39
export function normalizeIdentifier(str: string) {
  return capitalize(camelize(str.replace(/\//g, '-')))
}
fxy060608's avatar
fxy060608 已提交
40 41 42 43 44 45 46 47 48 49 50 51 52 53 54

export function normalizePagePath(pagePath: string, platform: UniApp.PLATFORM) {
  const absoltePagePath = path.resolve(process.env.UNI_INPUT_DIR, pagePath)
  let extnames = PAGE_EXTNAME
  if (platform === 'app') {
    extnames = PAGE_EXTNAME_APP
  }
  for (let i = 0; i < extnames.length; i++) {
    const extname = extnames[i]
    if (fs.existsSync(absoltePagePath + extname)) {
      return pagePath + extname
    }
  }
  console.error(`${pagePath} not found`)
}
fxy060608's avatar
fxy060608 已提交
55

fxy060608's avatar
fxy060608 已提交
56 57
export function removeExt(str: string) {
  return str.split('?')[0].replace(/\.\w+$/g, '')
fxy060608's avatar
fxy060608 已提交
58
}
fxy060608's avatar
fxy060608 已提交
59 60 61 62 63 64

const NODE_MODULES_REGEX = /(\.\.\/)?node_modules/g

export function normalizeNodeModules(str: string) {
  str = normalizePath(str).replace(NODE_MODULES_REGEX, 'node-modules')
  // HBuilderX 内置模块路径转换
fxy060608's avatar
fxy060608 已提交
65 66 67 68
  str = str.replace(
    /.*\/plugins\/uniapp-cli-vite\/node[-_]modules/,
    'node-modules'
  )
fxy060608's avatar
fxy060608 已提交
69 70 71 72 73
  if (process.env.UNI_PLATFORM === 'mp-alipay') {
    str = str.replace('node-modules/@', 'node-modules/npm-scope-')
  }
  return str
}
fxy060608's avatar
fxy060608 已提交
74 75 76 77 78

export function normalizeMiniProgramFilename(
  filename: string,
  inputDir?: string
) {
fxy060608's avatar
fxy060608 已提交
79
  if (!inputDir || !path.isAbsolute(filename)) {
fxy060608's avatar
fxy060608 已提交
80 81 82 83
    return normalizeNodeModules(filename)
  }
  return normalizeNodeModules(path.relative(inputDir, filename))
}
fxy060608's avatar
fxy060608 已提交
84 85 86 87 88 89 90 91 92 93 94 95 96 97

export function normalizeParsePlugins(
  importer: string,
  babelParserPlugins?: ParserPlugin[]
) {
  const isTS = EXTNAME_TS_RE.test(importer.split('?')[0])
  const plugins: ParserPlugin[] = []
  if (isTS) {
    plugins.push('jsx')
  }
  if (babelParserPlugins) plugins.push(...babelParserPlugins)
  if (isTS) plugins.push('typescript', 'decorators-legacy')
  return plugins
}
Q
qiang 已提交
98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113

export function pathToGlob(
  pathString: string,
  glob: string,
  options: { windows?: boolean; escape?: boolean } = {}
): string {
  const isWindows =
    'windows' in options ? options.windows : /^win/.test(process.platform)
  const useEscape = options.escape
  const str = isWindows ? pathString.replace(/\\/g, '/') : pathString
  let safeStr = str.replace(
    /[\\*?[\]{}()!]/g,
    isWindows || !useEscape ? '[$&]' : '\\$&'
  )
  return path.posix.join(safeStr, glob)
}
fxy060608's avatar
fxy060608 已提交
114

fxy060608's avatar
fxy060608 已提交
115 116 117 118
export function resolveSourceMapPath(
  outputDir?: string,
  platform?: UniApp.PLATFORM
) {
fxy060608's avatar
fxy060608 已提交
119
  return path.resolve(
fxy060608's avatar
fxy060608 已提交
120 121
    outputDir || process.env.UNI_OUTPUT_DIR,
    '../.sourcemap/' + (platform || getPlatformDir())
fxy060608's avatar
fxy060608 已提交
122
  )
fxy060608's avatar
fxy060608 已提交
123
}
fxy060608's avatar
fxy060608 已提交
124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152

function hasProjectYarn(cwd: string) {
  return fs.existsSync(path.join(cwd, 'yarn.lock'))
}

function hasProjectPnpm(cwd: string) {
  return fs.existsSync(path.join(cwd, 'pnpm-lock.yaml'))
}

function getInstallCommand(cwd: string) {
  return hasProjectYarn(cwd)
    ? 'yarn add'
    : hasProjectPnpm(cwd)
    ? 'pnpm i'
    : 'npm i'
}

export function installDepTips(
  type: 'dependencies' | 'devDependencies',
  module: string,
  version?: string
) {
  return `Cannot find module: ${module}
Please run \`${colors.cyan(
    `${getInstallCommand(process.cwd())} ${
      module + (version ? '@' + version : '')
    }${type === 'devDependencies' ? ' -D' : ''}`
  )}\` and try again.`
}