Skip to content

React Native Example

Bradley Matusiak edited this page Dec 30, 2023 · 1 revision

GUN works out of the box with React Native. SEA & RAD do not, instructions below.

Looking for just React docs? Click here.

Dependencies

SEA & RAD require special configuration for React Native that currently do not work with Expo, so please make sure you follow these instructions:

npm install --save buffer text-encoding react-native-webview react-native-webview-bridge react-native-webview-crypto react-native-get-random-values @react-native-community/async-storage
react-native link

Make sure to check out WebviewCrypto instructions!

If you need any help, contact @adamblvck, @alterx, @sirpy, or @aethiop on the chat!

Now in your app initiate GUN like so:

import "gun/lib/mobile.js" // most important!
import GUN from 'gun/gun'
import SEA from 'gun/sea'
import 'gun/lib/radix.js'
import 'gun/lib/radisk.js'
import 'gun/lib/store.js'
import AsyncStorage from "@react-native-community/async-storage"
import asyncStore from 'gun/lib/ras.js'

// Warning: Android AsyncStorage has 6mb limit by default!
Gun({ store: asyncStore({ AsyncStorage }) })

To see a working example, check out this repo.

Warning: Android AsyncStorage has 6mb limit by default

To change this, add a android/gradle.properties file with AsyncStorage_db_size_in_MB=99!

Or you may want to try @alterx 's Expo SQLite adapter.

Tutorial

@aethiop wrote a much nicer, in-depth, tutorial - check it out!

We will show you how to build a mobile app version of the Hello World example with live synchronization between the mobile and the web app.

Step 1

Follow the Hello World steps here and create a simple GUN app. Modify the app to connect via a remote relay peer, if you don't have one you can use our demo server:

var gun = Gun('http://gunjs.herokuapp.com/gun')

Step 2: React Native Dev Environment

We are assuming you are familiar with React Native and have the environment set up. If not, follow the instructions in the "Building Projects with Native Code" tab here. Continue below when you were able to successfully launch and edit a React Native app on an emulator or real device.

Create a new React Native app:

react-native init HelloWorldGUN

This generates a HelloWorldGUN folder prepopulated with a barebones app.

Go to the HelloWorldGUN folder and add GUN to the project:

cd HelloWorldGUN
npm install gun

Now let's modify the App.js code file. First, import and define the GUN variable:

import Gun from 'gun/gun'
const gun = new Gun('http://gunjs.herokuapp.com/gun') // or use your own GUN relay
Component.prototype.$gun = gun

We will need a couple of UI controls, so add them to the import statement:

import {
//...
TextInput,
Button
} from 'react-native' 

Add a constructor to the App class where we initialize the state and set up the Gun sync object:

export default class App extends Component<Props> {
  constructor(props){
    super(props)
    this.state = {
      text: 'What is your name?',
      name: ''
    }
    this.$hello = this.$gun.get('hello')
    let _this = this
    this.$hello.on(function(data, key) {
      let name=data.name
      _this.setState({name:name})
    })
  }

Finally, replace the content of the render function's View component with the code below:

<Text style={styles.welcome}>
  Hello {this.state.name}
</Text>
<TextInput value={this.state.text}
  onChangeText={(text) => this.setState({text})} 
/>
<Button title='Update' 
  onPress={()=>{
    this.$hello.put({name:this.state.text})
    this.setState({text:''})}}
/>

Now try launching the app:

react-native run-android 
   or
react-native run-ios

You should be able to see the Hello line update on both app and web page with a new name when you press Submit button on either side!

Local Development

Let's say you've got a GUN relay running on a NodeJS process on your machine; while you're developing your React Native application, you want to connect up to that peer rather than some remote or production relay over the internet. Instead of giving localhost, provide the Local-Area-Network (LAN) IP address for your machine:

const gun = new Gun("http://192.168.0.01:8765/gun"); // example, replace with your IP!

Notes

Like NodeJS we need to shim WebCrypto, we do this with the webview bridge. isomorphic-webcrypto can also work but lacks in performance and has issues with encrypting large files. Some of the performance issues are related to the javascript engine, which can be improved by switching to JIT enabled versions of v8 or jsc:

Also, you can pass any storage plugin to the Store that implements the AsyncStorage setItem/getItem API.

Request! We're looking for a contributor to enable Expo support & write a higher-performance and no-limit based RAD storage plugin using one of the following:

Old

These older community-contributed storage adapters have been deprecated:

This wiki is where all the GUN website documentation comes from.

You can read it here or on the website, but the website has some special features like rendering some markdown extensions to create interactive coding tutorials.

Please feel free to improve the docs itself, we need contributions!

Clone this wiki locally