Skip to content

Commit a18d94b

Browse files
committed
refactor Home page with Messages
1 parent 5d8cdac commit a18d94b

File tree

5 files changed

+268
-235
lines changed

5 files changed

+268
-235
lines changed

src/components/Home/index.js

+16-235
Original file line numberDiff line numberDiff line change
@@ -1,30 +1,15 @@
11
import React, { Component } from 'react';
2+
import { connect } from 'react-redux';
23
import { compose } from 'recompose';
34

4-
import {
5-
AuthUserContext,
6-
withAuthorization,
7-
withEmailVerification,
8-
} from '../Session';
5+
import { withAuthorization, withEmailVerification } from '../Session';
96
import { withFirebase } from '../Firebase';
7+
import Messages from '../Messages';
108

119
class HomePage extends Component {
12-
constructor(props) {
13-
super(props);
14-
15-
this.state = {
16-
loading: false,
17-
users: null,
18-
};
19-
}
20-
2110
componentDidMount() {
22-
this.setState({ loading: true });
2311
this.props.firebase.users().on('value', snapshot => {
24-
this.setState({
25-
users: snapshot.val(),
26-
loading: false,
27-
});
12+
this.props.onSetUsers(snapshot.val());
2813
});
2914
}
3015

@@ -33,239 +18,35 @@ class HomePage extends Component {
3318
}
3419

3520
render() {
36-
const { users, loading } = this.state;
21+
const { users } = this.props;
3722

3823
return (
3924
<div>
4025
<h1>Home Page</h1>
4126
<p>The Home Page is accessible by every signed in user.</p>
4227

43-
<Messages users={users} usersLoading={loading} />
28+
<Messages users={users} />
4429
</div>
4530
);
4631
}
4732
}
4833

49-
class MessagesBase extends Component {
50-
constructor(props) {
51-
super(props);
52-
53-
this.state = {
54-
text: '',
55-
loading: false,
56-
messages: [],
57-
limit: 5,
58-
};
59-
}
60-
61-
componentDidMount() {
62-
this.onListenForMessages();
63-
}
64-
65-
onListenForMessages = () => {
66-
this.setState({ loading: true });
67-
68-
this.props.firebase
69-
.messages()
70-
.orderByChild('createdAt')
71-
.limitToLast(this.state.limit)
72-
.on('value', snapshot => {
73-
const messageObject = snapshot.val();
74-
75-
if (messageObject) {
76-
const messageList = Object.keys(messageObject).map(key => ({
77-
...messageObject[key],
78-
uid: key,
79-
}));
80-
81-
this.setState({
82-
messages: messageList,
83-
loading: false,
84-
});
85-
} else {
86-
this.setState({ messages: null, loading: false });
87-
}
88-
});
89-
};
90-
91-
componentWillUnmount() {
92-
this.props.firebase.messages().off();
93-
}
94-
95-
onChangeText = event => {
96-
this.setState({ text: event.target.value });
97-
};
98-
99-
onCreateMessage = (event, authUser) => {
100-
this.props.firebase.messages().push({
101-
text: this.state.text,
102-
userId: authUser.uid,
103-
createdAt: this.props.firebase.serverValue.TIMESTAMP,
104-
});
105-
106-
this.setState({ text: '' });
107-
108-
event.preventDefault();
109-
};
110-
111-
onEditMessage = (message, text) => {
112-
this.props.firebase.message(message.uid).set({
113-
...message,
114-
text,
115-
editedAt: this.props.firebase.serverValue.TIMESTAMP,
116-
});
117-
};
118-
119-
onRemoveMessage = uid => {
120-
this.props.firebase.message(uid).remove();
121-
};
122-
123-
onNextPage = () => {
124-
this.setState(
125-
state => ({ limit: state.limit + 5 }),
126-
this.onListenForMessages,
127-
);
128-
};
129-
130-
render() {
131-
const { users, usersLoading } = this.props;
132-
const { text, messages, loading } = this.state;
133-
134-
return (
135-
<AuthUserContext.Consumer>
136-
{authUser => (
137-
<div>
138-
{!loading && messages && (
139-
<button type="button" onClick={this.onNextPage}>
140-
More
141-
</button>
142-
)}
143-
144-
{loading && usersLoading && <div>Loading ...</div>}
145-
146-
{users && messages && (
147-
<MessageList
148-
messages={messages.map(message => ({
149-
...message,
150-
user: users[message.userId],
151-
}))}
152-
onEditMessage={this.onEditMessage}
153-
onRemoveMessage={this.onRemoveMessage}
154-
/>
155-
)}
156-
157-
{!messages && <div>There are no messages ...</div>}
158-
159-
<form
160-
onSubmit={event =>
161-
this.onCreateMessage(event, authUser)
162-
}
163-
>
164-
<input
165-
type="text"
166-
value={text}
167-
onChange={this.onChangeText}
168-
/>
169-
<button type="submit">Send</button>
170-
</form>
171-
</div>
172-
)}
173-
</AuthUserContext.Consumer>
174-
);
175-
}
176-
}
177-
178-
const MessageList = ({
179-
messages,
180-
onEditMessage,
181-
onRemoveMessage,
182-
}) => (
183-
<ul>
184-
{messages.map(message => (
185-
<MessageItem
186-
key={message.uid}
187-
message={message}
188-
onEditMessage={onEditMessage}
189-
onRemoveMessage={onRemoveMessage}
190-
/>
191-
))}
192-
</ul>
193-
);
194-
195-
class MessageItem extends Component {
196-
constructor(props) {
197-
super(props);
198-
199-
this.state = {
200-
editMode: false,
201-
editText: this.props.message.text,
202-
};
203-
}
204-
205-
onToggleEditMode = () => {
206-
this.setState(state => ({
207-
editMode: !state.editMode,
208-
editText: this.props.message.text,
209-
}));
210-
};
211-
212-
onChangeEditText = event => {
213-
this.setState({ editText: event.target.value });
214-
};
215-
216-
onSaveEditText = () => {
217-
this.props.onEditMessage(this.props.message, this.state.editText);
218-
219-
this.setState({ editMode: false });
220-
};
221-
222-
render() {
223-
const { message, onRemoveMessage } = this.props;
224-
const { editMode, editText } = this.state;
225-
226-
return (
227-
<li>
228-
{editMode ? (
229-
<input
230-
type="text"
231-
value={editText}
232-
onChange={this.onChangeEditText}
233-
/>
234-
) : (
235-
<span>
236-
<strong>{message.user.username}</strong> {message.text}{' '}
237-
{message.editedAt && <span>(Edited)</span>}
238-
</span>
239-
)}
240-
241-
{editMode ? (
242-
<span>
243-
<button onClick={this.onSaveEditText}>Save</button>
244-
<button onClick={this.onToggleEditMode}>Reset</button>
245-
</span>
246-
) : (
247-
<button onClick={this.onToggleEditMode}>Edit</button>
248-
)}
249-
250-
{!editMode && (
251-
<button
252-
type="button"
253-
onClick={() => onRemoveMessage(message.uid)}
254-
>
255-
Delete
256-
</button>
257-
)}
258-
</li>
259-
);
260-
}
261-
}
34+
const mapStateToProps = state => ({
35+
users: state.userState.users,
36+
});
26237

