rsnext/packages/next-codemod/lib/cra-to-next/global-css-transform.ts
JJ Kasper dde9ad46ad
Add experimental cra-to-next transform in codemod cli (#24969)
Co-authored-by: Tim Neutkens <tim@timneutkens.nl>
Co-authored-by: kodiakhq[bot] <49736102+kodiakhq[bot]@users.noreply.github.com>
2021-06-09 16:51:56 +02:00

65 lines
1.7 KiB
TypeScript

import nodePath from 'path'
import { API, FileInfo, Options } from 'jscodeshift'
export const globalCssContext = {
cssImports: new Set<string>(),
reactSvgImports: new Set<string>(),
}
const globalStylesRegex = /(?<!\.module)\.(css|scss|sass)$/i
export default function transformer(
file: FileInfo,
api: API,
options: Options
) {
const j = api.jscodeshift
const root = j(file.source)
let hasModifications = false
root
.find(j.ImportDeclaration)
.filter((path) => {
const {
node: {
source: { value },
},
} = path
if (typeof value === 'string') {
if (globalStylesRegex.test(value)) {
let resolvedPath = value
if (value.startsWith('.')) {
resolvedPath = nodePath.resolve(nodePath.dirname(file.path), value)
}
globalCssContext.cssImports.add(resolvedPath)
const { start, end } = path.node as any
if (!path.parentPath.node.comments) {
path.parentPath.node.comments = []
}
path.parentPath.node.comments = [
j.commentLine(' ' + file.source.substring(start, end)),
]
hasModifications = true
return true
} else if (value.endsWith('.svg')) {
const isComponentImport = path.node.specifiers.some((specifier) => {
return (specifier as any).imported?.name === 'ReactComponent'
})
if (isComponentImport) {
globalCssContext.reactSvgImports.add(file.path)
}
}
}
return false
})
.remove()
return hasModifications && globalCssContext.reactSvgImports.size === 0
? root.toSource(options)
: null
}