Я создаю копию WhatsApp, чтобы иметь возможность узнать больше, и она попадает в неизвестность здесь, а именно:
В реальном WhatsApp, когда мы нажимаем сообщение друга на с правой стороны, он автоматически уже дает нам всю информацию с левой стороны, правильно?
Проблема, которая происходит со мной, состоит в том, что я делаю запрос к бэкэнду, чтобы он изменил свойство isClicked
пользователя и с этим запрос занимает X секунд и, таким образом, генерирует задержку при отображении информации с правой стороны.
Я даже думал о том, чтобы поместить свойство isClicked
в EntityAdapter
, но это не сработает, потому что это было бы «глобальным» без ссылки на конкретного пользователя, но сразу на всех пользователей.
Что я могу сделать, ребята?
ЗАДЕРЖКА
МОЙ РЕДУКТОР
export interface State extends EntityState<IPeople> {
error: IRequestError | null;
loading: boolean;
}
export const adapter: EntityAdapter<IPeople> = createEntityAdapter<IPeople>({
selectId: (people) => people.id,
});
const INIT_STATE: State = adapter.getInitialState({
error: null,
loading: true,
});
const peopleReducer = createReducer(
INIT_STATE,
on(fromPeopleAction.GET_ALL_SUCCESS, fromPeopleAction.CREATE_ALL_SUCCESS, (state, { peoples }) => adapter.addMany(peoples, { ...state, loading: false })),
on(fromPeopleAction.UPDATE_PARTIAL_WITH_CLICK_SUCCESS, (state, { updates }) => adapter.updateMany(updates, { ...state, loading: false })),
on(fromPeopleAction.GET_ALL_FAIL, fromPeopleAction.CREATE_ALL_FAIL, fromPeopleAction.UPDATE_PARTIAL_WITH_CLICK_FAIL, (state, { error }) => ({
...state,
error,
loading: false,
}))
);
export function reducer(state: State | undefined, action: Action) {
return peopleReducer(state, action);
}
МОИ ЭФФЕКТЫ
updatePartialWithClick$: Observable<Action> = createEffect(() =>
this.action$.pipe(
ofType(fromPeopleActions.UPDATE_PARTIAL_WITH_CLICK),
withLatestFrom(this.selectorsService.userFriendClicked),
switchMap(([action, userFriendClicked]) => {
if (action.updates.id !== userFriendClicked.id) {
const peoples: Update<IPeople>[] = [];
const https: Observable<Update<IPeople>>[] = [];
peoples.push(action.updates);
peoples.push({
...userFriendClicked,
changes: {
isClicked: false,
},
});
peoples.forEach((people) => https.push(this.backendService.updatePartial(people)));
return forkJoin(https).pipe(
map(() => fromPeopleActions.UPDATE_PARTIAL_WITH_CLICK_SUCCESS({ updates: peoples })),
catchError((error) => of(fromPeopleActions.UPDATE_PARTIAL_WITH_CLICK_FAIL({ error: this.requestHandlerService.getError(error) })))
);
}
return of(
fromPeopleActions.UPDATE_PARTIAL_WITH_CLICK_FAIL({
error: {
status: 400,
statusText: 'The server cannot process this request.',
url: `${environment.backend.url}/${environment.backend.port}`,
ok: false,
name: 'Bad Request',
message: 'The server cannot process this request, as this item is already selected.',
},
})
);
})
)
);
ЭФФЕКТ МОЕГО ВЫЗОВА
@Component({
selector: 'app-user-talk-controller-container',
template: `
<aside>
<header>
<app-user-container-controller
type="USER_TALK_CONTROLLER_CONTAINER"
[iconList]="iconList"
[username]="user.name"
[avatarSrc]="user.avatar.src"
[avatarAlt]="user.avatar.alt"
></app-user-container-controller>
</header>
<section>
<app-search-container></app-search-container>
</section>
<footer>
<app-user-friend-talk-list (friendClick)="openTalkContainer($event)" [talkList]="talkList"></app-user-friend-talk-list>
</footer>
</aside>
`,
styleUrls: ['./user-talk-controller-container.component.scss'],
})
export class UserTalkControllerContainerComponent implements OnInit {
@Input() user: IPeople;
@Input() talkList: IPeopleTalkList[];
iconList: IconList[] = [{ name: 'status' }, { name: 'chat' }, { name: 'more-options' }];
protected subscriber = new Subscriber<IPeople>();
constructor(protected readonly dispatchService: PeopleDispatchService, protected readonly selectorsService: PeopleSelectorsService) {}
ngOnInit(): void {}
openTalkContainer(friend: IPeople): void {
this.dispatchService.updatePartialWithClick({
id: friend.id,
changes: {
isClicked: true,
},
});
}
}