forked from Azure/azure-sdk-for-js
-
Notifications
You must be signed in to change notification settings - Fork 16
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[react-native] Add a basic sample for AppConfiguration (Azure#21907)
* [react-native] Add a basic sample for AppConfiguration * Apply suggestions from code review Co-authored-by: Harsha Nalluru <sanallur@microsoft.com> Co-authored-by: Harsha Nalluru <sanallur@microsoft.com>
- Loading branch information
1 parent
47dd3d6
commit bbc4e39
Showing
14 changed files
with
6,220 additions
and
0 deletions.
There are no files selected for viewing
15 changes: 15 additions & 0 deletions
15
samples/frameworks/react-native-expo/ts/appconfigBasic/.gitignore
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,15 @@ | ||
node_modules/ | ||
.expo/ | ||
dist/ | ||
npm-debug.* | ||
*.jks | ||
*.p8 | ||
*.p12 | ||
*.key | ||
*.mobileprovision | ||
*.orig.* | ||
web-build/ | ||
.env | ||
|
||
# macOS | ||
.DS_Store |
24 changes: 24 additions & 0 deletions
24
samples/frameworks/react-native-expo/ts/appconfigBasic/App.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,24 @@ | ||
import { StatusBar } from 'expo-status-bar'; | ||
import { Button, StyleSheet, Text, View } from 'react-native'; | ||
|
||
import "./shims"; | ||
import { runAppConfigSample } from "./appConfigSample"; | ||
|
||
export default function App() { | ||
return ( | ||
<View style={styles.container}> | ||
<Text>Open up App.tsx to start working on your app!</Text> | ||
<Button title="Click me!" onPress={() => runAppConfigSample() } /> | ||
<StatusBar style="auto" /> | ||
</View> | ||
); | ||
} | ||
|
||
const styles = StyleSheet.create({ | ||
container: { | ||
flex: 1, | ||
backgroundColor: '#fff', | ||
alignItems: 'center', | ||
justifyContent: 'center', | ||
}, | ||
}); |
128 changes: 128 additions & 0 deletions
128
samples/frameworks/react-native-expo/ts/appconfigBasic/README.md
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,128 @@ | ||
# Azure SDK samples for React Native using Expo (TypeScript) | ||
|
||
This sample application shows how to use the TypeScript client libraries for Azure in some common scenarios. | ||
|
||
In this sample, we build a simple application in React Native using Expo and integrating with Azure App Configuration service. | ||
|
||
## Prerequisites | ||
|
||
The samples are compatible with [LTS versions of Node.js](https://nodejs.org/about/releases/). | ||
|
||
Before running the samples in Node, they must be compiled to JavaScript using the TypeScript compiler. For more information on TypeScript, see the [TypeScript documentation][typescript]. | ||
|
||
The sample is using [Expo](https://expo.dev/), a framework and platform for universal React applications. | ||
|
||
You need [an Azure subscription][freesub] and the following resources created to run this sample: | ||
|
||
## Step by step | ||
|
||
### Create the project | ||
|
||
Run expo CLI to create a blank project with typescript support, give it a name of `appconf-rn-expo`. | ||
|
||
```shell | ||
expo init -t expo-template-blank-typescript | ||
``` | ||
|
||
At this point, we should be able to see the app running if the environment is set up correctly | ||
|
||
```shell | ||
expo start --android | ||
``` | ||
|
||
### Add a button to the app | ||
|
||
Open App.tsx and add the following code so it looks similar to following code | ||
```diff | ||
-import { StyleSheet, Text, View } from 'react-native'; | ||
+import { Button, StyleSheet, Text, View } from 'react-native'; | ||
+import { runAppConfigSample } from "./appConfigSample"; | ||
... | ||
|
||
<Text>Open up App.tsx to start working on your app!</Text> | ||
+ <Button title="Click me!" onPress={() => runAppConfigSample() } /> | ||
<StatusBar style="auto" /> | ||
``` | ||
|
||
### Add the App Configuration sample file | ||
|
||
create a new file `appConfigSample.ts` in the sample directory as `App.tsx` with following content from [appConfigSample.ts](./appConfigSample.ts) file | ||
|
||
### Add dependencies | ||
|
||
We need to add a dependency to the JavaScript Client SDK library for Azure App Configuration (version 1.4.0-beta.1 or later). We use `@babel/plugin-proposal-async-generator-functions` to help transform async iterator usage in our sample. We also use `babel-plugin-inline-dotenv` to help load secrets from our `.env` file while developing. | ||
|
||
```shell | ||
yarn add @azure/app-configuration@1.4.0-beta.1 | ||
yarn add --dev babel-plugin-inline-dotenv @babel/plugin-proposal-async-generator-functions | ||
``` | ||
|
||
Then add the following into `babel.config.js` to enable the plugin | ||
|
||
```diff | ||
presets: ["babel-preset-expo"], | ||
+ plugins: [ | ||
+ "@babel/plugin-proposal-async-generator-functions", | ||
+ ["inline-dotenv", { unsafe: true }], | ||
+ ], | ||
``` | ||
|
||
### Add connection string to .env file | ||
|
||
Create a `.env` file in the project directory. Retrieve your connection string from Azure portal and add them to the `.env` file. Since this file contains secrets you need to add it to the ignore list if your code is committed to a repository. | ||
|
||
**Note** We use connection string directly here for testing purpose. You should consider the trade-off between security and convenience and better use a backend to dynamically provide secrets to only authenticated users. | ||
|
||
``` | ||
APPCONFIG_CONNECTION_STRING="<your app configuration connection string>" | ||
``` | ||
|
||
**Note**: if you update the .env file, you would need to clear expo cache and rebuild. It can be done by passing `-c` to the start command, for example, in `package.json` | ||
|
||
```diff | ||
- "android": "expo start --android", | ||
+ "android": "expo start --android -c", | ||
``` | ||
|
||
### Add polyfills | ||
|
||
The `crypto` dependency of the JavaScript Client SDK library for Azure App Configuration are not available in React-Native, so we need to provide polyfills for them. We also need to polyfill the `TextEncoder` API. Add the following dependencies to the project | ||
|
||
```shell | ||
yarn add isomorphic-webcrypto react-native-get-random-values react-native-url-polyfill text-encoding-polyfill | ||
``` | ||
|
||
Then add a `shims.ts` file in the project root with the following content | ||
|
||
```typescript | ||
import 'react-native-url-polyfill/auto'; | ||
import "react-native-get-random-values"; | ||
import "text-encoding-polyfill"; | ||
const getRandomValues = global.crypto.getRandomValues; | ||
import * as crypto from "isomorphic-webcrypto"; | ||
global.crypto = crypto; | ||
global.crypto.getRandomValues = getRandomValues; | ||
``` | ||
|
||
Then add the following line to `App.tsx` | ||
|
||
```diff | ||
+import "./shims"; | ||
import { runAppConfigSample } from "./appConfigSample"; | ||
``` | ||
|
||
Now run the app in the emulator (Android in this case) | ||
|
||
```shell | ||
npm run android | ||
``` | ||
|
||
Click on the **CLICK ME!** button, you should see the following logged to the console output! | ||
|
||
``` | ||
Running helloworld sample | ||
Adding in new setting Samples:Greeting | ||
Samples:Greeting has been set to Hello! | ||
Samples:Greeting has been set to Goodbye! | ||
Samples:Greeting has been deleted | ||
``` |
32 changes: 32 additions & 0 deletions
32
samples/frameworks/react-native-expo/ts/appconfigBasic/app.json
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
{ | ||
"expo": { | ||
"name": "appconf-rn-expo", | ||
"slug": "appconf-rn-expo", | ||
"version": "1.0.0", | ||
"orientation": "portrait", | ||
"icon": "./assets/icon.png", | ||
"splash": { | ||
"image": "./assets/splash.png", | ||
"resizeMode": "contain", | ||
"backgroundColor": "#ffffff" | ||
}, | ||
"updates": { | ||
"fallbackToCacheTimeout": 0 | ||
}, | ||
"assetBundlePatterns": [ | ||
"**/*" | ||
], | ||
"ios": { | ||
"supportsTablet": true | ||
}, | ||
"android": { | ||
"adaptiveIcon": { | ||
"foregroundImage": "./assets/adaptive-icon.png", | ||
"backgroundColor": "#FFFFFF" | ||
} | ||
}, | ||
"web": { | ||
"favicon": "./assets/favicon.png" | ||
} | ||
} | ||
} |
54 changes: 54 additions & 0 deletions
54
samples/frameworks/react-native-expo/ts/appconfigBasic/appConfigSample.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,54 @@ | ||
/** | ||
* @summary Demonstrates the CRUD operations on the configuration settings. | ||
*/ | ||
import { AppConfigurationClient } from "@azure/app-configuration"; | ||
|
||
export async function runAppConfigSample() { | ||
console.log(`Running helloworld sample`); | ||
|
||
// Set the following environment variable or edit the value on the following line. | ||
const connectionString = | ||
process.env["APPCONFIG_CONNECTION_STRING"] || "<connection string>"; | ||
const client = new AppConfigurationClient(connectionString); | ||
|
||
const greetingKey = "Samples:Greeting"; | ||
|
||
await cleanupSampleValues([greetingKey], client); | ||
|
||
// creating a new setting | ||
console.log(`Adding in new setting ${greetingKey}`); | ||
await client.addConfigurationSetting({ key: greetingKey, value: "Hello!" }); | ||
|
||
const newSetting = await client.getConfigurationSetting({ key: greetingKey }); | ||
console.log(`${greetingKey} has been set to ${newSetting.value}`); | ||
|
||
// changing the value of a setting | ||
await client.setConfigurationSetting({ key: greetingKey, value: "Goodbye!" }); | ||
|
||
const updatedSetting = await client.getConfigurationSetting({ | ||
key: greetingKey, | ||
}); | ||
console.log(`${greetingKey} has been set to ${updatedSetting.value}`); | ||
|
||
// removing the setting | ||
await client.deleteConfigurationSetting({ key: greetingKey }); | ||
console.log(`${greetingKey} has been deleted`); | ||
|
||
await cleanupSampleValues([greetingKey], client); | ||
} | ||
|
||
async function cleanupSampleValues( | ||
keys: string[], | ||
client: AppConfigurationClient | ||
) { | ||
const settingsIterator = client.listConfigurationSettings({ | ||
keyFilter: keys.join(","), | ||
}); | ||
|
||
for await (const setting of settingsIterator) { | ||
await client.deleteConfigurationSetting({ | ||
key: setting.key, | ||
label: setting.label, | ||
}); | ||
} | ||
} |
Binary file added
BIN
+17.1 KB
samples/frameworks/react-native-expo/ts/appconfigBasic/assets/adaptive-icon.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added
BIN
+1.43 KB
samples/frameworks/react-native-expo/ts/appconfigBasic/assets/favicon.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added
BIN
+21.9 KB
samples/frameworks/react-native-expo/ts/appconfigBasic/assets/icon.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added
BIN
+46.2 KB
samples/frameworks/react-native-expo/ts/appconfigBasic/assets/splash.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
10 changes: 10 additions & 0 deletions
10
samples/frameworks/react-native-expo/ts/appconfigBasic/babel.config.js
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,10 @@ | ||
module.exports = function(api) { | ||
api.cache(true); | ||
return { | ||
presets: ["babel-preset-expo"], | ||
plugins: [ | ||
"@babel/plugin-proposal-async-generator-functions", | ||
["inline-dotenv", { unsafe: true }], | ||
], | ||
}; | ||
}; |
34 changes: 34 additions & 0 deletions
34
samples/frameworks/react-native-expo/ts/appconfigBasic/package.json
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,34 @@ | ||
{ | ||
"name": "appconf-rn-expo", | ||
"version": "1.0.0", | ||
"main": "node_modules/expo/AppEntry.js", | ||
"scripts": { | ||
"start": "expo start", | ||
"android": "expo start --android", | ||
"ios": "expo start --ios", | ||
"web": "expo start --web", | ||
"eject": "expo eject" | ||
}, | ||
"dependencies": { | ||
"@azure/app-configuration": "1.4.0-beta.1", | ||
"expo": "~44.0.0", | ||
"expo-status-bar": "~1.2.0", | ||
"isomorphic-webcrypto": "^2.3.8", | ||
"react": "17.0.1", | ||
"react-dom": "17.0.1", | ||
"react-native": "0.64.3", | ||
"react-native-get-random-values": "^1.7.2", | ||
"react-native-url-polyfill": "^1.3.0", | ||
"react-native-web": "0.17.1", | ||
"text-encoding-polyfill": "^0.6.7" | ||
}, | ||
"devDependencies": { | ||
"@babel/core": "^7.12.9", | ||
"@babel/plugin-proposal-async-generator-functions": "^7.16.8", | ||
"@types/react": "~17.0.21", | ||
"@types/react-native": "~0.64.12", | ||
"babel-plugin-inline-dotenv": "^1.7.0", | ||
"typescript": "~4.3.5" | ||
}, | ||
"private": true | ||
} |
7 changes: 7 additions & 0 deletions
7
samples/frameworks/react-native-expo/ts/appconfigBasic/shims.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,7 @@ | ||
import 'react-native-url-polyfill/auto'; | ||
import "react-native-get-random-values"; | ||
import "text-encoding-polyfill"; | ||
const getRandomValues = global.crypto.getRandomValues; | ||
import * as crypto from "isomorphic-webcrypto"; | ||
global.crypto = crypto; | ||
global.crypto.getRandomValues = getRandomValues; |
6 changes: 6 additions & 0 deletions
6
samples/frameworks/react-native-expo/ts/appconfigBasic/tsconfig.json
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
{ | ||
"extends": "expo/tsconfig.base", | ||
"compilerOptions": { | ||
"strict": true | ||
} | ||
} |
Oops, something went wrong.