Meteor.user()
和localStorage.getItem('Meteor.userId')
返回null,直到刷新页面
我正在使用来自Meteor.user()
的值来尝试更改状态,从而重新呈现组件,但它会一直返回null
直到页面重新加载。
export default class Header extends React.Component {
constructor(props){
super(props);
this.state = {loggedIn: Meteor.user() !== null}// false if no user
//is logged in
//save the component context to avoid scope issues
thisComponent = this;
}
onSubmit(e){
e.preventDefault();
let el = $(e.target);
let email = el.find('#email').val();
let password = el.find('#password').val();
let confirmPassword = el.find('#confirmPassword').val();
// Login user
Meteor.loginWithPassword(email, password, err => {
if (err) {
Materialize.toast(err.reason, 4000);
} else {
Materialize.toast('Success loging in', 4000);
//change state just to cause a rerender
thisComponent.setState({ loggedIn: true })
}
});
}
render() {
//if user is logged in
if(Meteor.user()) {
return <Redirect to='/dashboard' />;
} else {
return <LoginComponent />;
}
}
答案 0 :(得分:1)
您需要使用反应式数据源来访问组件中的Meteor.user()对象。最好的方法是包装(整个应用程序)或仅将数据容器中的特定组件包装为将Meteor.user()对象作为道具传递给组件。
使用createContainer
的示例:
import { Meteor } from 'meteor/meteor';
import { createContainer } from 'meteor/react-meteor-data';
import { Header } from '/imports/ui/components/Header';
export default createContainer(() => {
const loading = !Meteor.user();
const user = Meteor.user();
return { loading, user };
}, Header);
然后在标题中:
export default class Header extends React.Component {
constructor(props){
super(props);
this.state = { loggedIn: !!user}
thisComponent = this;
}
onSubmit(e){
e.preventDefault();
let el = $(e.target);
let email = el.find('#email').val();
let password = el.find('#password').val();
let confirmPassword = el.find('#confirmPassword').val();
// Login user
Meteor.loginWithPassword(email, password, err => {
if(err){
Materialize.toast(err.reason, 4000);
}else {
Materialize.toast('Success loging in', 4000);
//change state just to cause a rerender
thisComponent.setState({ loggedIn: true })
}
});
}
render() {
{ !!user ? <Redirect to='/dashboard' /> : <LoginComponent /> }
}
}
答案 1 :(得分:0)
由于异步问题,Meteor.user()返回错误!
(Meteor.userId()只返回一个ID,它比Meteor.user()更快 - 返回一个对象)
因此,您可以使用Komposer来包装您的组件,这也是Meteor / React应用程序中的标准组件(并为页面提供足够的时间来加载Meteor.user()对象并将其作为道具传递到Header组件中):
创建 HeaderComposer 文件:
import React from 'react';
import {composeWithTracker} from 'react-komposer';
// also import your Header here..
function composer(props, onData) {
const user = Meteor.user();
onData(null, {user})
};
export default composeWithTracker(composer)(Header);
并在您的Header文件中:
export default class Header extends React.Component {
constructor(props){
super(props);
this.state = {loggedIn: this.props.user !== null}// false if no user
//is logged in
//save the component context to avoid scope issues
thisComponent = this;
}
onSubmit(e){
e.preventDefault();
let el = $(e.target);
let email = el.find('#email').val();
let password = el.find('#password').val();
let confirmPassword = el.find('#confirmPassword').val();
// Login user
Meteor.loginWithPassword(email, password, err => {
if (err) {
Materialize.toast(err.reason, 4000);
} else {
Materialize.toast('Success loging in', 4000);
//change state just to cause a rerender
thisComponent.setState({ loggedIn: true })
}
});
}
render() {
//if user is logged in
if(this.props.user) {
return <Redirect to='/dashboard' />;
} else {
return <LoginComponent />;
}
}
}
当然,在另一个组件文件中,您可以在其中呈现标题组件,可以随意使用 HeaderComposer