In my project I have many users and many resources (and many user_resources/the join between users and resources).When I POST to user_resources I see it work on my rails backend (as in I see that instance posted) but in my react native front end I don't see it listed upon update. However, once the app is completely refresh (when I stop and restart the expo server), I finally see those items rendered. ANY IDEAS? I've been working on this forever now to no avail and my project is due tmrw, so any help is appreciated.
screen where I post to user_resources:
import React from 'react';
import { ScrollView,SafeAreaView,StyleSheet, Text, View, FlatList, TouchableOpacity,Button, NativeEventEmitter} from 'react-native';
import {connect} from 'react-redux';
import {fetchResources,searchChanged} from '../actions';
import { addUserResource } from '../actions'
import {SearchBar} from 'react-native-elements';
import { MaterialIcons } from '@expo/vector-icons';
import { MaterialCommunityIcons } from '@expo/vector-icons';
class ResourcesScreen extends React.Component {
state = {
search: ''
}
componentDidMount = () =>{
this.props.fetchResources();
}
FlatListItemSeparator = () => {
return (
<View
style={{
height: 0.5,
width: "100%",
backgroundColor: "lightblue",
}}
/>
);
}
handlePress(item) {
debugger
fetch('http://localhost:3000/user_resources', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
Accept: 'application/json'
},
body: JSON.stringify({
resource_id: item.id,
user_id: this.props.users.id,
name: item.name,
description:item.description,
link:item.link,
})
})
.then(res => res.json())
.then(data2 => {
console.log(data2)
this.props.addUserResource(data2)
console.log(this.props)
})
}
header = () => {
return <View>
<Text style={styles.header}>Resources</Text>
</View>
}
onSearchChange = text => {
this.setState({search:text})
}
render(){
return(
<SafeAreaView>
<SearchBar placeholderTextColor="white" placeholder="Enter resource name here" onChangeText={this.onSearchChange} value={this.state.search}/>
<TouchableOpacity onPress={() => this.props.navigation.navigate('Add A New Resource',{topicId:this.props.route.params.topicId})} style={styles.buttonitem}>
<Text style={styles.text}>
<MaterialIcons name="add-circle-outline" size={24} color="white"/>Add A New Resource
</Text>
</TouchableOpacity>
<FlatList keyExtractor={(item)=> item.id.toString()} data={this.props.resourceName} ItemSeparatorComponent = { this.FlatListItemSeparator } renderItem={({item}) => {
return <TouchableOpacity style={styles.material2}>
<Text onPress={() => this.props.navigation.navigate('Add A New Resource',{topicId:item.id})} style={styles.listitem}>{item.name}</Text>
<MaterialCommunityIcons name="bookmark-plus" size={50} color="#16a085" backgroundColor='black' onPress={()=>this.handlePress(item)}/>
</TouchableOpacity>
}}
ListHeaderComponent = {this.header}/>
</SafeAreaView>
)
}
}
const mapStateToProps = (state) => {
return {
resourceName: state.resourceReducer.resources,
users: state.userReducer,
search:state.resourceReducer.searchTerm
}
}
const mapDispatchToProps = (dispatch) => {
return {
fetchResources: () => dispatch(fetchResources()),
addUserResource,
searchChanged
}
}
export default connect(mapStateToProps,mapDispatchToProps)(ResourcesScreen)
After this I head to the profile page where the user_resources SHOULD be displayed, but aren't
import React from 'react';
import { ScrollView,StyleSheet, Text, View, FlatList, TouchableOpacity} from 'react-native';
import {connect} from 'react-redux';
import {SearchBar} from 'react-native-elements';
import { AntDesign } from '@expo/vector-icons';
class Profile extends React.Component{
handleDelete = (id) => {
debugger
fetch(`http://localhost:3000/user_resources/${id}`, {
method: "DELETE",
headers: {
"Authorization": this.props.users.token
}
})
.then(r => r.json())
.then((delResource) => {
console.log(delResource)
this.props.deleteOneFood(delResource)
console.log('deleted')
this.forceUpdate()
})
}
render(){
return(
<View>
{this.props.users.user_resources.map(singleResource=> {
return <Text key={singleResource.id}>{singleResource.name}</Text>
})}
</View>
)}
}
let deleteOneResource = (id) => {
return {
type: "DELETE_ONE_USER_RESOURCE",
payload: id
}
}
const mapDispatchToProps = {
deleteOneResource
}
const mapStateToProps = (state) => {
return {
users: state.userReducer,
}
}
export default connect(mapStateToProps,mapDispatchToProps)(Profile)
I had a flatlist before but thought that may be causing the issues so rendered it another way, still no luck. I tried forceUpdates as well, still no luck. I'm not sure if the issue is coming from my reducer:
let userInitialState = {
id: 0,
username: "",
name: '',
category: '',
token: "",
user_resources:[],
}
let userReducer = (state = userInitialState, action) => {
switch(action.type){
case "ADD_USERS":
let singleNestedObject = {
...action.users.user,
token: action.users.token
}
return {
...state,
username: action.users.user.username,
token: action.users.token,
id: action.users.user.id,
name: action.users.user.name,
category: action.users.user.category,
user_resources: action.users.user.user_resources
}
case "ADD_ONE_USER_RESOURCE":
let copyOfResources = [...state.user_resources, action.userResources]
return {
...state,
user_resources: copyOfResources
}
default:
return state
}
}
and it's action
export const addUserResource = (resourceInfo) => {
return {
type: "ADD_ONE_USER_RESOURCE",
userResources: resourceInfo
}
}
Please help me find the issue here, I'm losing it.