IA update: Update configuration to settings

This is the fourth update to information architecture changes and has
the following changes:

- The configuration section is updated to settings
- The date and time settings page is updated to date and time
- The network settings page is updated to network
- The power restore policy page in operations section is moved to
settings section

Signed-off-by: Sandeepa Singh <sandeepa.singh@ibm.com>
Change-Id: I6f5ab25f5227530be430bd39a4d9629b3bf09d8b
diff --git a/src/store/modules/Settings/DateTimeStore.js b/src/store/modules/Settings/DateTimeStore.js
new file mode 100644
index 0000000..51b722a
--- /dev/null
+++ b/src/store/modules/Settings/DateTimeStore.js
@@ -0,0 +1,81 @@
+import api from '@/store/api';
+import i18n from '@/i18n';
+
+const DateTimeStore = {
+  namespaced: true,
+  state: {
+    ntpServers: [],
+    isNtpProtocolEnabled: null,
+  },
+  getters: {
+    ntpServers: (state) => state.ntpServers,
+    isNtpProtocolEnabled: (state) => state.isNtpProtocolEnabled,
+  },
+  mutations: {
+    setNtpServers: (state, ntpServers) => (state.ntpServers = ntpServers),
+    setIsNtpProtocolEnabled: (state, isNtpProtocolEnabled) =>
+      (state.isNtpProtocolEnabled = isNtpProtocolEnabled),
+  },
+  actions: {
+    async getNtpData({ commit }) {
+      return await api
+        .get('/redfish/v1/Managers/bmc/NetworkProtocol')
+        .then((response) => {
+          const ntpServers = response.data.NTP.NTPServers;
+          const isNtpProtocolEnabled = response.data.NTP.ProtocolEnabled;
+          commit('setNtpServers', ntpServers);
+          commit('setIsNtpProtocolEnabled', isNtpProtocolEnabled);
+        })
+        .catch((error) => {
+          console.log(error);
+        });
+    },
+    async updateDateTime({ state }, dateTimeForm) {
+      const ntpData = {
+        NTP: {
+          ProtocolEnabled: dateTimeForm.ntpProtocolEnabled,
+        },
+      };
+      if (dateTimeForm.ntpProtocolEnabled) {
+        ntpData.NTP.NTPServers = dateTimeForm.ntpServersArray;
+      }
+      return await api
+        .patch(`/redfish/v1/Managers/bmc/NetworkProtocol`, ntpData)
+        .then(async () => {
+          if (!dateTimeForm.ntpProtocolEnabled) {
+            const dateTimeData = {
+              DateTime: dateTimeForm.updatedDateTime,
+            };
+            /**
+             * https://github.com/openbmc/phosphor-time-manager/blob/master/README.md#special-note-on-changing-ntp-setting
+             * When time mode is initially set to Manual from NTP,
+             * NTP service is disabled and the NTP service is
+             * stopping but not stopped, setting time will return an error.
+             * There are no responses from backend to notify when NTP is stopped.
+             * To work around, a timeout is set to allow NTP to fully stop
+             * TODO: remove timeout if backend solves
+             * https://github.com/openbmc/openbmc/issues/3459
+             */
+            const timeoutVal = state.isNtpProtocolEnabled ? 20000 : 0;
+            return await new Promise((resolve, reject) => {
+              setTimeout(() => {
+                return api
+                  .patch(`/redfish/v1/Managers/bmc`, dateTimeData)
+                  .then(() => resolve())
+                  .catch(() => reject());
+              }, timeoutVal);
+            });
+          }
+        })
+        .then(() => {
+          return i18n.t('pageDateTime.toast.successSaveDateTime');
+        })
+        .catch((error) => {
+          console.log(error);
+          throw new Error(i18n.t('pageDateTime.toast.errorSaveDateTime'));
+        });
+    },
+  },
+};
+
+export default DateTimeStore;
diff --git a/src/store/modules/Settings/NetworkStore.js b/src/store/modules/Settings/NetworkStore.js
new file mode 100644
index 0000000..4040658
--- /dev/null
+++ b/src/store/modules/Settings/NetworkStore.js
@@ -0,0 +1,113 @@
+import api from '@/store/api';
+import i18n from '@/i18n';
+import { find, remove } from 'lodash';
+
+const NetworkStore = {
+  namespaced: true,
+  state: {
+    defaultGateway: '',
+    ethernetData: [],
+    interfaceOptions: [],
+  },
+  getters: {
+    defaultGateway: (state) => state.defaultGateway,
+    ethernetData: (state) => state.ethernetData,
+    interfaceOptions: (state) => state.interfaceOptions,
+  },
+  mutations: {
+    setDefaultGateway: (state, defaultGateway) =>
+      (state.defaultGateway = defaultGateway),
+    setEthernetData: (state, ethernetData) =>
+      (state.ethernetData = ethernetData),
+    setInterfaceOptions: (state, interfaceOptions) =>
+      (state.interfaceOptions = interfaceOptions),
+  },
+  actions: {
+    async getEthernetData({ commit }) {
+      return await api
+        .get('/redfish/v1/Managers/bmc/EthernetInterfaces')
+        .then((response) =>
+          response.data.Members.map(
+            (ethernetInterface) => ethernetInterface['@odata.id']
+          )
+        )
+        .then((ethernetInterfaceIds) =>
+          api.all(
+            ethernetInterfaceIds.map((ethernetInterface) =>
+              api.get(ethernetInterface)
+            )
+          )
+        )
+        .then((ethernetInterfaces) => {
+          const ethernetData = ethernetInterfaces.map(
+            (ethernetInterface) => ethernetInterface.data
+          );
+          const interfaceOptions = ethernetInterfaces.map(
+            (ethernetName) => ethernetName.data.Id
+          );
+          const addresses = ethernetData[0].IPv4StaticAddresses;
+
+          // Default gateway manually set to first gateway saved on the first interface. Default gateway property is WIP on backend
+          const defaultGateway = addresses.map((ipv4) => {
+            return ipv4.Gateway;
+          });
+
+          commit('setDefaultGateway', defaultGateway[0]);
+          commit('setEthernetData', ethernetData);
+          commit('setInterfaceOptions', interfaceOptions);
+        })
+        .catch((error) => {
+          console.log('Network Data:', error);
+        });
+    },
+
+    async updateInterfaceSettings({ dispatch, state }, networkSettingsForm) {
+      const updatedAddresses = networkSettingsForm.staticIpv4;
+      const originalAddresses =
+        state.ethernetData[networkSettingsForm.selectedInterfaceIndex]
+          .IPv4StaticAddresses;
+
+      const addressArray = originalAddresses.map((item) => {
+        const address = item.Address;
+        if (find(updatedAddresses, { Address: address })) {
+          remove(updatedAddresses, (item) => {
+            return item.Address === address;
+          });
+          return {};
+        } else {
+          return null;
+        }
+      });
+
+      const data = {
+        HostName: networkSettingsForm.hostname,
+        MACAddress: networkSettingsForm.macAddress,
+        DHCPv4: {
+          DHCPEnabled: networkSettingsForm.isDhcpEnabled,
+        },
+      };
+
+      // If DHCP disabled, update static DNS or static ipv4
+      if (!networkSettingsForm.isDhcpEnabled) {
+        data.IPv4StaticAddresses = [...addressArray, ...updatedAddresses];
+        data.StaticNameServers = networkSettingsForm.staticNameServers;
+      }
+
+      return await api
+        .patch(
+          `/redfish/v1/Managers/bmc/EthernetInterfaces/${networkSettingsForm.interfaceId}`,
+          data
+        )
+        .then(() => dispatch('getEthernetData'))
+        .then(() => {
+          return i18n.t('pageNetwork.toast.successSaveNetworkSettings');
+        })
+        .catch((error) => {
+          console.log(error);
+          throw new Error(i18n.t('pageNetwork.toast.errorSaveNetworkSettings'));
+        });
+    },
+  },
+};
+
+export default NetworkStore;
diff --git a/src/store/modules/Settings/PowerPolicyStore.js b/src/store/modules/Settings/PowerPolicyStore.js
new file mode 100644
index 0000000..4e76cdf
--- /dev/null
+++ b/src/store/modules/Settings/PowerPolicyStore.js
@@ -0,0 +1,72 @@
+import api from '@/store/api';
+import i18n from '@/i18n';
+
+const PowerControlStore = {
+  namespaced: true,
+  state: {
+    powerRestoreCurrentPolicy: null,
+    powerRestorePolicies: [],
+  },
+  getters: {
+    powerRestoreCurrentPolicy: (state) => state.powerRestoreCurrentPolicy,
+    powerRestorePolicies: (state) => state.powerRestorePolicies,
+  },
+  mutations: {
+    setPowerRestoreCurrentPolicy: (state, powerRestoreCurrentPolicy) =>
+      (state.powerRestoreCurrentPolicy = powerRestoreCurrentPolicy),
+    setPowerRestorePolicies: (state, powerRestorePolicies) =>
+      (state.powerRestorePolicies = powerRestorePolicies),
+  },
+  actions: {
+    async getPowerRestorePolicies({ commit }) {
+      return await api
+        .get('/redfish/v1/JsonSchemas/ComputerSystem/ComputerSystem.json')
+        .then(
+          ({
+            data: {
+              definitions: { PowerRestorePolicyTypes = {} },
+            },
+          }) => {
+            let powerPoliciesData = PowerRestorePolicyTypes.enum.map(
+              (powerState) => {
+                let desc = `${i18n.t(
+                  `pagePowerRestorePolicy.policies.${powerState}`
+                )} - ${PowerRestorePolicyTypes.enumDescriptions[powerState]}`;
+                return {
+                  state: powerState,
+                  desc,
+                };
+              }
+            );
+            commit('setPowerRestorePolicies', powerPoliciesData);
+          }
+        );
+    },
+    async getPowerRestoreCurrentPolicy({ commit }) {
+      api
+        .get('/redfish/v1/Systems/system')
+        .then(({ data: { PowerRestorePolicy } }) => {
+          commit('setPowerRestoreCurrentPolicy', PowerRestorePolicy);
+        })
+        .catch((error) => console.log(error));
+    },
+    async setPowerRestorePolicy({ commit }, powerPolicy) {
+      const data = { PowerRestorePolicy: powerPolicy };
+
+      return await api
+        .patch('/redfish/v1/Systems/system', data)
+        .then(() =>
+          commit('setPowerRestoreCurrentPolicy', data.PowerRestorePolicy)
+        )
+        .then(() => i18n.t('pagePowerRestorePolicy.toast.successSaveSettings'))
+        .catch((error) => {
+          console.log(error);
+          throw new Error(
+            i18n.t('pagePowerRestorePolicy.toast.errorSaveSettings')
+          );
+        });
+    },
+  },
+};
+
+export default PowerControlStore;
diff --git a/src/store/modules/Settings/SecuritySettingsStore.js b/src/store/modules/Settings/SecuritySettingsStore.js
new file mode 100644
index 0000000..5a88542
--- /dev/null
+++ b/src/store/modules/Settings/SecuritySettingsStore.js
@@ -0,0 +1,95 @@
+import api from '@/store/api';
+import i18n from '@/i18n';
+
+const SecuritySettingsStore = {
+  namespaced: true,
+  state: {
+    sshProtocolEnabled: false,
+    ipmiProtocolEnabled: false,
+  },
+  getters: {
+    sshProtocolEnabled: (state) => state.sshProtocolEnabled,
+    ipmiProtocolEnabled: (state) => state.ipmiProtocolEnabled,
+  },
+  mutations: {
+    setSshProtocolEnabled: (state, sshProtocolEnabled) =>
+      (state.sshProtocolEnabled = sshProtocolEnabled),
+    setIpmiProtocolEnabled: (state, ipmiProtocolEnabled) =>
+      (state.ipmiProtocolEnabled = ipmiProtocolEnabled),
+  },
+  actions: {
+    async getNetworkProtocolStatus({ commit }) {
+      return await api
+        .get('/redfish/v1/Managers/bmc/NetworkProtocol')
+        .then((response) => {
+          const sshProtocol = response.data.SSH.ProtocolEnabled;
+          const ipmiProtocol = response.data.IPMI.ProtocolEnabled;
+          commit('setSshProtocolEnabled', sshProtocol);
+          commit('setIpmiProtocolEnabled', ipmiProtocol);
+        })
+        .catch((error) => console.log(error));
+    },
+    async saveIpmiProtocolState({ commit }, protocolEnabled) {
+      commit('setIpmiProtocolEnabled', protocolEnabled);
+      const ipmi = {
+        IPMI: {
+          ProtocolEnabled: protocolEnabled,
+        },
+      };
+      return await api
+        .patch('/redfish/v1/Managers/bmc/NetworkProtocol', ipmi)
+        .then(() => {
+          if (protocolEnabled) {
+            return i18n.t('pageSecuritySettings.toast.successIpmiEnabled');
+          } else {
+            return i18n.t('pageSecuritySettings.toast.successIpmiDisabled');
+          }
+        })
+        .catch((error) => {
+          console.log(error);
+          commit('setIpmiProtocolEnabled', !protocolEnabled);
+          if (protocolEnabled) {
+            throw new Error(
+              i18n.t('pageSecuritySettings.toast.errorIpmiEnabled')
+            );
+          } else {
+            throw new Error(
+              i18n.t('pageSecuritySettings.toast.errorIpmiDisabled')
+            );
+          }
+        });
+    },
+    async saveSshProtocolState({ commit }, protocolEnabled) {
+      commit('setSshProtocolEnabled', protocolEnabled);
+      const ssh = {
+        SSH: {
+          ProtocolEnabled: protocolEnabled,
+        },
+      };
+      return await api
+        .patch('/redfish/v1/Managers/bmc/NetworkProtocol', ssh)
+        .then(() => {
+          if (protocolEnabled) {
+            return i18n.t('pageSecuritySettings.toast.successSshEnabled');
+          } else {
+            return i18n.t('pageSecuritySettings.toast.successSshDisabled');
+          }
+        })
+        .catch((error) => {
+          console.log(error);
+          commit('setSshProtocolEnabled', !protocolEnabled);
+          if (protocolEnabled) {
+            throw new Error(
+              i18n.t('pageSecuritySettings.toast.errorSshEnabled')
+            );
+          } else {
+            throw new Error(
+              i18n.t('pageSecuritySettings.toast.errorSshDisabled')
+            );
+          }
+        });
+    },
+  },
+};
+
+export default SecuritySettingsStore;