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

SvgUri example as given in README.md crashes in Expo Web #1742

Closed
raarts opened this issue Apr 9, 2022 · 14 comments
Closed

SvgUri example as given in README.md crashes in Expo Web #1742

raarts opened this issue Apr 9, 2022 · 14 comments
Labels
Close when stale This issue is going to be closed when there is no activity for a while

Comments

@raarts
Copy link

raarts commented Apr 9, 2022

Bug

I created a fresh expo app using expo init app-simple using the Typescript template. Added the SvgUri example.
Resulted in the following error in my console:

(I have to add, the standard Expo component supports svg if you install react-native-svg. If not, it will skip svg files without warning.)

index.js:1 Warning: React.jsx: type is invalid -- expected a string (for built-in components) or a class/function (for composite components) but got: undefined. You likely forgot to export your component from the file it's defined in, or you might have mixed up default and named imports.

Check the render method of `App`.
    at App
    at ExpoRootComponent (http://localhost:19007/static/js/bundle.js:8361:83)
    at div
    at http://localhost:19007/static/js/bundle.js:46754:25
    at div
    at http://localhost:19007/static/js/bundle.js:46754:25
    at AppContainer (http://localhost:19007/static/js/bundle.js:38675:24)
console.<computed> @ index.js:1
react-dom.development.js:25058 Uncaught Error: Element type is invalid: expected a string (for built-in components) or a class/function (for composite components) but got: undefined. You likely forgot to export your component from the file it's defined in, or you might have mixed up default and named imports.

Check the render method of `App`.
    at createFiberFromTypeAndProps (react-dom.development.js:25058:1)
    at createFiberFromElement (react-dom.development.js:25086:1)
    at createChild (react-dom.development.js:13446:1)
    at reconcileChildrenArray (react-dom.development.js:13719:1)
    at reconcileChildFibers (react-dom.development.js:14125:1)
    at reconcileChildren (react-dom.development.js:16990:1)
    at updateHostComponent (react-dom.development.js:17632:1)
    at beginWork (react-dom.development.js:19080:1)
    at HTMLUnknownElement.callCallback (react-dom.development.js:3945:1)
    at Object.invokeGuardedCallbackDev (react-dom.development.js:3994:1)
    at invokeGuardedCallback (react-dom.development.js:4056:1)
    at beginWork$1 (react-dom.development.js:23964:1)
    at performUnitOfWork (react-dom.development.js:22776:1)
    at workLoopSync (react-dom.development.js:22707:1)
    at renderRootSync (react-dom.development.js:22670:1)
    at performSyncWorkOnRoot (react-dom.development.js:22293:1)
    at scheduleUpdateOnFiber (react-dom.development.js:21881:1)
    at updateContainer (react-dom.development.js:25482:1)
    at react-dom.development.js:26021:1
    at unbatchedUpdates (react-dom.development.js:22431:1)
    at legacyRenderSubtreeIntoContainer (react-dom.development.js:26020:1)
    at render (react-dom.development.js:26103:1)
    at renderApplication (renderApplication.js:23:1)
    at Object.run (index.js:49:1)
    at Function.runApplication (index.js:93:1)
    at registerRootComponent (registerRootComponent.tsx:14:1)
    at Module../node_modules/expo/AppEntry.js (AppEntry.js:5:1)
    at __webpack_require__ (bootstrap:789:1)
    at fn (bootstrap:100:1)
    at Object.1 (tracing.js:7:1)
    at __webpack_require__ (bootstrap:789:1)
    at bootstrap:856:1
    at bootstrap:856:1

Environment info

Run react-native info in your terminal and copy the results here. Also, include the precise version number of this library that you are using in the project

React native info output:

System:
    OS: macOS 12.3.1
    CPU: (10) arm64 Apple M1 Pro
    Memory: 387.34 MB / 32.00 GB
    Shell: 5.8 - /bin/zsh
  Binaries:
    Node: 16.14.0 - /opt/homebrew/opt/node@16/bin/node
    Yarn: 1.22.17 - /opt/homebrew/bin/yarn
    npm: 8.3.1 - /opt/homebrew/opt/node@16/bin/npm
    Watchman: 2022.02.21.00 - /opt/homebrew/bin/watchman
  Managers:
    CocoaPods: 1.11.2 - /opt/homebrew/bin/pod
  SDKs:
    iOS SDK:
      Platforms: DriverKit 21.4, iOS 15.4, macOS 12.3, tvOS 15.4, watchOS 8.5
    Android SDK: Not Found
  IDEs:
    Android Studio: 2021.1 AI-211.7628.21.2111.8193401
    Xcode: 13.3/13E113 - /usr/bin/xcodebuild
  Languages:
    Java: 17.0.2 - /usr/bin/javac
  npmPackages:
    @react-native-community/cli: Not Found
    react: 17.0.1 => 17.0.1
    react-native: 0.64.3 => 0.64.3
    react-native-macos: Not Found
  npmGlobalPackages:
    *react-native*: Not Found

Library version: 12.1.1 (preferred by expo install, but same thing happend with 12.3.0)

Steps To Reproduce

Issues without reproduction steps or code are likely to stall.

  1. expo init app-simple (use typescript template)
  2. cd app-simple
  3. yarn add react-native-svg
  4. copy the example code for SvgUri into App.tsx
export default function App() {
  return (
    <View style={styles.container}>
      <Text>Open up App.tsx to start working on your app!</Text>
      <SvgUri
          // style={styles.image}
          width="100%"
          height="100%"
          uri="http://thenewcode.com/assets/images/thumbnails/homer-simpson.svg"
      />
      <StatusBar style="auto" />
    </View>
  );
}

Describe what you expected to happen:

I was expecting the app to show Homer. But it crashed and showed the above error instead.

@raarts raarts changed the title SvgUri example as given in README.md crashes in Expo Web in with Warning: React.jsx: type is invalid -- expected a string SvgUri example as given in README.md crashes in Expo Web Apr 9, 2022
@ansmlc
Copy link

ansmlc commented Apr 18, 2022

I have the same issue. Took forever to track here.

@raarts Have you found any workaround?

And can you explain what you mean by:
I have to add, the standard Expo component supports svg if you install react-native-svg. If not, it will skip svg files without warning.

@raarts
Copy link
Author

raarts commented Apr 18, 2022

I tried to show a list of remote images using FlatList and the Image component. This worked, except for the svg images.
To Solve this I tried to detect (by file extension) what the image type was, and use the appropriate component to display the image. That's when I found out about the crashing.

Later on I found out that if react-native-svg is installed the Image component will support svg. So, that's what I ended up doing.

@ansmlc
Copy link

ansmlc commented Apr 18, 2022

I tried to show a list of remote images using FlatList and the Image component. This worked, except for the svg images. To Solve this I tried to detect (by file extension) what the image type was, and use the appropriate component to display the image. That's when I found out about the crashing.

Later on I found out that if react-native-svg is installed the Image component will support svg. So, that's what I ended up doing.

I have react-native-svg installed but Image component still doesn't render svg images.

Did you still have to import { Svg } from 'react-native-svg';?

This is my Image component:

                    <Image
                        source={{
                        uri: icon,
                        }}
                    /

Any idea why it's not working?

@raarts
Copy link
Author

raarts commented Apr 18, 2022

No, I have no idea why it's not working, but are you sure you use uri properly? Mine is a http:// URL.

@ansmlc
Copy link

ansmlc commented Apr 19, 2022

No, I have no idea why it's not working, but are you sure you use uri properly? Mine is a http:// URL.

Mine is https:// URL.

Yes, it's corrent, I can see the SVG in DevTools inspect, when viewing in Expo Web:

<img alt="" draggable="false" src="https://res.cloudinary.com/dresqigku/image/upload/v1650007219/general_6d3491bccd.svg" class="css-accessibilityImage-9pa8cd">

There's no error, it just doesn't show anything.

When viewing in Expo iOS, it gives console warning:
"Failed prop type: Invalid prop 'source' supplied to 'Image', expected one of type [number, number].

Are you sure all you had to do is install react-native-svg for Image component to be able to accept SVG?

@raarts
Copy link
Author

raarts commented Apr 20, 2022

This is how I do it:

        <Image
          style={styles.image}
          source={{ uri: API_SERVER_URL + `/v1/s3/download?id=${item.id}` }}
          resizeMode="contain"
        />

I'm pretty sure I only needed to install react-native-svg.
Maybe the remote server needs to send the 'Content-Type': 'image/svg+xml' ? Mine does.

@grzabrodskiy
Copy link

Hi everyone, any idea when it is going to be fixed?
Using Image works for me on the web, but not on iOS (have not tried Android)

@Akronae
Copy link

Akronae commented Jan 12, 2023

I have the same bug. The only solution to display SVGs is either to use react-native Image, or if you wish to have your svg properly rendered to <svg> and stylable use Svg, Path, .. and construct it yourself. I guess that could be automated, but still a pain :/

@tmountain
Copy link

Same issues here, anybody making progress on this?

@ritute
Copy link

ritute commented Jun 14, 2023

Same issue here.

@airowe
Copy link

airowe commented Mar 13, 2024

Same issues here, anybody making progress on this?

@Bi0max
Copy link

Bi0max commented Mar 27, 2024

Same issue

@xavierhamel
Copy link

SvgUri does not seem to be implemented/supported for the web.

Here is a very quick fix that I have hacked together. There is probably a better way to do it.

Inside of node_modules/react-native-svg/lib/module/ReactNativeSVG.web.js or node_modules/react-native-svg/lib/commonjs/ReactNativeSVG.web.js (depending on which module you are using) add this:

export async function fetchText(uri) {
  const response = await fetch(uri);
  if (response.ok || response.status === 0 && uri.startsWith('file://')) {
    return await response.text();
  }
  throw new Error(`Fetching ${uri} failed with status ${response.status}`);
}
export function SvgUri(props) {
  const { onError, uri, onLoad, fallback } = props;
  const [xml, setXml] = React.useState(null);
  const [isError, setIsError] = React.useState(false);
  React.useEffect(() => {
    uri
      ? fetchText(uri)
          .then((data) => {
            setXml(data);
            isError && setIsError(false);
            onLoad?.();
          })
          .catch((e) => {
            onError(e);
            setIsError(true);
          })
      : setXml(null);
    // eslint-disable-next-line react-hooks/exhaustive-deps
  }, [onError, uri, onLoad]);
  if (isError) {
    return fallback ?? null;
  }
  if (!xml) {
      return fallback ?? null;
  }
  const encoded = encodeSvg(xml);
  return createElement("img", { src: "data:image/svg+xml," + encoded });
}

I have placed it after the function measureLayout at the line 160, but it should work elsewhere.

You should save your patch with patch-package afterwards.

jakex7 pushed a commit that referenced this issue Jul 29, 2024
…1916)

# Summary

**What issues does the pull request solve? Please tag them so that they
will get automatically closed once the PR is merged**

When utilizing with `react-native-web`: SvgXml and SvgUri are not
exported in the `src/ReactNativeSVG.web.ts` extension. The logic for
SvgXml and SvgUri do not have native dependencies, so they are safe to
consume on web.

Issues:
- #1279
- #1742

**What is the feature? (if applicable)**

Add SvgXml and SvgUri as consumable exports for `react-native-web`

**How did you implement the solution?**

Extract `tags` to shapes map into separate `tags.tsx` file, where native
shape elements and web shape elements can be provided to their
respective envs.

**What areas of the library does it impact?**

`src` directory

## Test Plan

Demonstrate the code is solid. Example: The exact commands you ran and
their output, screenshots / videos if the pull request changes UI.

### What's required for testing (prerequisites)?
n/a

### What are the steps to reproduce (after prerequisites)?
n/a

## Compatibility

| OS      | Implemented |
| ------- | :---------: |
| iOS     |    ✅     |
| Android |    ✅     |

## Checklist

<!-- Check completed item, when applicable, via: [X] -->

- [x] I have tested this on a device and a simulator
- [x] I added documentation in `README.md`
- [x] I updated the typed files (typescript)
- [ ] I added a test for the API in the `__tests__` folder

---------

Co-authored-by: bohdanprog <bohdan.artiukhov@swmansion.com>
@bohdanprog
Copy link
Member

Hello @airowe @raarts @tmountain,
It should work now.
But if you are still having that problem, please don't hesitate to let us know.
here is an example of how you can check that problem:

import {View, Text} from 'react-native';
import {SvgUri} from 'react-native-svg';

export default function App() {
  return (
    <View style={{flex: 1, backgroundColor: 'purple'}}>
      <Text>Open up App.tsx to start working on your app!</Text>
      <SvgUri
        width="100%"
        height="100%"
        uri="https://upload.wikimedia.org/wikipedia/commons/7/73/Ruby_logo.svg"
      />
    </View>
  );
}

Thank you.

@bohdanprog bohdanprog added the Close when stale This issue is going to be closed when there is no activity for a while label Aug 27, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Close when stale This issue is going to be closed when there is no activity for a while
Projects
None yet
Development

No branches or pull requests

10 participants