Skip to content

Commit

Permalink
Address follow-up work for #14639 (#14650)
Browse files Browse the repository at this point in the history
This PR adds a few more test cases to #14639 and updates the
documentation.

---------

Co-authored-by: Jordan Pittman <jordan@cryptica.me>
  • Loading branch information
philipp-spiess and thecrypticace authored Oct 14, 2024
1 parent 4e219dc commit 4b19de3
Show file tree
Hide file tree
Showing 7 changed files with 278 additions and 24 deletions.
2 changes: 1 addition & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- _Upgrade (experimental)_: Migrate v3 PostCSS setups to v4 in some cases ([#14612](https://github.com/tailwindlabs/tailwindcss/pull/14612))
- _Upgrade (experimental)_: Automatically discover JavaScript config files ([#14597](https://github.com/tailwindlabs/tailwindcss/pull/14597))
- _Upgrade (experimental)_: Migrate legacy classes to the v4 alternative ([#14643](https://github.com/tailwindlabs/tailwindcss/pull/14643))
- _Upgrade (experimental)_: Fully convert simple JS configs to CSS ([#14639](https://github.com/tailwindlabs/tailwindcss/pull/14639))
- _Upgrade (experimental)_: Migrate static JS configurations to CSS ([#14639](https://github.com/tailwindlabs/tailwindcss/pull/14639), [#14650](https://github.com/tailwindlabs/tailwindcss/pull/14650))
- _Upgrade (experimental)_: Migrate `@media screen(…)` when running codemods ([#14603](https://github.com/tailwindlabs/tailwindcss/pull/14603))
- _Upgrade (experimental)_: Inject `@config "…"` when a `tailwind.config.{js,ts,…}` is detected ([#14635](https://github.com/tailwindlabs/tailwindcss/pull/14635))
- _Upgrade (experimental)_: Migrate `aria-*`, `data-*`, and `supports-*` variants from arbitrary values to bare values ([#14644](https://github.com/tailwindlabs/tailwindcss/pull/14644))
Expand Down
193 changes: 191 additions & 2 deletions integrations/upgrade/js-config.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import { expect } from 'vitest'
import { css, json, test, ts } from '../utils'

test(
`upgrades a simple JS config file to CSS`,
`upgrade JS config files with flat theme values, darkMode, and content fields`,
{
fs: {
'package.json': json`
Expand Down Expand Up @@ -103,7 +103,196 @@ test(
)

test(
`does not upgrade a complex JS config file to CSS`,
'does not upgrade JS config files with functions in the theme config',
{
fs: {
'package.json': json`
{
"dependencies": {
"@tailwindcss/upgrade": "workspace:^"
}
}
`,
'tailwind.config.ts': ts`
import { type Config } from 'tailwindcss'
export default {
theme: {
extend: {
colors: ({ colors }) => ({
gray: colors.neutral,
}),
},
},
} satisfies Config
`,
'src/input.css': css`
@tailwind base;
@tailwind components;
@tailwind utilities;
`,
},
},
async ({ exec, fs }) => {
await exec('npx @tailwindcss/upgrade')

expect(await fs.dumpFiles('src/**/*.{css,ts}')).toMatchInlineSnapshot(`
"
--- src/input.css ---
@import 'tailwindcss';
@config '../tailwind.config.ts';
"
`)

expect(await fs.dumpFiles('tailwind.config.ts')).toMatchInlineSnapshot(`
"
--- tailwind.config.ts ---
import { type Config } from 'tailwindcss'
export default {
theme: {
extend: {
colors: ({ colors }) => ({
gray: colors.neutral,
}),
},
},
} satisfies Config
"
`)
},
)

test(
'does not upgrade JS config files with theme keys contributed to by plugins in the theme config',
{
fs: {
'package.json': json`
{
"dependencies": {
"@tailwindcss/upgrade": "workspace:^"
}
}
`,
'tailwind.config.ts': ts`
import { type Config } from 'tailwindcss'
export default {
theme: {
typography: {
DEFAULT: {
css: {
'--tw-prose-body': 'red',
color: 'var(--tw-prose-body)',
},
},
},
},
} satisfies Config
`,
'src/input.css': css`
@tailwind base;
@tailwind components;
@tailwind utilities;
@config '../tailwind.config.ts';
`,
},
},
async ({ exec, fs }) => {
await exec('npx @tailwindcss/upgrade')

expect(await fs.dumpFiles('src/**/*.css')).toMatchInlineSnapshot(`
"
--- src/input.css ---
@import 'tailwindcss';
@config '../tailwind.config.ts';
"
`)

expect(await fs.dumpFiles('tailwind.config.ts')).toMatchInlineSnapshot(`
"
--- tailwind.config.ts ---
import { type Config } from 'tailwindcss'
export default {
theme: {
typography: {
DEFAULT: {
css: {
'--tw-prose-body': 'red',
color: 'var(--tw-prose-body)',
},
},
},
},
} satisfies Config
"
`)
},
)

test(
'does not upgrade JS config files with plugins',
{
fs: {
'package.json': json`
{
"dependencies": {
"@tailwindcss/typography": "^0.5.15",
"@tailwindcss/upgrade": "workspace:^"
}
}
`,
'tailwind.config.ts': ts`
import { type Config } from 'tailwindcss'
import typography from '@tailwindcss/typography'
import customPlugin from './custom-plugin'
export default {
plugins: [typography, customPlugin],
} satisfies Config
`,
'custom-plugin.js': ts`
export default function ({ addVariant }) {
addVariant('inverted', '@media (inverted-colors: inverted)')
addVariant('hocus', ['&:focus', '&:hover'])
}
`,
'src/input.css': css`
@tailwind base;
@tailwind components;
@tailwind utilities;
`,
},
},
async ({ exec, fs }) => {
await exec('npx @tailwindcss/upgrade')

expect(await fs.dumpFiles('src/**/*.css')).toMatchInlineSnapshot(`
"
--- src/input.css ---
@import 'tailwindcss';
@config '../tailwind.config.ts';
"
`)

expect(await fs.dumpFiles('tailwind.config.ts')).toMatchInlineSnapshot(`
"
--- tailwind.config.ts ---
import { type Config } from 'tailwindcss'
import typography from '@tailwindcss/typography'
import customPlugin from './custom-plugin'
export default {
plugins: [typography, customPlugin],
} satisfies Config
"
`)
},
)

test(
`does not upgrade JS config files with inline plugins`,
{
fs: {
'package.json': json`
Expand Down
8 changes: 3 additions & 5 deletions packages/@tailwindcss-node/src/compile.ts
Original file line number Diff line number Diff line change
Expand Up @@ -100,11 +100,8 @@ async function importModule(path: string): Promise<any> {
try {
return await import(path)
} catch (error) {
try {
jiti ??= createJiti(import.meta.url, { moduleCache: false, fsCache: false })
return await jiti.import(path)
} catch {}
throw error
jiti ??= createJiti(import.meta.url, { moduleCache: false, fsCache: false })
return await jiti.import(path)
}
}

Expand Down Expand Up @@ -144,6 +141,7 @@ async function resolveCssId(id: string, base: string): Promise<string | false |
const jsResolver = EnhancedResolve.ResolverFactory.createResolver({
fileSystem: new EnhancedResolve.CachedInputFileSystem(fs, 4000),
useSyncFileSystemCalls: true,
extensions: ['.js', '.json', '.node', '.ts'],
})

function resolveJsId(id: string, base: string): Promise<string | false | undefined> {
Expand Down
14 changes: 6 additions & 8 deletions packages/@tailwindcss-upgrade/src/codemods/migrate-config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -63,9 +63,8 @@ export function migrateConfig(
cssConfig.append(postcss.parse(css + jsConfigMigration.css))
}

// Inject the `@config` in a sensible place
// 1. Below the last `@import`
// 2. At the top of the file
// Inject the `@config` directive after the last `@import` or at the
// top of the file if no `@import` rules are present
let locationNode = null as AtRule | null

walk(root, (node) => {
Expand Down Expand Up @@ -99,10 +98,9 @@ export function migrateConfig(

if (!hasTailwindImport) return

// - If a full `@import "tailwindcss"` is present, we can inject the
// `@config` directive directly into this stylesheet.
// - If we are the root file (no parents), then we can inject the `@config`
// directive directly into this file as well.
// If a full `@import "tailwindcss"` is present or this is the root
// stylesheet, we can inject the `@config` directive directly into this
// file.
if (hasFullTailwindImport || sheet.parents.size <= 0) {
injectInto(sheet)
return
Expand Down Expand Up @@ -134,7 +132,7 @@ function relativeToStylesheet(sheet: Stylesheet, absolute: string) {
if (relative[0] !== '.') {
relative = `./${relative}`
}
// Ensure relative is a posix style path since we will merge it with the
// Ensure relative is a POSIX style path since we will merge it with the
// glob.
return normalizePath(relative)
}
Loading

0 comments on commit 4b19de3

Please sign in to comment.