Amplify-js: React Native - withAuthenticator - Custom Greetings UI

Created on 7 Dec 2018  路  9Comments  路  Source: aws-amplify/amplify-js

* Which Category is your question related to? *

  • Authentication

* What AWS Services are you utilizing? *

  • Cognito, AppSync

Hi There! Is it possible to replace the built in Greetings component in aws-amplify-react-native with a custom component when using withAuthenticator?

From looking at the related code for withAuthenticator here it appears that the Amplify's built-in Greetings component is hard-coded.

We've followed the documentation for custom UI here and have successfully built our own components for SignIn, etc. Unfortunately we have been unable override Greetings.

React Native

All 9 comments

Hi @jessedoyle,

Were you unable to override the Greetings component using these instructions:
https://aws-amplify.github.io/docs/js/authentication#customize-withauthenticator

You should be able to override the render function of the an extended Greetings component. If that does not work with the instructions above, there may be a bug.

You should also be able to disable the Greetings from appearing, build a custom one into the App, and implement your own functionality using the Auth api like so:

withAuthenticator(App, false); // 2nd param is the includeGreetings boolean

@jordanranz - I did try the overrides as per the documentation you linked without luck. I'm going to revisit our code today and see if we're making any mistakes.

If I'm able to build anything reproducible that illustrates the issue, I'll report back!

hey @jessedoyle,

Could you post some code of the overridden Greetings component and how you passed it to withAuthenticator. This would help us debug a bit further.

Hi @jordanranz! Thanks for reminding me of this issue!

We ended up going down an alternate path to achieve the same results (I'll explain this later), but I can give a brief overview of the issue we encountered.

Unfortunately I don't have the exact code we had written handy, but it was similar to this:

// App.js
import React from 'react';
import { StyleSheet } from 'react-native';
import { withAuthenticator } from 'aws-amplify-react-native';
import { 
  Greetings,
  Loading,
  SignIn,
  ForgotPassword
} from './customAuth';

const authComponents = [
  <Greetings />
  <Loading />,
  <SignIn />,
  <ForgotPassword />,
]

const App = ...

export default withAuthenticator(
  App,
  false,
  authComponents,
  null,
  StyleSheet.create({
    container: {
      flex: 1,
    },
  }),
);

// customAuth/Greetings.js
import React from 'react';
import { 
  Text,
  View
} from 'react-native';
import { Auth } from 'aws-amplify';
import { Greetings } from 'aws-amplify-react-native';

export default class CustomGreetings extends Greetings {
  render() {
    const name = Auth.user && Auth.user.username;
    const message = `Hello, ${name}`;

    return (
      <View>
        <Text>{message}</Text>
      </View>
    );
  }
}

Unfortunately this approach didn't work for us and the custom Greetings component didn't appear to display in the Authenticator component.

I wasn't able to troubleshoot the root issue, but I believe the custom Greetings component was not displayed due to the following:

  • The Greetings component defines a render function as opposed to a showComponent function.
  • The Greetings class does not set the _validAuthStates property in the constructor (example).

The approach we ultimately went forward with was creating our own custom component to display the user message by reading from Auth.currentAuthenticatedUser() directly. Our custom component was able to initiate a sign out by utilizing the onStateChange prop that is passed down from withAuthenticator.

I would say we were able to work around the issue we were encountering, so feel free to close this issue if necessary.

Glad you got this working!

I think your solution is the preferred way to achieve what you are asking for. Since the Greetings component simply provides a UI wrapper for sign out and username text, it is simpler to use the Auth method mentioned above and create your own Header above your app. I will close this for now. Please reopen if you experience any related issue.

Hi Guys!

Im also having some issues customizing authentication. Im trying to customize my withauthenticator as follows:

  const MyTheme = {
  googleSignInButton: { backgroundColor: "red", borderColor: "red" },
  button: { backgroundColor: "green", borderColor: "red" },
  signInButtonIcon: { display: "none" }
};

const signUpConfig = {
  header: 'My Customized Sign Up',
  hideAllDefaults: true,
  signUpFields: [
    {
      label: 'Email',
      key: 'email',
      required: true,
      displayOrder: 1,
      type: 'string'
    },
    {
      label: 'Username*',
      key: 'username',
      required: true,
      displayOrder: 1,
      type: 'string'
    },
    {
      label: 'Password',
      key: 'password',
      required: true,
      displayOrder: 2,
      type: 'password'
    },
  ],
};

export default withAuthenticator(App, false, [
<SignIn/>,
  <SignUp/>,
  <ForgotPassword/>,
  <RequireNewPassword/>
], null, MyTheme, {signUpConfig});
It appears that i can only either pass the auth components array (& theme) or the signUpConfig object but not both.

Any idea on how i can do both?

Thanks!!

@jessedoyle Can you please share the exact code you used to trigger sign out using onStateChange?
We tried to do the same without luck.

@evah88 - We moved to the withOAuth HOC (see: https://github.com/aws-amplify/amplify-js/pull/2665) to handle authentication so our code in this area has changed significantly.

Looking at some of our older commits, the code we had when using withAuthenticator to logout was similar to this:

async logout() {
  await Auth.signOut();
  // onStateChange function passed in as a prop from withAuthenticator
  this.props.onStateChange('signedOut');
}

I have my UI as same from the aws-amplify-react-native.

Now I needs to change for the custom UI.

If I change my UI, Shall I add the withAuthenticator and the screens.

I have AuthenticatorScreen.js file (, etc...) before. It has all the screens from aws-amplify-react-native.

How to add my custom screens inside the Authenticator.

The withAuthenticator file has an app. How it will be handled.

(or)

Shall I need to add all the screens in stackNavigator and create the navigations and add the Auth.signin and so on to do all the login methods.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

lucasmike picture lucasmike  路  3Comments

shinnapatthesix picture shinnapatthesix  路  3Comments

DougWoodCDS picture DougWoodCDS  路  3Comments

ldgarcia picture ldgarcia  路  3Comments

rygo6 picture rygo6  路  3Comments