Why does this return two sets of data? - node.js

I have built my firs full stack app that uses a react front end to communicate with a graphql server and surface data up from a mongoDB. When I look at the app from front end it looks like I am making two calls and return two sets of data (actually the same set twice).
Here is what I see in the dev tools console...
It looks to me like the first two are calls out and the last two are the data returns. If you look on the right, those are all to do with line 17 of BookList.js which is this...
console.log(this.props);
and this is the full code of that file....
import React, { Component } from 'react';
import { gql } from 'apollo-boost';
import { graphql } from 'react-apollo';
const getBooksQuery = gql`
{
books {
name
id
}
}
`;
class BookList extends Component {
render(){
console.log(this.props);
return(
<div>
<ul id="book-list">
<li>Book name</li>
</ul>
</div>
);
}
}
export default graphql(getBooksQuery)(BookList);
I am calling that BookList component with this code...
// components
import BookList from './components/BookList';
// apollo client setup
const client = new ApolloClient({
uri: 'http://localhost:5000/graphql'
});
class App extends Component {
render() {
return (
<ApolloProvider client={client}>
<div id="main">
<h1>Ninja's Reading List</h1>
<BookList />
</div>
</ApolloProvider>
);
}
}
export default App;
I am unsure why I am getting dbl calls or if that is the expectation. Any guidance at all is appreciated.

Related

reaching data inside an object while using map

I'm sorry in advance for my ignorance, But its been a while since I coded, and I need a little help with this basic thing, Im trying to reach name, and display it on screen when I click a button, but i just can't figure it out, can u help me and explain what you did so I can know for the next time? looked manuals and articles about how to do it but you guys are just simply better.
my code:
functional (pokeAPI.ts):
import React from "react";
import axios from 'axios'
export const getPokemon=()=>{
axios.get("https://pokeapi.co/api/v2/pokemon?limit=151").then((response)=>{
response.data.results.map((cont : string,index : number) => console.log(
cont
));
})
}
app.tsx:
import './App.css';
import React from 'react';
import {getPokemon} from './func/pokeAPI';
function App() {
return (
<div>
<button onClick={getPokemon}>Cli</button>
</div>
);
}
export default App;
Here you go! Since you're using typescript, I created a PokemonData interface as well.
import React from 'react'
import axios from 'axios'
import "./styles.css";
interface PokemonData {
name: string
url: string
}
export default function App() {
const [pokemons, setPokemons] = React.useState<null|PokemonData[]>(null)
const onClick = async () => {
axios.get("https://pokeapi.co/api/v2/pokemon?limit=151").then((response)=>{
console.log(response.data.results)
setPokemons(response.data.results)
})
}
return (
<div className="App">
<button onClick={onClick}>Get pokemon</button>
{pokemons?.map((pokemon) => (
<div key={pokemon.name}>
<p>{pokemon.name}</p>
<p>{pokemon.url}</p>
</div>
))}
</div>
);
}
I also wrote a Codesandbox here so you can check it out
Edit: Another version of the return statement if optional chaining isn't supported on your project's version
return (
<div className="App">
<button onClick={onClick}>Get pokemon</button>
{pokemons && pokemons.map((pokemon) => (
<div key={pokemon.name}>
<p>{pokemon.name}</p>
<p>{pokemon.url}</p>
</div>
))}
</div>
);
}

Can you use templates in Next.js?

I am fairly new to web development and currently have a rudimentary web server using Node.js, Express, and Pug which I am hoping to convert to Next.js. Is it possible to create re-usable templates (similar to Pug/Jade) in Next.js?
This is how I do mine. There are better ways, but it's how I like it. I came from express handlebars, and have used pug before, so this is how I did mine.
In pages/_app.js file:
import React from 'react'
import Head from 'next/head'
export default function MyApp({ Component, pageProps }) {
const Layout = Component.Layout || LayoutEmpty // if page has no layout, it uses blank layout
const PageTitle = Component.PageTitle // page title of the page
return (
<Layout>
{PageTitle? (<Head><title>{PageTitle}</title></Head>) : '' }
<Component {...pageProps} />
</Layout>
)
}
const LayoutEmpty = ({children}) => <>{children}</> // blank layout if doesnt detect any layout
In your component folder where ever you want to put your layout file: eg component/layout.js
import Link from 'next/link';
import {useRouter} from 'next/router'
export function LayoutOne({children}) {
try {
return (<>
<nav>
<ul>
<li><Link href="/"><a>Home</a></Link></li>
</ul>
</nav>
<div>{children}</div>
</>)
} catch(e) {console.log(e)}
}
Then in your pages: eg pages/about.js
import React, { useState, useEffect } from 'react';
import {LayoutOne} from '../component/layout' // location of your layout.js file
Aboutpage.PageTitle = 'About | Website Tag Line' // set title of your page
Aboutpage.Layout = LayoutOne // using LayoutOne. If you dont do this, its considered blank layout and you'll get no layout
export default function Aboutpage() {
try {
return (
<>
<div>
<h2>About</h2>
</div>
</>
);
} catch(e) {console.log(e)}
}
If you want more layout, in your layout.js file at the end, just change the name of the export function eg: LayoutTwo
export function LayoutTwo({children}) {
try {
return (<>
<nav>
<ul>
<li><Link href="/dashboard"><a>Dashboard</a></Link></li>
</ul>
</nav>
<div>{children}</div>
</>)
} catch(e) {console.log(e)}
}
And one the page, you change layout to two
import {LayoutTwo} from '../component/layout'
Aboutpage.Layout = LayoutTwo