263-
const Messages = withFirebase(MessagesBase);
38+
const mapDispatchToProps = dispatch => ({
39+
onSetUsers: users => dispatch({ type: 'USERS_SET', users }),
40+
});
26441

26542
const condition = authUser => !!authUser;
26643

26744
export default compose(
26845
withFirebase,
46+
connect(
47+
mapStateToProps,
48+
mapDispatchToProps,
49+
),
26950
withEmailVerification,
27051
withAuthorization(condition),
27152
)(HomePage);
+73
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,73 @@
1+
import React, { Component } from 'react';
2+
3+
class MessageItem extends Component {
4+
constructor(props) {
5+
super(props);
6+
7+
this.state = {
8+
editMode: false,
9+
editText: this.props.message.text,
10+
};
11+
}
12+
13+
onToggleEditMode = () => {
14+
this.setState(state => ({
15+
editMode: !state.editMode,
16+
editText: this.props.message.text,
17+
}));
18+
};
19+
20+
onChangeEditText = event => {
21+
this.setState({ editText: event.target.value });
22+
};
23+
24+
onSaveEditText = () => {
25+
this.props.onEditMessage(this.props.message, this.state.editText);
26+
27+
this.setState({ editMode: false });
28+
};
29+
30+
render() {
31+
const { message, onRemoveMessage } = this.props;
32+
const { editMode, editText } = this.state;
33+
34+
return (
35+
<li>
36+
{editMode ? (
37+
<input
38+
type="text"
39+
value={editText}
40+
onChange={this.onChangeEditText}
41+
/>
42+
) : (
43+
<span>
44+
<strong>
45+
{message.user.username || message.user.userId}
46+
</strong>{' '}
47+
{message.text} {message.editedAt && <span>(Edited)</span>}
48+
</span>
49+
)}
50+
51+
{editMode ? (
52+
<span>
53+
<button onClick={this.onSaveEditText}>Save</button>
54+
<button onClick={this.onToggleEditMode}>Reset</button>
55+
</span>
56+
) : (
57+
<button onClick={this.onToggleEditMode}>Edit</button>
58+
)}
59+
60+
{!editMode && (
61+
<button
62+
type="button"
63+
onClick={() => onRemoveMessage(message.uid)}
64+
>
65+
Delete
66+
</button>
67+
)}
68+
</li>
69+
);
70+
}
71+
}
72+
73+
export default MessageItem;
+22
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
import React from 'react';
2+
3+
import MessageItem from './MessageItem';
4+
5+
const MessageList = ({
6+
messages,
7+
onEditMessage,
8+
onRemoveMessage,
9+
}) => (
10+
<ul>
11+
{messages.map(message => (
12+
<MessageItem
13+
key={message.uid}
14+
message={message}
15+
onEditMessage={onEditMessage}
16+
onRemoveMessage={onRemoveMessage}
17+
/>
18+
))}
19+
</ul>
20+
);
21+
22+
export default MessageList;

0 commit comments

Comments
 (0)