类型“(状态:状态,操作:AuthActionsUnion)=>状态”的参数不可分配

时间:2019-08-23 00:44:56

标签: javascript angular typescript ngrx angular8

我的 main.module.ts 中不断出现以下错误。这是下面的代码:

@NgModule({
  declarations: [
    PressComponent,
    LegalComponent,
    InviteComponent
  ],
  providers: [
    AuthService
  ],
  imports: [
    HomeModule,
    MainRoutingModule,
    ContactModule,
    EffectsModule.forRoot([
      AuthEffects
    ]),
    StoreModule.forRoot(AuthReducer, {
      metaReducers,
      runtimeChecks: {
        strictActionImmutability: true,
        strictStateImmutability: true,
      },
    }),
    SectionHeaderGroupModule,
    FormRegisterModule,
    ReactiveFormsModule
  ]
})

export class MainModule {
}

这是错误:

Error:(34, 25) TS2345: Argument of type '(state: State, action: AuthActionsUnion) => State' is not assignable to parameter of type 'ActionReducerMap<State, Action> | InjectionToken<ActionReducerMap<State, Action>>'.
  Type '(state: State, action: AuthActionsUnion) => State' is not assignable to type 'InjectionToken<ActionReducerMap<State, Action>>'.
    Property '_desc' is missing in type '(state: State, action: AuthActionsUnion) => State'.

这是我的 auth.reducer.ts 文件:

import { IUser } from '../shared/models/user';
import * as AuthActions from './auth.actions';

export interface State {
  user: IUser | null;
  error: any;
}

const initialState: State = {
  user: null,
  error: '',
};

export function AuthReducer(state = initialState, action: AuthActions.AuthActionsUnion): State {
  switch (action.type) {
    case AuthActions.AuthActionsTypes.GetUserDataGoogleSignIn: {
      return {
        ...state,
        user: action.payload,
        error: '',
      };
    }
    case AuthActions.AuthActionsTypes.SignIn: {
      return {
        ...state,
        error: '',
      };
    }
    case AuthActions.AuthActionsTypes.SignUp: {
      return {
        ...state,
        error: '',
      };
    }
    case AuthActions.AuthActionsTypes.GoogleSignIn: {
      return {
        ...state,
        error: '',
      };
    }
    case AuthActions.AuthActionsTypes.MobileGoogleSignIn: {
      return {
        ...state,
        error: '',
      };
    }
    case AuthActions.AuthActionsTypes.FacebookSignIn: {
      return {
        ...state,
        error: '',
      };
    }
    case AuthActions.AuthActionsTypes.MobileFacebookSignIn: {
      return {
        ...state,
        error: '',
      };
    }
    case AuthActions.AuthActionsTypes.SignInFailure: {
      return {
        ...state,
        user: null,
        error: getErrorMessage(action.payload),
      };
    }
    case AuthActions.AuthActionsTypes.SignUpFailure: {
      return {
        ...state,
        user: null,
        error: getErrorMessage(action.payload),
      };
    }
  }
}

function getErrorMessage(error): string {
  switch (error) {
    case 'auth/wrong-password':
      return 'Wrong password';
    case 'auth/user-not-found':
      return 'IUser does not exist';
    case 'auth/invalid-email':
      return 'Invalid email address';
    default:
      return error;
  }
}

我该如何解决?

1 个答案:

答案 0 :(得分:1)

我看到您在ngrx v8和v7的语法之间混淆了,这是我配置代码的方式

在app.module.ts

StoreModule.forRoot(ROOT_REDUCERS, {
  metaReducers,
  runtimeChecks: {
    strictStateImmutability: true,
    strictActionImmutability: true
  }
}),

然后是根减速器

import {
  ActionReducer,
  ActionReducerMap,
  MetaReducer,
  Action
} from "@ngrx/store";
import { environment } from "../../../environments/environment";
import * as fromRouter from "@ngrx/router-store";
import { InjectionToken } from "@angular/core";

/**
 * Every reducer module's default export is the reducer function itself. In
 * addition, each module should export a type or interface that describes
 * the state of the reducer plus any selector functions. The `* as`
 * notation packages up all of the exports into a single object.
 */
/**
 * As mentioned, we treat each reducer like a table in a database. This means
 * our top level state interface is just a map of keys to inner state types.
 */
export interface State {
  router: fromRouter.RouterReducerState<any>;
}

/**
 * Our state is composed of a map of action reducer functions.
 * These reducer functions are called with each dispatched action
 * and the current or initial state and return a new immutable state.
 */
export const ROOT_REDUCERS = new InjectionToken<
  ActionReducerMap<State, Action>
>("Root reducers token", {
  factory: () => ({
    router: fromRouter.routerReducer
  })
});

以及ngrx v8如何编写reducer

import { createReducer, on } from "@ngrx/store";
import {
  EntityState,
  EntityAdapter,
  createEntityAdapter
} from "@ngrx/entity";

import * as PostActions from "../actions/post.actions";

import { IPost } from "../models/post.model";

export interface PostState extends EntityState<IPost> {
  selectedPost: IPost;
  errors: any;
}

const postAdapter: EntityAdapter<IPost> = createEntityAdapter<IPost>();

const initialState: PostState = postAdapter.getInitialState({
  selectedPost: null,
  errors: null
});

export const postReducer = createReducer(
  initialState,
  on(PostActions.LoadPostsSuccess, (state, { posts }) =>
    postAdapter.addAll(posts, state)
  ),
  on(PostActions.LoadPostSuccess, (state, { post }) => {
    return postAdapter.addOne(post, { ...state, selectedPost: post });
  }),
  on(PostActions.UpdatePost, (state, { post }) => {
    return postAdapter.updateOne(post, state);
    //return postAdapter.updateOne(post, { ...state, selectedPost: post });
  }),
  on(PostActions.UpdateSelectedPost, (state, { selectedPost }) => {
    console.log(selectedPost);
    return { ...state, selectedPost };
  }),

  //catch errors
  on(
    PostActions.LoadPostsFail,
    PostActions.LoadPostFail,
    PostActions.UpdatePostFail,
    (state, { errors }) => {
      return { ...state, errors };
    }
  )
);

export const { selectAll } = postAdapter.getSelectors();