How can I rerender an array of components in react?

I'm traing to make an experiment in react and websockets. The web app sends an input from the user to a server and the server responds. For each response from the server the web creates a component to show the response. I don't know how to rerender the array after each response.
import React, { useState, Component } from 'react'
import './HomePage2.css'
import Text from '../../commons/Text/Text'
import Input from '../../commons/Input/Input'
import TextInput from '../../commons/TextInput/TextInput'
const ws = new WebSocket('ws://localhost:5656')
var path = 'path$ '
var items = []
const hc = () =>{
this.forceUpdate()
}
ws.addEventListener("message", data => {
console.log(data.data)
items.push(<TextInput path={path} text={data.data} />)
//items.push(data.data)
if(data.data !== ''){
items.push(<Text text={data.data} />)
}
})
class HomePage2 extends Component {
render(){
function setCommand(comm){
ws.send(comm)
}
return(
<div className='homepage2' >
{items}
<Input path={path} callback={setCommand} />
</div>
)
}
}
export default HomePage2
save received data in an array and use the map method to render an element for each value in the array, e.g:
return (
<>
{items.map((item, key) => (
<TextInput path={path} text={item.data} key={key} />
))}
</>
);

View collections item in Mern

I have some items in a mongodb collection, now i want to view them on a react app, i've that code, but it doesn't display nothing, but if i check value with a console.log() i get the content. How i can do?
import axios from "axios";
const viewMails = []
axios.get('http://localhost:5000/emails').then(res => {
let emailString = JSON.parse(res.request.response)
for (const [index, value] of Array(emailString).entries()) {
viewMails.push(
<div key={index}>
<h1>{value.name}</h1>
<h3>{value.email}</h3>
<p>{value.message}</p>
<p>{value.createdAt}</p>
</div>
);
}
});
export default class EmailsViewer extends Component {
render() {
return (
<div className="emails">
<h1>Sos</h1>
{viewMails}
</div>
);
}
}```
Since you are trying to do a simple component to show a list, if you're using one of the last version of React, consider using axios hook (check the package documentation to see how to add it to your project https://www.npmjs.com/package/axios-hook)
Here I show you an example of what you need to do: list demo

props can not be resolved in the render of a React class

I am getting started on webdevelopment with React and Node.js, all are new to me so I am following this tutorial: https://reactjs.org/tutorial/tutorial.html. I am using Visual Studio as IDE.
Everything seems to go as expected until I try to pass data through props. At that point "props" becomes flagged with an error "Cannot resolve symbol 'props'. I have googled myself silly trying to find a solution.
So far I have tried:
import React instead of declaring it as variable. Gives another error: Symbol 'React' cannot be properly resolved, probably it is located in inaccessible module
create a constructor. Gives another error: Call target does not contain any signatures.
Installed npm package for prop-types
I have posted my question to the relevant discord
So at this point I turn to you all, can you help me get going? See my code below:
declare var require: any;
var React = require('react');
var ReactDOM = require('react-dom');
//import * as React from "react";
//import * as ReactDOM from "react-dom";
//node_modules\.bin\webpack app.tsx --config webpack-config.js
class Square extends React.Component<any, any> {
//constructor() {
// super();
//}
render() {
return (
<button className="square">
{this.props.value}
</button>
);
}
}
class Board extends React.Component {
renderSquare(i) {
return <Square value={i}/>;
}
render() {
const status = 'Next player: X';
return (
<div>
<div className="status">{status}</div>
<div className="board-row">
{this.renderSquare(0)}
{this.renderSquare(1)}
{this.renderSquare(2)}
</div>
<div className="board-row">
{this.renderSquare(3)}
{this.renderSquare(4)}
{this.renderSquare(5)}
</div>
<div className="board-row">
{this.renderSquare(6)}
{this.renderSquare(7)}
{this.renderSquare(8)}
</div>
</div>
);
}
}
class Game extends React.Component {
render() {
return (
<div className="game">
<div className="game-board">
<Board />
</div>
<div className="game-info">
<div>{/* status */}</div>
<ol>{/* TODO */}</ol>
</div>
</div>
);
}
}
// ========================================
ReactDOM.render(
<Game />,
document.getElementById('root')
);

Resources