Skip to content

Commit d57ffd2

Browse files
committed
(DOCSP-27001): @realm/react-ify 'Query MongoDB' page (mongodb#2566)
## Pull Request Info @realm/react-ify 'Query MongoDB' page ### Jira - https://jira.mongodb.org/browse/DOCSP-27001 ### Staged Changes - [Query MongoDB (React Native)](https://docs-mongodbcom-staging.corp.mongodb.com/realm/docsworker-xlarge/DOCSP-27001/sdk/react-native/app-services/query-mongodb/) ### Reminder Checklist If your PR modifies the docs, you might need to also update some corresponding pages. Check if completed or N/A. - [x] Create Jira ticket for corresponding docs-app-services update(s), if any - [x] Checked/updated Admin API - [x] Checked/updated CLI reference ### Review Guidelines [REVIEWING.md](https://github.com/mongodb/docs-realm/blob/master/REVIEWING.md)
1 parent 8fdfc70 commit d57ffd2

File tree

7 files changed

+248
-13
lines changed

7 files changed

+248
-13
lines changed

examples/react-native/.eslintrc.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
module.exports = {
22
root: true,
3-
extends: ['@react-native-community', 'prettier'],
3+
extends: ['@react-native-community'],
44
parser: '@typescript-eslint/parser',
5-
plugins: ['@typescript-eslint'],
5+
plugins: ['@typescript-eslint', 'prettier'],
66
env: {
77
jest: true,
88
},

examples/react-native/.prettierrc.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,5 +7,5 @@ module.exports = {
77
trailingComma: 'all',
88
quoteProps: 'preserve',
99
jsxSingleQuote: true, // do not remove this line, otherwise the bluehawk replacement of testIDs won't work
10-
printWidth: 300,
10+
printWidth: 80,
1111
};
Lines changed: 92 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,92 @@
1+
// :snippet-start: mongodb
2+
import React from 'react';
3+
import {useUser} from '@realm/react';
4+
// :remove-start:
5+
import {Credentials, BSON} from 'realm';
6+
import {useEffect} from 'react';
7+
import {App} from 'realm';
8+
import {AppProvider, UserProvider, useApp} from '@realm/react';
9+
import {render, fireEvent, waitFor} from '@testing-library/react-native';
10+
import {View, Button} from 'react-native';
11+
12+
const APP_ID = 'example-testers-kvjdy';
13+
14+
function AppWrapper() {
15+
return (
16+
<View>
17+
<AppProvider id={APP_ID}>
18+
<UserProvider fallback={<LogIn />}>
19+
<QueryPlants />
20+
</UserProvider>
21+
</AppProvider>
22+
</View>
23+
);
24+
}
25+
26+
function LogIn() {
27+
const app = useApp();
28+
29+
useEffect(() => {
30+
app.logIn(Credentials.anonymous()).then(async user => {
31+
const plants = user
32+
.mongoClient('mongodb-atlas')
33+
.db('example')
34+
.collection('plants');
35+
try {
36+
await plants.insertOne({
37+
_id: new BSON.ObjectId('5f87976b7b800b285345a8b4'),
38+
name: 'venus flytrap',
39+
sunlight: 'full',
40+
color: 'white',
41+
type: 'perennial',
42+
_partition: 'Store 42',
43+
});
44+
} catch (err) {
45+
console.error(err);
46+
}
47+
});
48+
}, []);
49+
return <></>;
50+
}
51+
52+
let higherScopedVenusFlyTrap;
53+
// :remove-end:
54+
55+
function QueryPlants() {
56+
// Get currently logged in user
57+
const user = useUser();
58+
59+
const getPlantByName = async name => {
60+
// Access linked MongoDB collection
61+
const mongodb = user.mongoClient('mongodb-atlas');
62+
const plants = mongodb.db('example').collection('plants');
63+
// Query the collection
64+
const response = await plants.findOne({name});
65+
higherScopedVenusFlyTrap = response; // :remove:
66+
67+
return response;
68+
};
69+
// ...
70+
// :remove-start:
71+
return (
72+
<Button
73+
onPress={() => getPlantByName('venus flytrap')}
74+
testID='test-mongodb-call'
75+
title='Test Me!'
76+
/>
77+
);
78+
// :remove-end:
79+
}
80+
// :snippet-end:
81+
82+
afterEach(async () => await App.getApp(APP_ID).currentUser?.logOut());
83+
84+
test('Use MongoDB Data Access', async () => {
85+
const {getByTestId} = render(<AppWrapper />);
86+
87+
const button = await waitFor(() => getByTestId('test-mongodb-call'));
88+
fireEvent.press(button);
89+
await waitFor(() =>
90+
expect(higherScopedVenusFlyTrap?.name).toBe('venus flytrap'),
91+
);
92+
});
Lines changed: 104 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,104 @@
1+
// :snippet-start: mongodb
2+
import React from 'react';
3+
import {useUser} from '@realm/react';
4+
// :remove-start:
5+
import {Credentials, BSON} from 'realm';
6+
import {useEffect} from 'react';
7+
import {App} from 'realm';
8+
import {AppProvider, UserProvider, useApp} from '@realm/react';
9+
import {render, fireEvent, waitFor} from '@testing-library/react-native';
10+
import {View, Button} from 'react-native';
11+
12+
const APP_ID = 'example-testers-kvjdy';
13+
14+
function AppWrapper() {
15+
return (
16+
<View>
17+
<AppProvider id={APP_ID}>
18+
<UserProvider fallback={<LogIn />}>
19+
<QueryPlants />
20+
</UserProvider>
21+
</AppProvider>
22+
</View>
23+
);
24+
}
25+
26+
function LogIn() {
27+
const app = useApp();
28+
29+
useEffect(() => {
30+
app.logIn(Credentials.anonymous()).then(async user => {
31+
const plants = user
32+
.mongoClient('mongodb-atlas')
33+
.db('example')
34+
.collection<Plant>('plants');
35+
try {
36+
await plants.insertOne({
37+
_id: new BSON.ObjectId('5f87976b7b800b285345a8b4'),
38+
name: 'venus flytrap',
39+
sunlight: 'full',
40+
color: 'white',
41+
type: 'perennial',
42+
_partition: 'Store 42',
43+
});
44+
} catch (err) {
45+
console.error(err);
46+
}
47+
});
48+
}, []);
49+
return <></>;
50+
}
51+
52+
let higherScopedVenusFlyTrap: Plant | null;
53+
54+
type Plant = {
55+
_id: BSON.ObjectId;
56+
_partition: string;
57+
name: string;
58+
sunlight?: string;
59+
color?: string;
60+
type?: string;
61+
};
62+
// :remove-end:
63+
64+
function QueryPlants() {
65+
// Get currently logged in user
66+
const user = useUser();
67+
68+
const getPlantByName = async (name: string) => {
69+
// Access linked MongoDB collection
70+
const mongodb = user.mongoClient('mongodb-atlas');
71+
const plants = mongodb.db('example').collection<Plant>('plants');
72+
// Query the collection
73+
const response = await plants.findOne({name});
74+
higherScopedVenusFlyTrap = response; // :remove:
75+
76+
return response;
77+
};
78+
// ...
79+
// :remove-start:
80+
return (
81+
<Button
82+
onPress={() => getPlantByName('venus flytrap')}
83+
testID='test-mongodb-call'
84+
title='Test Me!'
85+
/>
86+
);
87+
// :remove-end:
88+
}
89+
// :snippet-end:
90+
91+
afterEach(async () => await App.getApp(APP_ID).currentUser?.logOut());
92+
93+
test('Use MongoDB Data Access', async () => {
94+
const {getByTestId} = render(<AppWrapper />);
95+
96+
const button = await waitFor(() => getByTestId('test-mongodb-call'));
97+
fireEvent.press(button);
98+
await waitFor(() =>
99+
expect(higherScopedVenusFlyTrap?.name).toBe('venus flytrap'),
100+
);
101+
});
102+
103+
// Note: rest of the examples on React Native 'query MongoDB' page can be found
104+
// in the Node.js unit test suite in the file `examples/node/Examples/mongodb.js`.
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
import React from 'react';
2+
import {useUser} from '@realm/react';
3+
4+
function QueryPlants() {
5+
// Get currently logged in user
6+
const user = useUser();
7+
8+
const getPlantByName = async name => {
9+
// Access linked MongoDB collection
10+
const mongodb = user.mongoClient('mongodb-atlas');
11+
const plants = mongodb.db('example').collection('plants');
12+
// Query the collection
13+
const response = await plants.findOne({name});
14+
15+
return response;
16+
};
17+
// ...
18+
}
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
import React from 'react';
2+
import {useUser} from '@realm/react';
3+
4+
function QueryPlants() {
5+
// Get currently logged in user
6+
const user = useUser();
7+
8+
const getPlantByName = async (name: string) => {
9+
// Access linked MongoDB collection
10+
const mongodb = user.mongoClient('mongodb-atlas');
11+
const plants = mongodb.db('example').collection<Plant>('plants');
12+
// Query the collection
13+
const response = await plants.findOne({name});
14+
15+
return response;
16+
};
17+
// ...
18+
}

source/sdk/react-native/app-services/query-mongodb.txt

Lines changed: 13 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -79,23 +79,26 @@ in the App Services documentation.
7979
Connect to a Linked Cluster
8080
---------------------------
8181

82-
To access a linked cluster from your client application, pass the cluster name
83-
to :js-sdk:`User.mongoClient() <Realm.User.html#mongoClient>`. This returns a
84-
MongoDB service interface that you can use to access databases and collections
85-
in the cluster.
82+
To access a linked cluster from your client application, authenticate a user
83+
and pass the cluster name to :js-sdk:`User.mongoClient() <Realm.User.html#mongoClient>`.
84+
This returns a MongoDB service interface that you can use to access databases
85+
and collections in the cluster.
86+
87+
If you are using ``@realm/react``, you can access the MongoDB client
88+
with the ``useUser()`` hook in a component wrapped by the ``UserProvider``.
8689

8790
.. tabs-realm-languages::
88-
91+
8992
.. tab::
9093
:tabid: javascript
91-
92-
.. literalinclude:: /examples/generated/node/mongodb.snippet.plants-collection-handle.js
94+
95+
.. literalinclude:: /examples/generated/react-native/js/mongodb.test.snippet.mongodb.jsx
9396
:language: javascript
94-
97+
9598
.. tab::
9699
:tabid: typescript
97-
98-
.. literalinclude:: /examples/generated/node/mongodb.snippet.plants-collection-handle.ts
100+
101+
.. literalinclude:: /examples/generated/react-native/ts/mongodb.test.snippet.mongodb.tsx
99102
:language: typescript
100103

101104
Read Operations

0 commit comments

Comments
 (0)