app/addons/replication/reducers.js (346 lines of code) (raw):

// Licensed under the Apache License, Version 2.0 (the "License"); you may not // use this file except in compliance with the License. You may obtain a copy of // the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, WITHOUT // WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the // License for the specific language governing permissions and limitations under // the License. import FauxtonAPI from '../../core/api'; import ActionTypes from './actiontypes'; import Constants from './constants'; import app from "../../app"; const setActivitySort = (sort) => { app.utils.localStorageSet('replication-activity-sort', sort); }; const loadActivitySort = () => { const defaultSort = { descending: false, column: 'statusTime' }; let sort = app.utils.localStorageGet('replication-activity-sort'); if (!sort) { sort = defaultSort; } setActivitySort(sort); return sort; }; const validFieldMap = { remoteSource: 'remoteSource', remoteTarget: 'remoteTarget', localTarget: 'localTarget', replicationType: 'replicationType', replicationDocName: 'replicationDocName', replicationSource: 'replicationSource', replicationTarget: 'replicationTarget', localSource: 'localSource', sourceAuthType: 'sourceAuthType', sourceAuth: 'sourceAuth', targetAuthType: 'targetAuthType', targetAuth: 'targetAuth', targetDatabasePartitioned: 'targetDatabasePartitioned' }; const initialState = { loading: false, databases: [], // source fields replicationSource: '', localSource: '', remoteSource: '', sourceAuthType: Constants.REPLICATION_AUTH_METHOD.NO_AUTH, sourceAuth: {}, // target fields replicationTarget: '', localTarget: '', remoteTarget: '', targetAuthType: Constants.REPLICATION_AUTH_METHOD.NO_AUTH, targetAuth: {}, targetDatabasePartitioned: false, // other isConflictModalVisible: false, replicationType: Constants.REPLICATION_TYPE.ONE_TIME, replicationDocName: '', submittedNoChange: false, statusDocs: [], statusFilteredStatusDocs: [], statusFilter: '', replicateFilter: '', allDocsSelected: false, allReplicateSelected: false, username: '', password: '', activityLoading: false, tabSection: 'new replication', supportNewApi: false, fetchingReplicateInfo: false, replicateInfo: [], checkingAPI: true, activitySort: loadActivitySort(), pageLimit: 100, }; const clearForm = (state) => { const newState = { ...state }; Object.values(validFieldMap).forEach(field => { if (field === 'sourceAuth' || field === 'targetAuth') { newState[field] = {}; } else if (field === 'targetDatabasePartitioned') { newState[field] = false; } else { newState[field] = ''; } }); newState.sourceAuthType = Constants.REPLICATION_AUTH_METHOD.NO_AUTH; newState.targetAuthType = Constants.REPLICATION_AUTH_METHOD.NO_AUTH; return newState; }; const updateFormField = (state, fieldName, value) => { const updateState = { ...state, submittedNoChange: false, }; updateState[validFieldMap[fieldName]] = value; // Set default username when state is set to local target/source AND auth is user/pwd if (fieldName === validFieldMap.sourceAuthType || fieldName === validFieldMap.replicationSource) { const isUserPwdAuth = updateState[validFieldMap.sourceAuthType] === Constants.REPLICATION_AUTH_METHOD.BASIC; const isLocalDB = updateState[validFieldMap.replicationSource] === Constants.REPLICATION_SOURCE.LOCAL; const usernameNotSet = !updateState[validFieldMap.sourceAuth] || !updateState[validFieldMap.sourceAuth].username; if (isUserPwdAuth && isLocalDB && usernameNotSet) { updateState[validFieldMap.sourceAuth] = { username: FauxtonAPI.session.user().name, password: '' }; } } else if (fieldName === validFieldMap.targetAuthType || fieldName === validFieldMap.replicationTarget) { const isUserPwdAuth = updateState[validFieldMap.targetAuthType] === Constants.REPLICATION_AUTH_METHOD.BASIC; const isLocalDB = updateState[validFieldMap.replicationTarget] === Constants.REPLICATION_TARGET.EXISTING_LOCAL_DATABASE || updateState[validFieldMap.replicationTarget] === Constants.REPLICATION_TARGET.NEW_LOCAL_DATABASE; const usernameNotSet = !updateState[validFieldMap.targetAuth] || !updateState[validFieldMap.targetAuth].username; if (isUserPwdAuth && isLocalDB && usernameNotSet) { updateState[validFieldMap.targetAuth] = { username: FauxtonAPI.session.user().name, password: '' }; } } // Set default local source/target database to the first in the list (to match the default dropdown display) if (fieldName === validFieldMap.replicationSource) { const isLocalDB = updateState[validFieldMap.replicationSource] === Constants.REPLICATION_SOURCE.LOCAL; if (isLocalDB && updateState.databases.length > 0) { updateState[validFieldMap.localSource] = updateState.databases[0]; } } if (fieldName === validFieldMap.replicationTarget) { const isLocalDB = updateState[validFieldMap.replicationTarget] === Constants.REPLICATION_TARGET.EXISTING_LOCAL_DATABASE; if (isLocalDB && updateState.databases.length > 0) { updateState[validFieldMap.localTarget] = updateState.databases[0]; } } return updateState; }; const toggleDoc = (state, id) => { const doc = state.statusDocs.find(doc => doc._id === id); if (!doc) { return state; } doc.selected = !doc.selected; return { ...state, allDocsSelected: false }; }; const selectAllDocs = (state) => { const newState = { ...state, allDocsSelected: !state.allDocsSelected }; getFilteredReplicationStatus(newState) .forEach(doc => doc.selected = newState.allDocsSelected); return newState; }; const selectReplicate = (state, id) => { const newState = { ...state }; const doc = newState._replicateInfo.find(doc => doc._id === id); if (!doc) { return newState; } doc.selected = !doc.selected; newState._allReplicateSelected = false; }; const selectAllReplicate = (state) => { const newState = { ...state, allReplicateSelected: !state.allReplicateSelected }; getReplicateInfo(newState).forEach(doc => doc.selected = newState.allReplicateSelected); return newState; }; const setStateFromDoc = (state, doc) => { let newState = { ...state, loading: false }; return Object.keys(doc).reduce((state, key) => { return updateFormField(state, key, doc[key]); }, newState); }; const replication = (state = initialState, {type, options}) => { switch (type) { case ActionTypes.INIT_REPLICATION: const newState = { ...state, loading: true }; if (options.localSource) { newState.localSource = options.localSource; newState.replicationSource = Constants.REPLICATION_SOURCE.LOCAL; newState.remoteSource = ''; newState.replicationTarget = ''; newState.localTarget = ''; newState.remoteTarget = ''; } return newState; case ActionTypes.REPLICATION_DATABASES_LOADED: return { ...state, loading: false, databases: options.databases }; case ActionTypes.REPLICATION_FETCHING_FORM_STATE: return { ...state, loading: true }; case ActionTypes.REPLICATION_UPDATE_FORM_FIELD: return updateFormField(state, options.fieldName, options.value); case ActionTypes.REPLICATION_CLEAR_FORM: return clearForm(state); case ActionTypes.REPLICATION_STARTING: return { ...state, submittedNoChange: true }; case ActionTypes.REPLICATION_FETCHING_STATUS: return { ...state, activityLoading: true }; case ActionTypes.REPLICATION_STATUS: return { ...state, activityLoading: false, statusDocs: options }; case ActionTypes.REPLICATION_FILTER_DOCS: return { ...state, statusFilter: options }; case ActionTypes.REPLICATION_FILTER_REPLICATE: return { ...state, replicateFilter: options }; case ActionTypes.REPLICATION_TOGGLE_DOC: return toggleDoc(state, options); case ActionTypes.REPLICATION_TOGGLE_ALL_DOCS: return selectAllDocs(state); case ActionTypes.REPLICATION_TOGGLE_REPLICATE: return selectReplicate(state, options); case ActionTypes.REPLICATION_TOGGLE_ALL_REPLICATE: return selectAllReplicate(state); case ActionTypes.REPLICATION_SET_STATE_FROM_DOC: return setStateFromDoc(state, options); case ActionTypes.REPLICATION_SHOW_CONFLICT_MODAL: return { ...state, isConflictModalVisible: true }; case ActionTypes.REPLICATION_HIDE_CONFLICT_MODAL: return { ...state, isConflictModalVisible: false }; case ActionTypes.REPLICATION_CHANGE_ACTIVITY_SORT: setActivitySort(options); return { ...state, activitySort: loadActivitySort() }; case ActionTypes.REPLICATION_CLEAR_SELECTED_DOCS: return { ...state, allDocsSelected: false }; case ActionTypes.REPLICATION_CHANGE_TAB_SECTION: return { ...state, tabSection: options }; case ActionTypes.REPLICATION_SUPPORT_NEW_API: return { ...state, checkingApi: false, supportNewApi: options }; case ActionTypes.REPLICATION_FETCHING_REPLICATE_STATUS: return { ...state, fetchingReplicateInfo: true, }; case ActionTypes.REPLICATION_REPLICATE_STATUS: return { ...state, fetchingReplicateInfo: false, replicateInfo: options }; case ActionTypes.REPLICATION_CLEAR_SELECTED_REPLICATES: return { ...state, allReplicateSelected: false }; case ActionTypes.REPLICATION_SET_PAGE_LIMIT: return { ...state, pageLimit: options }; default: return state; } }; export const isLoading = (state) => state.isLoading; export const isActivityLoading = (state) => state.activityLoading; export const getDatabases = (state) => state.databases; export const getReplicationSource = (state) => state.replicationSource; export const getLocalSource = (state) => state.localSource; export const isLocalSourceKnown = (state) => _.includes(state.databases, state.localSource); export const getRemoteSource = (state) => state.remoteSource; export const getReplicationTarget = (state) => state.replicationTarget; export const getLocalTarget = (state) => state.localTarget; export const isLocalTargetKnown = (state) => _.includes(state.databases, state.localTarget); export const getRemoteTarget = (state) => state.remoteTarget; export const isConflictModalVisible = (state) => state.isConflictModalVisible; export const getReplicationType = (state) => state.replicationType; export const getReplicationDocName = (state) => state.replicationDocName; export const getSubmittedNoChange = (state) => state.submittedNoChange; export const getFilteredReplicationStatus = (state) => { return state.statusDocs.filter(doc => { return Object.values(doc).filter(item => { if (!item) {return null;} return item.toString().toLowerCase().match(state.statusFilter); }).length > 0; }); }; export const getStatusFilter = (state) => state.statusFilter; export const getReplicateFilter = (state) => state.replicateFilter; export const getAllDocsSelected = (state) => state.allDocsSelected; export const getSomeDocsSelected = (state) => getFilteredReplicationStatus(state).some(doc => doc.selected); export const getUsername = (state) => state.username; export const getPassword = (state) => state.password; export const getActivitySort = (state) => state.activitySort; export const getTabSection = (state) => state.tabSection; export const getCheckingApi = (state) => state.checkingAPI; export const supportNewApi = (state) => state.supportNewApi; export const isReplicateInfoLoading = (state) => state.fetchingReplicateInfo; export const getAllReplicateSelected = (state) => state.allReplicateSelected; export const someReplicateSelected = (state) => getReplicateInfo(state).some(doc => doc.selected); export const getReplicateInfo = (state) => { return state.replicateInfo.filter(doc => { return Object.values(doc).filter(item => { if (!item) {return false;} return item.toString().toLowerCase().match(state._replicateFilter); }).length > 0; }); }; export const getPageLimit = (state) => state.pageLimit; export default replication;