diff --git a/source/Background/Keyring/index.js b/source/Background/Keyring/index.js
index 79ec8537..d4b2d348 100644
--- a/source/Background/Keyring/index.js
+++ b/source/Background/Keyring/index.js
@@ -109,6 +109,7 @@ export const HANDLER_TYPES = {
GET_CURRENT_NETWORK: 'get-current-network',
IMPORT_PEM_ACCOUNT: 'import-pem-account',
REMOVE_PEM_ACCOUNT: 'remove-pem-account',
+ VALIDATE_PEM: 'validate-pem',
REMOVE_CUSTOM_TOKEN: 'remove-custom-token',
};
@@ -146,6 +147,7 @@ export const getKeyringErrorMessage = (type) => ({
[HANDLER_TYPES.REMOVE_CUSTOM_TOKEN]: 'removing custom token',
[HANDLER_TYPES.IMPORT_PEM_ACCOUNT]: 'importing account from pem',
[HANDLER_TYPES.REMOVE_PEM_ACCOUNT]: 'removing pem account',
+ [HANDLER_TYPES.VALIDATE_PEM]: 'validate pem',
}[type]);
export const sendMessage = (args, callback) => {
@@ -199,6 +201,7 @@ export const getKeyringHandler = (type, keyring) => ({
[HANDLER_TYPES.IMPORT_PEM_ACCOUNT]: async (params) => keyring.importAccountFromPem(params),
[HANDLER_TYPES.CREATE_PRINCIPAL]: async (params) => keyring.createPrincipal(params),
[HANDLER_TYPES.REMOVE_PEM_ACCOUNT]: async (params) => keyring.deleteImportedAccount(params),
+ [HANDLER_TYPES.VALIDATE_PEM]: async (params) => keyring.validatePem(params),
[HANDLER_TYPES.SET_CURRENT_PRINCIPAL]:
async (walletId) => {
await keyring.setCurrentPrincipal(walletId);
diff --git a/source/assets/new-key.svg b/source/assets/new-key.svg
new file mode 100644
index 00000000..151a52f5
--- /dev/null
+++ b/source/assets/new-key.svg
@@ -0,0 +1,9 @@
+
diff --git a/source/assets/paper.svg b/source/assets/paper.svg
new file mode 100644
index 00000000..1dc8a96a
--- /dev/null
+++ b/source/assets/paper.svg
@@ -0,0 +1,9 @@
+
diff --git a/source/locales/en/translation.json b/source/locales/en/translation.json
index 6ffdbca8..f911138a 100644
--- a/source/locales/en/translation.json
+++ b/source/locales/en/translation.json
@@ -396,8 +396,12 @@
"dfxUse": "dfx identity use ",
"selectAccount": "Select Account"
},
+ "importWallet": {
+ "importWallet": "Import Wallet"
+ },
"importPem": {
"importPEMfile": "Import PEM file",
+ "description": "Import wallet through a PEM file",
"editWalletPic": "Edit Wallet Pic",
"walletDetails": "Wallet Details",
"dragAndDrop": "Drag and Drop",
@@ -406,6 +410,12 @@
"fileNotSupported": "File not supported. Try a different file.",
"dropIt": "Drop it!"
},
+ "importPrivateKey": {
+ "importPrivateKey": "Import Private Key",
+ "description": "Import wallet through a Private Key",
+ "privateKey": "Private Key",
+ "invalidString": "Invalid String. Please, try again."
+ },
"nfts": {
"allNfts": "All NFTs",
"expandNFT": "View",
diff --git a/source/views/Extension/Popup.jsx b/source/views/Extension/Popup.jsx
index b35305d9..7d8af582 100644
--- a/source/views/Extension/Popup.jsx
+++ b/source/views/Extension/Popup.jsx
@@ -25,6 +25,8 @@ import ClockError from './Views/ClockError';
import Network from './Views/Network';
import NetworkCreation from './Views/NetworkCreation';
import ImportWallet from './Views/ImportWallet';
+import ImportPemFile from './Views/ImportPemFile';
+import ImportPrivateKey from './Views/ImportPrivateKey';
const Popup = ({ initialRoute }) => (
@@ -38,6 +40,8 @@ const Popup = ({ initialRoute }) => (
{/* */}
+
+
diff --git a/source/views/Extension/Views/ImportWallet/Steps/Step1.jsx b/source/views/Extension/Views/ImportPemFile/Steps/Step1.jsx
similarity index 100%
rename from source/views/Extension/Views/ImportWallet/Steps/Step1.jsx
rename to source/views/Extension/Views/ImportPemFile/Steps/Step1.jsx
diff --git a/source/views/Extension/Views/ImportWallet/Steps/Step2.jsx b/source/views/Extension/Views/ImportPemFile/Steps/Step2.jsx
similarity index 100%
rename from source/views/Extension/Views/ImportWallet/Steps/Step2.jsx
rename to source/views/Extension/Views/ImportPemFile/Steps/Step2.jsx
diff --git a/source/views/Extension/Views/ImportWallet/hooks/useSteps.jsx b/source/views/Extension/Views/ImportPemFile/hooks/useSteps.jsx
similarity index 87%
rename from source/views/Extension/Views/ImportWallet/hooks/useSteps.jsx
rename to source/views/Extension/Views/ImportPemFile/hooks/useSteps.jsx
index 0d204d9b..37eb8c95 100644
--- a/source/views/Extension/Views/ImportWallet/hooks/useSteps.jsx
+++ b/source/views/Extension/Views/ImportPemFile/hooks/useSteps.jsx
@@ -24,9 +24,9 @@ const useSteps = () => {
const steps = [
{
component: ,
- left: leftButton(() => handleClose()),
+ left: leftButton(() => navigator.navigate('import-wallet')),
right: rightButton,
- center: `${t("importPem.importPEMfile")}`,
+ center: `${t("importWallet.importWallet")}`,
},
{
component: {
userPemFile={userPemFile}
/>,
right: rightButton,
- center: `${t("importPem.walletDetails")}`,
+ center: `${t("importWallet.importWallet")}`,
},
];
diff --git a/source/views/Extension/Views/ImportPemFile/index.jsx b/source/views/Extension/Views/ImportPemFile/index.jsx
new file mode 100644
index 00000000..18be5bc5
--- /dev/null
+++ b/source/views/Extension/Views/ImportPemFile/index.jsx
@@ -0,0 +1,21 @@
+import React from 'react';
+import { Layout, Header } from '@components';
+import useSteps from './hooks/useSteps';
+
+const ImportWallet = () => {
+ const {
+ component,
+ left,
+ right,
+ center,
+ } = useSteps();
+
+ return (
+
+
+ {component}
+
+ );
+};
+
+export default ImportWallet;
diff --git a/source/views/Extension/Views/ImportWallet/styles.js b/source/views/Extension/Views/ImportPemFile/styles.js
similarity index 100%
rename from source/views/Extension/Views/ImportWallet/styles.js
rename to source/views/Extension/Views/ImportPemFile/styles.js
diff --git a/source/views/Extension/Views/ImportPrivateKey/Steps/Step1.jsx b/source/views/Extension/Views/ImportPrivateKey/Steps/Step1.jsx
new file mode 100644
index 00000000..74ebd5d4
--- /dev/null
+++ b/source/views/Extension/Views/ImportPrivateKey/Steps/Step1.jsx
@@ -0,0 +1,76 @@
+import React, { useState, useCallback, useEffect } from "react";
+import { useTranslation } from "react-i18next";
+import useStyles from "../styles";
+import { Typography, Grid } from "@material-ui/core";
+import { Container, Button, TextInput, FormItem, UserIcon } from "@components";
+import { HANDLER_TYPES, sendMessage } from "@background/Keyring";
+
+const Step1 = ({ handleChangeStep, setPrivateKey, privateKey }) => {
+ const { t } = useTranslation();
+ const classes = useStyles();
+
+ const [loading, setLoading] = useState(false);
+ const [disabled, setDisabled] = useState(true);
+ const [invalidPem, setInvalidPem] = useState(null);
+
+ const handlePrivateKey = (e) => {
+ setLoading(true);
+ setPrivateKey(e.target.value);
+ sendMessage(
+ {
+ type: HANDLER_TYPES.VALIDATE_PEM,
+ params: {
+ pem: e.target.value
+ },
+ },
+ (a) => {
+ if (a) {
+ setDisabled(false);
+ setInvalidPem(false);
+ setLoading(false);
+ } else {
+ setInvalidPem(true);
+ setLoading(false);
+ setDisabled(true);
+ }
+ },
+ );
+ }
+
+ return (
+
+
+
+ handlePrivateKey(e)}
+ type="text"
+ data-testid="import-private-key-fill"
+ error={invalidPem}
+ />
+ }
+ />
+ {invalidPem && {`${t("importPrivateKey.invalidString")}`}}
+
+
+
+
+
+ );
+};
+
+export default Step1;
diff --git a/source/views/Extension/Views/ImportPrivateKey/Steps/Step2.jsx b/source/views/Extension/Views/ImportPrivateKey/Steps/Step2.jsx
new file mode 100644
index 00000000..755471a1
--- /dev/null
+++ b/source/views/Extension/Views/ImportPrivateKey/Steps/Step2.jsx
@@ -0,0 +1,118 @@
+import { Container, Button, TextInput, FormItem, UserIcon } from "@components";
+import Grid from "@material-ui/core/Grid";
+import useStyles from "../styles";
+import React, { useState } from "react";
+import { useRouter } from "@components/Router";
+import { HANDLER_TYPES, sendMessage } from "@background/Keyring";
+import Picker from "emoji-picker-react";
+import { useEffect } from "react";
+import { useTranslation } from "react-i18next";
+
+const Step2 = ({ privateKey }) => {
+ const { t } = useTranslation();
+
+ const [loading, setLoading] = useState(false);
+ const [disabled, setDisabled] = useState(true);
+ const [openEmojis, setOpenEmojis] = useState(false);
+ const [walletName, setWalletName] = useState(""); // add deafault wallet name, for example the next wallet not used number
+ const [currentEmoji, setCurrentEmoji] = useState("😎"); // add default emoji, not used in other wallets
+ const [openEmojiSelector, setOpenEmojiSelector] = useState(false);
+
+ const { navigator } = useRouter();
+
+ const classes = useStyles();
+
+ useEffect(() => {
+ if (walletName && walletName !== "") {
+ setDisabled(false);
+ } else {
+ setDisabled(true);
+ }
+ }, [currentEmoji, walletName]);
+
+ const onEmojiClick = (_event, emojiObject) => {
+ setCurrentEmoji(emojiObject.emoji);
+ setOpenEmojis(false);
+ setOpenEmojiSelector(false);
+ };
+
+ const createImportedAccount = () => {
+ setLoading(true);
+ sendMessage(
+ {
+ type: HANDLER_TYPES.IMPORT_PEM_ACCOUNT,
+ params: { icon: currentEmoji, name: walletName, pem: privateKey },
+ },
+ () => {},
+ );
+ setLoading(false);
+ navigator.navigate("home");
+ };
+
+
+ return (
+
+
+
+
+
+
+ setWalletName(e.target.value.trim())}
+ type="text"
+ // error={}
+ />
+ }
+ />
+
+
+
+
+ );
+};
+
+export default Step2;
diff --git a/source/views/Extension/Views/ImportPrivateKey/hooks/useSteps.jsx b/source/views/Extension/Views/ImportPrivateKey/hooks/useSteps.jsx
new file mode 100644
index 00000000..229dc018
--- /dev/null
+++ b/source/views/Extension/Views/ImportPrivateKey/hooks/useSteps.jsx
@@ -0,0 +1,44 @@
+import React, { useState } from 'react';
+import { LinkButton } from '@components';
+import { useTranslation } from 'react-i18next';
+import { useRouter } from '@components/Router';
+import BackIcon from '@assets/icons/back.svg';
+import Step1 from '../Steps/Step1';
+import Step2 from '../Steps/Step2';
+
+const useSteps = () => {
+ const [step, setStep] = useState(0);
+ const { navigator } = useRouter();
+ const { t } = useTranslation();
+
+ const [privateKey, setPrivateKey] = useState(null);
+
+ const handleChangeStep = (index) => setStep(index);
+ const handleClose = () => navigator.navigate('home');
+
+ const leftButton = (onClick) => ;
+ const rightButton = ;
+
+
+
+ const steps = [
+ {
+ component: ,
+ left: leftButton(() => navigator.navigate('import-wallet')),
+ right: rightButton,
+ center: `${t("importWallet.importWallet")}`,
+ },
+ {
+ component: ,
+ right: rightButton,
+ center: `${t("importWallet.importWallet")}`,
+ },
+ ];
+
+ return steps[step];
+};
+
+export default useSteps;
diff --git a/source/views/Extension/Views/ImportPrivateKey/index.jsx b/source/views/Extension/Views/ImportPrivateKey/index.jsx
new file mode 100644
index 00000000..c3db2c11
--- /dev/null
+++ b/source/views/Extension/Views/ImportPrivateKey/index.jsx
@@ -0,0 +1,21 @@
+import React from 'react';
+import { Layout, Header } from '@components';
+import useSteps from './hooks/useSteps';
+
+const ImportPrivateKey = () => {
+ const {
+ component,
+ left,
+ right,
+ center,
+ } = useSteps();
+
+ return (
+
+
+ {component}
+
+ );
+};
+
+export default ImportPrivateKey;
diff --git a/source/views/Extension/Views/ImportPrivateKey/styles.js b/source/views/Extension/Views/ImportPrivateKey/styles.js
new file mode 100644
index 00000000..9d272b9c
--- /dev/null
+++ b/source/views/Extension/Views/ImportPrivateKey/styles.js
@@ -0,0 +1,114 @@
+import { makeStyles } from '@material-ui/core/styles';
+
+export default makeStyles((theme) => ({
+ dragDropContainer: {
+ border: '2px dashed #D1D5DB',
+ boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.05)',
+ height: '142px',
+ width: '370px',
+ borderRadius: 6,
+ marginBottom: 20,
+ display: 'flex',
+ justifyContent: 'center',
+ alignItems: 'center',
+ flexDirection: 'column',
+ },
+ dragDropContainerError: {
+ border: '2px dashed #E53C3C',
+ boxShadow: '0px 1px 2px rgba(0, 0, 0, 0.05)',
+ height: '142px',
+ width: '370px',
+ borderRadius: 6,
+ marginBottom: 40,
+ },
+ insideDragDrop: {
+ display: 'flex',
+ justifyContent: 'center',
+ alignItems: 'center',
+ flexDirection: 'column',
+ height: '100%',
+ },
+ inputFile: {
+ display: 'none',
+ },
+ chooseEmojiContainer: {
+ display: 'flex',
+ justifyContent: 'center',
+ alignItems: 'center',
+ flexDirection: 'column',
+ width: '100%',
+ gap: 14,
+ marginTop: 10,
+ marginBottom: 30,
+ },
+ label: {
+ width: 'auto',
+ },
+ formItem: {
+ marginBottom: 35,
+ },
+ inputFileLabel: {
+ textDecorationLine: 'underline',
+ textDecorationColor: '#3574F4',
+ color: '#3574F4',
+ '&:hover': {
+ cursor: 'pointer',
+ }
+ },
+ nameXIcon: {
+ display: 'flex',
+ justifyContent: 'center',
+ alignItems: 'center',
+ marginTop: 12,
+ gap: 4,
+ zIndex: 100,
+ },
+ dragDropIcon: {
+ color: '#BBBEC2',
+ },
+ dragDropText: {
+ color: '#D1D5DB',
+ textAlign: 'center'
+ },
+ icon: {
+ cursor: 'pointer',
+ color: '#11182766',
+ fontSize: 20,
+ },
+ dragDropBrowse: {
+ color: '#111827',
+ },
+ inputDropContainer: {
+ display: 'none',
+ },
+ labelInputDropContainer: {
+ height: '100%',
+ width: '100%',
+ display: 'flex',
+ alignItems: 'center',
+ justifyContent: 'center',
+ flexDirection: 'column',
+ },
+ dropItContainer: {
+ display: 'flex',
+ justifyContent: 'center',
+ alignItems: 'center',
+ gap: 10,
+ },
+ dropItLabel: {
+ fontSize: 22,
+ fontStyle: "bold",
+ },
+ dragFileElement: {
+ position: 'absolute',
+ width: '100vw',
+ height: '100vh',
+ },
+ error: {
+ color: '#E53C3C',
+ fontSize: 14,
+ display: 'flex',
+ gap: 11,
+ marginTop: 15,
+ }
+}));
diff --git a/source/views/Extension/Views/ImportWallet/index.jsx b/source/views/Extension/Views/ImportWallet/index.jsx
index 18be5bc5..7acdf417 100644
--- a/source/views/Extension/Views/ImportWallet/index.jsx
+++ b/source/views/Extension/Views/ImportWallet/index.jsx
@@ -1,19 +1,27 @@
import React from 'react';
-import { Layout, Header } from '@components';
-import useSteps from './hooks/useSteps';
+import { Layout, Header, MenuItemDetailed } from '@components';
+import { LinkButton } from '@components';
+import { useTranslation } from 'react-i18next';
+import BackIcon from '@assets/icons/back.svg';
+import { useRouter } from '@components/Router';
+import PaperEmoji from "@assets/paper.svg"
+import NewKey from "@assets/new-key.svg"
const ImportWallet = () => {
- const {
- component,
- left,
- right,
- center,
- } = useSteps();
+ const { t } = useTranslation();
+ const { navigator } = useRouter();
+
+
+ const left = navigator.navigate('home')} startIcon={BackIcon} />;
+ const right = navigator.navigate('home')} />;
+ const center = `${t("importWallet.importWallet")}`
+
return (
- {component}
+ navigator.navigate('import-pem-file')}/>
+ navigator.navigate('import-private-key')}/>
);
};