Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

JSX.IntrinsicElements error with typescript and react #1090

Closed
ywwu1 opened this issue Sep 13, 2018 · 18 comments
Closed

JSX.IntrinsicElements error with typescript and react #1090

ywwu1 opened this issue Sep 13, 2018 · 18 comments
Assignees

Comments

@ywwu1
Copy link

ywwu1 commented Sep 13, 2018

Stencil version:

I'm submitting a:

[ x ] bug report
[ ] feature request
[ ] support request => Please do not submit support requests here, use one of these channels: https://stencil-worldwide.herokuapp.com/ or https://forum.ionicframework.com/

Current behavior:

I upgrade to version @stencil/[email protected], the latest typescript, react, react-dom, and associated typings. After building the stencil component in it's own repo I imported the component using defineCustomElements, however typescript is throwing an error Property 'hello-world' does not exist on type 'JSX.IntrinsicElements' when I try to start the project.

Expected behavior:

There should be no errors.

Steps to reproduce:

I have created a repo demonstrating the bug, here.
https://github.com/ywwu1/__stencil-react-typescript-jsx-issue

The stencil component is located here.
https://github.com/ywwu1/hello-world

@ionitron-bot ionitron-bot bot added the triage label Sep 13, 2018
@hartjus
Copy link

hartjus commented Sep 26, 2018

I'm running into this issue as well. I noticed that the typings for JSX in Typescript were removed in 0.12.4. Is there a recommended way to integrate built stencil components into a react/typescript application? Do I need to author my own d.ts to get around the compile errors?

@cbyte
Copy link

cbyte commented Oct 17, 2018

Same problem here. I created manually an components.d.ts in the root folder of the project to define the element declarations by hand. This is not a good solution overall, but works for the moment.

Now i step into the problem, how to include multiple compiled packages, because defineCustomElements() cannot be called multiple times - it throws the error Uncaught (in promise) TypeError: Cannot redefine property: queue.

Here is the self defined component.d.ts as temporarily solution to include one compiled stencil package:

import { Components } from "@ionic/core";

declare global {
  namespace JSX {
    interface IntrinsicElements {
       [...]
      "ion-toggle": Components.IonToggleAttributes;
      "ion-toolbar": Components.IonToolbarAttributes;
      "ion-virtual-scroll": Components.IonVirtualScrollAttributes;
    }
  }
}

@lcgreen
Copy link

lcgreen commented Oct 23, 2018

Also experiencing the same issue, is there no update on this? Authoring our own components.d.ts is not a solution.

@Dohxis
Copy link

Dohxis commented Oct 28, 2018

We are experiencing this as well.

@maraisr
Copy link

maraisr commented Oct 28, 2018

Bumping +1

@arjunyel
Copy link
Contributor

Anyone have a workaround?

@Dohxis
Copy link

Dohxis commented Nov 12, 2018

Right now we maintain our own types.d.ts file as suggested by @cbyte.

@ghost
Copy link

ghost commented Nov 15, 2018

I found the same error when I was updating my library :( If you see something... I'll appreciate your help.

Hi,

I take the comment to put here something has worked for me. I removed the components.d.ts file, and the node_modules folder, after it, I installed the packages again with yarn, and the problem was solved.

Now, the components.d.ts file autogenerated has this.

  export namespace JSX {
    export interface Element {}
    export interface IntrinsicElements extends StencilIntrinsicElements {
      [tagName: string]: any;
    }
  }

I hope it works for you also.

Thanks! :)

@alex-hall
Copy link

alex-hall commented Jan 16, 2019

Any movement on this?

Have gone with the following hack for now:

//jsx-interfaces.d.ts
declare namespace JSX {
    interface IntrinsicElements {
        [tagName:string]: any
    }
}

Which basically just turns off Typescript JSX validation. NOTE: I do NOT like this solution.

I feel like i'm missing something obvious here, as all of the types are seemingly defined in:

<my_stencil_component>/dist/types/components.d.ts

But I can't seem to get create-react-app to recognize them or import them.

@hartjus
Copy link

hartjus commented Jan 16, 2019

@alex-hall We ended up having to author (actually generate) our own d.ts for any stencil components that we pulled into our project. Stencil is generating most of the type definitions required, however there's the last step of adding the JSX tag into the global definitions.

Here's the basic structure of what we generated:

