core: Make JSX typings an optional install as they conflict with React TSX

Version

3.0.0-beta.3

Reproduction link

https://github.com/elevatebart/vue-next-react-ts-conflict

Steps to reproduce

# Checkout the repo
git checkout https://github.com/elevatebart/vue-next-react-ts-conflict.git

# Install all modules
npm ci

# run tsc
npm start

The errors you see in the console are due to React and Vue TSX accepting different values.

What is expected?

When migrating from React to Vue, types should not fail without installing them.

What is actually happening?

it fails at compilation


JSX types could be made a separate package: @vue/jsx-types.

This way, types would not systematically be installed.

Devs could install the runtime they need without the typings.

The transition would be easier.

About this issue

  • Original URL
  • State: closed
  • Created 4 years ago
  • Reactions: 26
  • Comments: 39 (16 by maintainers)

Commits related to this issue

Most upvoted comments

I started getting these errors after installing storybook 3.6.10. My project’s stack is vite + vue3 (typescript), while storybook is using webpack and is based on react, so I’m making a wild guess that by adding storybook, these errors started surfacing because of react dependencies.

Type ‘{ class: string; }’ is not assignable to type ‘DetailedHTMLProps<OlHTMLAttributes<HTMLOListElement>, HTMLOListElement>’.\n Property ‘class’ does not exist on type ‘DetailedHTMLProps<OlHTMLAttributes<HTMLOListElement>, HTMLOListElement>’. Did you mean ‘className’?"

guys ,add at the head of the file

/* @jsxImportSource @vue/runtime-dom */

or

tsconfig.json
{
...
  "types": ["vue"],
}

I test it works

IMHO the issue should stay open because it’s still valid. As mentioned in the past - I’m willing to work on this if somebody green lights this. I would probably also need to chat with the maintainers before getting to work because we’d need to establish the risks, breakage concerns, potential migration strategies etc

There is actually a way to make JSX namespace “local”. It could be a namespace attached to the h factory, similarly to what I’ve done in Emotion: https://github.com/emotion-js/emotion/blob/4266aa0183fe2c19904c25c6e803e8c534923865/packages/react/types/index.d.ts#L96-L114

I’ve explored this quite a bit and I’m also advocating for @types/react to use this technique instead of polluting the global JSX namespace but I’m not sure when this stuff might land there (well, not sure if it ever lands there).

I’m happy to discuss this further if you’d like to resolve this here once and for all, I could even prepare a PR for this. I’m not a Vue user though and I lack certain expertise when it comes to understanding the butterfly effect of such a change. So if the team here would be willing to discuss this - let me know and we could go through this together to recheck if such a change could be introduced in a backwards-compatible manner.

I started getting these errors after installing storybook 3.6.10. My project’s stack is vite + vue3 (typescript), while storybook is using webpack and is based on react, so I’m making a wild guess that by adding storybook, these errors started surfacing because of react dependencies.

Type ‘{ class: string; }’ is not assignable to type ‘DetailedHTMLProps<OlHTMLAttributes, HTMLOListElement>’.\n Property ‘class’ does not exist on type ‘DetailedHTMLProps<OlHTMLAttributes, HTMLOListElement>’. Did you mean ‘className’?"

@olemarius Did you find a way to resolve this I’m having the same problem with Vue and Storybook setup with vite + vue3?

Using this thread to remind that because of those jsx types clobbering the global namespace (on vue 2.7.13 at least), React and Vue cannot be used on the same project which is a real problem.

FYI, namespace JSX can be renamed to avoid conflict (for example, VueJSX ).

And TypeScript uses VueJSX instead of JSX by putting this configuration into tsconfig.json .

"jsxFactory": "VueJSX"

I create a vue project with vue-cli. the project has a dependency of package named B. B has a dependency with react types. for example:

import type { PropsWithChildren } from 'react';

then my project emit errors:

Type ‘{ children: Element[]; class: string; }’ is not assignable to type ‘DetailedHTMLProps<HTMLAttributes<HTMLDivElement>, HTMLDivElement>’. Property ‘class’ does not exist on type ‘DetailedHTMLProps<HTMLAttributes<HTMLDivElement>, HTMLDivElement>’. Did you mean ‘className’?ts(2322)

here is my code: index.tsx:

import { defineComponent, ref } from 'vue';
import style from './index.module.less';

export default defineComponent({
  setup() {
    const activeTab = ref('tab-one');
    return () => (
      <div
        class={style.detail}
      >
        xxxx
      </div>
    )
  },
});

I strive for solving this, what can I do with this situation?

remove the package which has a dependency with react library, the error disappear.

by the way. I organized my project with mono repo. which has react project and vue project.

But are you going to use JSX/TSX in Vue, or are you going entirely with templates?

While this does make it compile, you still wouldn’t be able to use Vue TSX until you completely remove React typings?

Hi,

Try this in your tsconfig.json file

 "exclude": [
        "**/node_modules",
        "**/dist",
        // https://github.com/johnsoncodehk/volar/discussions/592
        "**/*.stories.ts"
    ]

I think the ide does not differnce beetween the subfolder projects.

Thank you for this perspective … because I believe/feel “mono repos are a other name for monoliths.”

try to reduce the overhead by managing the independent packages … a go back to move all in only one repo.

If you are disciplined, then you can also properly design/develop monoliths.

@elevatebart we haven’t yet implemented vue-next in storybook. you’re in uncharted territory! 😄

Thanks olemarius.

Adding this fixed it

// tsconfig.json
{
  "compilerOptions": {
    // ...
    "types": [
      "vite/client", // if using vite
      // ...
    ]
  }
}