mattermost-redux
Version:
Common code (API client, Redux stores, logic, utility functions) for building a Mattermost client
472 lines (471 loc) • 18.6 kB
JavaScript
"use strict";
// Copyright (c) 2015-present Mattermost, Inc. All Rights Reserved.
// See LICENSE.txt for license information.
Object.defineProperty(exports, "__esModule", { value: true });
const redux_1 = require("redux");
const action_types_1 = require("mattermost-redux/action_types");
const team_utils_1 = require("mattermost-redux/utils/team_utils");
function currentTeamId(state = '', action) {
switch (action.type) {
case action_types_1.TeamTypes.SELECT_TEAM:
return action.data;
case action_types_1.UserTypes.LOGOUT_SUCCESS:
return '';
default:
return state;
}
}
function teams(state = {}, action) {
switch (action.type) {
case action_types_1.TeamTypes.RECEIVED_TEAMS_LIST:
case action_types_1.SchemeTypes.RECEIVED_SCHEME_TEAMS:
case action_types_1.AdminTypes.RECEIVED_DATA_RETENTION_CUSTOM_POLICY_TEAMS_SEARCH:
return Object.assign({}, state, (0, team_utils_1.teamListToMap)(action.data));
case action_types_1.AdminTypes.RECEIVED_DATA_RETENTION_CUSTOM_POLICY_TEAMS:
case action_types_1.UserTypes.LOGIN: // Used by the mobile app
return Object.assign({}, state, (0, team_utils_1.teamListToMap)(action.data.teams));
case action_types_1.TeamTypes.RECEIVED_TEAMS:
return Object.assign({}, state, action.data);
case action_types_1.TeamTypes.CREATED_TEAM:
case action_types_1.TeamTypes.UPDATED_TEAM:
case action_types_1.TeamTypes.PATCHED_TEAM:
case action_types_1.TeamTypes.REGENERATED_TEAM_INVITE_ID:
case action_types_1.TeamTypes.RECEIVED_TEAM:
return {
...state,
[action.data.id]: action.data,
};
case action_types_1.TeamTypes.RECEIVED_TEAM_DELETED: {
const nextState = { ...state };
const teamId = action.data.id;
if (Object.hasOwn(nextState, teamId)) {
Reflect.deleteProperty(nextState, teamId);
return nextState;
}
return state;
}
case action_types_1.TeamTypes.RECEIVED_TEAM_UNARCHIVED: {
const team = action.data;
return { ...state, [team.id]: team };
}
case action_types_1.TeamTypes.UPDATED_TEAM_SCHEME: {
const { teamId, schemeId } = action.data;
const team = state[teamId];
if (!team) {
return state;
}
return { ...state, [teamId]: { ...team, scheme_id: schemeId } };
}
case action_types_1.AdminTypes.REMOVE_DATA_RETENTION_CUSTOM_POLICY_TEAMS_SUCCESS: {
const { teams } = action.data;
const nextState = { ...state };
teams.forEach((teamId) => {
if (nextState[teamId]) {
nextState[teamId] = {
...nextState[teamId],
policy_id: null,
};
}
});
return nextState;
}
case action_types_1.UserTypes.LOGOUT_SUCCESS:
return {};
default:
return state;
}
}
function myMembers(state = {}, action) {
function updateState(receivedTeams = {}, currentState = {}) {
return Object.keys(receivedTeams).forEach((teamId) => {
if (receivedTeams[teamId].delete_at > 0 && currentState[teamId]) {
Reflect.deleteProperty(currentState, teamId);
}
});
}
switch (action.type) {
case action_types_1.TeamTypes.RECEIVED_MY_TEAM_MEMBER: {
const nextState = { ...state };
const member = action.data;
if (member.delete_at === 0) {
nextState[member.team_id] = member;
}
return nextState;
}
case action_types_1.TeamTypes.RECEIVED_MY_TEAM_MEMBERS: {
const nextState = {};
const members = action.data;
for (const m of members) {
if (m.delete_at == null || m.delete_at === 0) {
const prevMember = state[m.team_id] || { mention_count: 0, msg_count: 0, mention_count_root: 0, msg_count_root: 0 };
nextState[m.team_id] = {
...prevMember,
...m,
};
}
}
return nextState;
}
case action_types_1.TeamTypes.RECEIVED_TEAMS_LIST: {
const nextState = { ...state };
const receivedTeams = (0, team_utils_1.teamListToMap)(action.data);
updateState(receivedTeams, nextState);
return nextState;
}
case action_types_1.TeamTypes.RECEIVED_TEAMS: {
const nextState = { ...state };
const receivedTeams = action.data;
updateState(receivedTeams, nextState);
return nextState;
}
case action_types_1.TeamTypes.RECEIVED_MY_TEAM_UNREADS: {
const nextState = { ...state };
const unreads = action.data;
for (const u of unreads) {
const msgCount = u.msg_count < 0 ? 0 : u.msg_count;
const mentionCount = u.mention_count < 0 ? 0 : u.mention_count;
const msgCountRoot = u.msg_count_root < 0 ? 0 : u.msg_count_root;
const mentionCountRoot = u.mention_count_root < 0 ? 0 : u.mention_count_root;
const m = {
...state[u.team_id],
mention_count: mentionCount,
msg_count: msgCount,
mention_count_root: mentionCountRoot,
msg_count_root: msgCountRoot,
};
nextState[u.team_id] = m;
}
return nextState;
}
case action_types_1.ChannelTypes.INCREMENT_UNREAD_MSG_COUNT: {
const { teamId, amount, amountRoot, onlyMentions } = action.data;
const member = state[teamId];
if (!member) {
// Don't keep track of unread posts until we've loaded the actual team member
return state;
}
if (onlyMentions) {
// Incrementing the msg_count marks the team as unread, so don't do that if these posts shouldn't be unread
return state;
}
return {
...state,
[teamId]: {
...member,
msg_count: member.msg_count + amount,
msg_count_root: member.msg_count_root + amountRoot,
},
};
}
case action_types_1.ChannelTypes.DECREMENT_UNREAD_MSG_COUNT: {
const { teamId, amount, amountRoot } = action.data;
const member = state[teamId];
if (!member) {
// Don't keep track of unread posts until we've loaded the actual team member
return state;
}
return {
...state,
[teamId]: {
...member,
msg_count: Math.max(member.msg_count - Math.abs(amount), 0),
msg_count_root: Math.max(member.msg_count_root - Math.abs(amountRoot), 0),
},
};
}
case action_types_1.ChannelTypes.INCREMENT_UNREAD_MENTION_COUNT: {
const { teamId, amount, amountRoot } = action.data;
const member = state[teamId];
if (!member) {
// Don't keep track of unread posts until we've loaded the actual team member
return state;
}
return {
...state,
[teamId]: {
...member,
mention_count: member.mention_count + amount,
mention_count_root: member.mention_count_root + amountRoot,
},
};
}
case action_types_1.ChannelTypes.DECREMENT_UNREAD_MENTION_COUNT: {
const { teamId, amount, amountRoot } = action.data;
const member = state[teamId];
if (!member) {
// Don't keep track of unread posts until we've loaded the actual team member
return state;
}
return {
...state,
[teamId]: {
...member,
mention_count: Math.max(member.mention_count - amount, 0),
mention_count_root: Math.max(member.mention_count_root - amountRoot, 0),
},
};
}
case action_types_1.TeamTypes.LEAVE_TEAM:
case action_types_1.TeamTypes.RECEIVED_TEAM_DELETED: {
const nextState = { ...state };
const data = action.data;
Reflect.deleteProperty(nextState, data.id);
return nextState;
}
case action_types_1.TeamTypes.UPDATED_TEAM_MEMBER_SCHEME_ROLES: {
return updateMyTeamMemberSchemeRoles(state, action);
}
case action_types_1.ChannelTypes.POST_UNREAD_SUCCESS: {
const { teamId, deltaMsgs, mentionCount, msgCount } = action.data;
const teamState = state[teamId];
if (!teamState) {
return state;
}
const newTeamState = {
...teamState,
msg_count: (typeof teamState.msg_count === 'undefined' ? msgCount : teamState.msg_count - deltaMsgs),
mention_count: (typeof teamState.mention_count === 'undefined' ? mentionCount : teamState.mention_count + mentionCount),
};
return { ...state, [teamId]: newTeamState };
}
case action_types_1.UserTypes.LOGIN: { // Used by the mobile app
const { teamMembers, teamUnreads } = action.data;
const nextState = { ...state };
for (const m of teamMembers) {
if (m.delete_at == null || m.delete_at === 0) {
const unread = teamUnreads.find((u) => u.team_id === m.team_id);
if (unread) {
m.mention_count = unread.mention_count;
m.msg_count = unread.msg_count;
m.mention_count_root = unread.mention_count_root;
m.msg_count_root = unread.msg_count_root;
}
nextState[m.team_id] = m;
}
}
return nextState;
}
case action_types_1.UserTypes.LOGOUT_SUCCESS:
return {};
default:
return state;
}
}
function membersInTeam(state = {}, action) {
switch (action.type) {
case action_types_1.TeamTypes.RECEIVED_MEMBER_IN_TEAM: {
const data = action.data;
const members = { ...(state[data.team_id] || {}) };
members[data.user_id] = data;
return {
...state,
[data.team_id]: members,
};
}
case action_types_1.TeamTypes.RECEIVED_TEAM_MEMBERS: {
const data = action.data;
if (data && data.length) {
const nextState = { ...state };
for (const member of data) {
if (nextState[member.team_id]) {
nextState[member.team_id] = { ...nextState[member.team_id] };
}
else {
nextState[member.team_id] = {};
}
nextState[member.team_id][member.user_id] = member;
}
return nextState;
}
return state;
}
case action_types_1.TeamTypes.RECEIVED_MEMBERS_IN_TEAM: {
const data = action.data;
if (data && data.length) {
const teamId = data[0].team_id;
const members = { ...(state[teamId] || {}) };
for (const member of data) {
members[member.user_id] = member;
}
return {
...state,
[teamId]: members,
};
}
return state;
}
case action_types_1.TeamTypes.REMOVE_MEMBER_FROM_TEAM: {
const data = action.data;
const members = state[data.team_id];
if (members) {
const nextState = { ...members };
Reflect.deleteProperty(nextState, data.user_id);
return {
...state,
[data.team_id]: nextState,
};
}
return state;
}
case action_types_1.TeamTypes.RECEIVED_TEAM_DELETED: {
const nextState = { ...state };
const teamId = action.data.id;
if (Object.hasOwn(nextState, teamId)) {
Reflect.deleteProperty(nextState, teamId);
return nextState;
}
return state;
}
case action_types_1.TeamTypes.UPDATED_TEAM_MEMBER_SCHEME_ROLES: {
return updateTeamMemberSchemeRoles(state, action);
}
case action_types_1.UserTypes.LOGOUT_SUCCESS:
return {};
default:
return state;
}
}
function stats(state = {}, action) {
switch (action.type) {
case action_types_1.TeamTypes.RECEIVED_TEAM_STATS: {
const stat = action.data;
return {
...state,
[stat.team_id]: stat,
};
}
case action_types_1.TeamTypes.RECEIVED_TEAM_DELETED: {
const nextState = { ...state };
const teamId = action.data.id;
if (Object.hasOwn(nextState, teamId)) {
Reflect.deleteProperty(nextState, teamId);
return nextState;
}
return state;
}
case action_types_1.UserTypes.LOGOUT_SUCCESS:
return {};
default:
return state;
}
}
function groupsAssociatedToTeam(state = {}, action) {
switch (action.type) {
case action_types_1.GroupTypes.RECEIVED_GROUP_ASSOCIATED_TO_TEAM: {
const { teamID, groups } = action.data;
const nextState = { ...state };
const associatedGroupIDs = new Set(state[teamID] ? state[teamID].ids : []);
for (const group of groups) {
associatedGroupIDs.add(group.id);
}
nextState[teamID] = { ids: Array.from(associatedGroupIDs), totalCount: associatedGroupIDs.size };
return nextState;
}
case action_types_1.GroupTypes.RECEIVED_GROUPS_ASSOCIATED_TO_TEAM: {
const { teamID, groups, totalGroupCount } = action.data;
const nextState = { ...state };
const associatedGroupIDs = new Set(state[teamID] ? state[teamID].ids : []);
for (const group of groups) {
associatedGroupIDs.add(group.id);
}
nextState[teamID] = { ids: Array.from(associatedGroupIDs), totalCount: totalGroupCount };
return nextState;
}
case action_types_1.GroupTypes.RECEIVED_ALL_GROUPS_ASSOCIATED_TO_TEAM: {
const { teamID, groups } = action.data;
const nextState = { ...state };
const associatedGroupIDs = new Set([]);
for (const group of groups) {
associatedGroupIDs.add(group.id);
}
const ids = Array.from(associatedGroupIDs);
nextState[teamID] = { ids, totalCount: ids.length };
return nextState;
}
case action_types_1.GroupTypes.RECEIVED_GROUP_NOT_ASSOCIATED_TO_TEAM:
case action_types_1.GroupTypes.RECEIVED_GROUPS_NOT_ASSOCIATED_TO_TEAM: {
const { teamID, groups } = action.data;
const nextState = { ...state };
const associatedGroupIDs = new Set(state[teamID] ? state[teamID].ids : []);
for (const group of groups) {
associatedGroupIDs.delete(group.id);
}
nextState[teamID] = { ids: Array.from(associatedGroupIDs), totalCount: associatedGroupIDs.size };
return nextState;
}
default:
return state;
}
}
function updateTeamMemberSchemeRoles(state, action) {
const { teamId, userId, isSchemeUser, isSchemeAdmin } = action.data;
const team = state[teamId];
if (team) {
const member = team[userId];
if (member) {
return {
...state,
[teamId]: {
...state[teamId],
[userId]: {
...state[teamId][userId],
scheme_user: isSchemeUser,
scheme_admin: isSchemeAdmin,
},
},
};
}
}
return state;
}
function updateMyTeamMemberSchemeRoles(state, action) {
const { teamId, isSchemeUser, isSchemeAdmin } = action.data;
const member = state[teamId];
if (member) {
return {
...state,
[teamId]: {
...state[teamId],
scheme_user: isSchemeUser,
scheme_admin: isSchemeAdmin,
},
};
}
return state;
}
function totalCount(state = 0, action) {
switch (action.type) {
case action_types_1.TeamTypes.RECEIVED_TOTAL_TEAM_COUNT: {
return action.data;
}
default:
return state;
}
}
function contentFlaggingStatus(state = {}, action) {
switch (action.type) {
case action_types_1.TeamTypes.RECEIVED_CONTENT_FLAGGING_STATUS: {
return {
...state,
[action.data.teamId]: action.data.status,
};
}
default:
return state;
}
}
exports.default = (0, redux_1.combineReducers)({
// the current selected team
currentTeamId,
// object where every key is the team id and has and object with the team detail
teams,
// object where every key is the team id and has and object with the team members detail
myMembers,
// object where every key is the team id and has an object of members in the team where the key is user id
membersInTeam,
// object where every key is the team id and has an object with the team stats
stats,
groupsAssociatedToTeam,
totalCount,
contentFlaggingStatus,
});