import {Components as SomeOtherName} from 'your-stencil-component';

declare global {
    namespace JSX {
        export interface IntrinsicElements {
            'your-component-tag': SomeOtherName.YourComponentAttributes;
        }
    }
}

While this works, it's definitely not ideal.

@alex-hall
Copy link

Gotcha, Thanks for the quick response.

I felt like I was doing the right thing but nothing was working. Your explanation makes a lot of sense.

@alex-hall
Copy link

alex-hall commented Jan 16, 2019

Now i'm considering a PR :)

async function generateComponentTypesFile(config: d.Config, compilerCtx: d.CompilerCtx, metadata: d.ModuleFile[], destination: string) {

The information looks to be correctly generated in the original source, it just never makes it into the bundled version:

//src/components.d.ts
  export namespace JSX {
    export interface Element {}
    export interface IntrinsicElements extends StencilIntrinsicElements {
      [tagName: string]: any;
    }
  }
  export interface HTMLAttributes extends StencilHTMLAttributes {}

@SimoneIrato
Copy link

Did anybody find a solution for this problem? Actually when using StencilJs in a monorepo, JSX typings from Stencil conflicts with those from React

@manucorporat
Copy link
Contributor

Upcoming version of stencil will completely solve this problem by using locally scoped JSX namespaces, a new feature of typescript!

@vidarc
Copy link
Contributor

vidarc commented Apr 5, 2019

@manucorporat has that made it in stencil/core version 1 yet? i'm currently using alpha 5, but not really seeing a way to get the typing in my react project to work. i can easily just ignore it by using one of the examples above and basically setting the component to an any type. would certainly prefer to not do that.

using any of my stencil components, like <ma-icon>, just gives the Property 'ma-icon' does not exist on type 'JSX.IntrinsicElements'. error

@manucorporat
Copy link
Contributor

Stencil one uses locally scoped JSX, which is the final solution to the root of the problem, global styles conflicting with each other

@nireak
Copy link

nireak commented May 27, 2019

I still have the same error when using, inside a CRA 3.0 typescript react app, a webcomponent ("vertical-fields") created with "@stencil/core": "^1.0.0-beta.5"

Within the main "index.tsx" I'm loading the definitions with

...
import { defineCustomElements } from 'mywebcomponent/dist/loader'
...
defineCustomElements(window)

the file at node_modules/mywebcomponent/dist/types/components.d.ts seems to use locally scoped JSX

import { HTMLStencilElement, JSXBase } from './stencil.core';


export namespace Components {
  interface VerticalFields {
    'colorvorh': string;
    'levels': number;
  }
}

declare namespace LocalJSX {
  interface VerticalFields extends JSXBase.HTMLAttributes {
    'colorvorh'?: string;
    'levels'?: number;
  }
  interface IntrinsicElements {
    'vertical-fields': VerticalFields;
  }
}
export { LocalJSX as JSX };
declare module "@stencil/core" {
  export namespace JSX {
    interface IntrinsicElements extends LocalJSX.IntrinsicElements {}
  }
}
declare global {
  interface HTMLVerticalFieldsElement extends Components.VerticalFields, HTMLStencilElement {}
  var HTMLVerticalFieldsElement: {
    prototype: HTMLVerticalFieldsElement;
    new (): HTMLVerticalFieldsElement;
  };
  interface HTMLElementTagNameMap {
    'vertical-fields': HTMLVerticalFieldsElement;
  }
  interface ElementTagNameMap extends HTMLElementTagNameMap {}
}

Any ideas? Thank you

@Nibblesh
Copy link

Nibblesh commented Jun 12, 2019

for people struggling with this, I've gotten things working this way

// register-web-components.ts
/* eslint-disable */
import { defineCustomElements, JSX as LocalJSX } from 'stencil-library/dist/loader';
import { HTMLAttributes } from 'react';

type StencilToReact<T> = {
  [P in keyof T]?: T[P] & Omit<HTMLAttributes<Element>, 'className'> & {
    class?: string;
  };
} ;

declare global {
  export namespace JSX {
    interface IntrinsicElements extends StencilToReact<LocalJSX.IntrinsicElements> {
    }
  }
}

defineCustomElements(window)
// index.ts
// ...
import './register-web-components';
// ...

eslint will shout about using declare global but this is keeping me going for now. gets auto complete working

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests