Skip to content

Commit

Permalink
Merge pull request #73 from HunnySajid/feat/aid-cred-sig
Browse files Browse the repository at this point in the history
Feat/aid cred sig
  • Loading branch information
rodolfomiranda committed Jan 17, 2024
2 parents 3832c67 + e7a816a commit 7dda975
Show file tree
Hide file tree
Showing 8 changed files with 157 additions and 72 deletions.
65 changes: 46 additions & 19 deletions example-web/my-app/src/App.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@ import logo from "./ACME_Corporation.png";
import Button from "@mui/material/Button";
import "./App.css";

const extensionId = "dfhkgnnnbadadbljpjnpifpbaemcgpfa";

function App() {
const handleRequestIdentifier = () => {
window.postMessage({ type: "select-identifier" }, "*");
Expand All @@ -11,34 +13,59 @@ function App() {
window.postMessage({ type: "select-credential" }, "*");
};

const handleSyncRequest = () => {
const handleRequestIdORCred = () => {
window.postMessage({ type: "select-aid-or-credential" }, "*");
};

const handleSyncRequest = async () => {
// TODO extension Id harcoded just for testing, need to find a way to get it dynamically
chrome.runtime.sendMessage(
"fklmfbmpaimbgjplbambkdjphdadbmed",
{ data: "test" },
function (response) {
if (!response.success) console.log(response.data);
alert(
"Signed headers received\n" +
JSON.stringify(response.data.headers, null, 2)
);
}
);
const { data, error } = await chrome.runtime.sendMessage(extensionId, {
type: "fetch-resource",
subtype: "auto-signin-signature",
});

if (error) {
alert(error?.message);
} else {
alert(
"Signed headers received\n" + JSON.stringify(data.headers, null, 2)
);
}
};

return (
<div className="App">
<header className="App-header">
<img src={logo} alt="logo" />
<div className="flex flex-row gap-x-2 mt-2">
<Button variant="contained" onClick={handleRequestIdentifier}>
Authenticate with AID
<div className="flex flex-col gap-y-2 mt-2">
<p className=" text-lg font-bold">Authenticate with</p>
<Button
variant="contained"
color="success"
onClick={handleRequestIdentifier}
>
AID
</Button>
<Button
variant="contained"
color="success"
onClick={handleRequestCredential}
>
Credential
</Button>
<Button variant="contained" onClick={handleRequestCredential}>
Authenticate with Credential
<Button
variant="contained"
color="success"
onClick={handleRequestIdORCred}
>
AID or CRED
</Button>
<Button variant="contained" onClick={handleSyncRequest}>
Synchronous Authentication
<Button
variant="contained"
color="success"
onClick={handleSyncRequest}
>
Synchronous
</Button>
</div>
</header>
Expand Down
62 changes: 37 additions & 25 deletions src/components/main.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,46 +16,58 @@ export function Main(props: IMain): JSX.Element {
const [tabState, setTabState] = useState(TAB_STATE.DEFAULT);

const fetchTabState = async () => {
chrome.tabs.query(
{ active: true, currentWindow: true },
async function (tabs) {
const { data } = await chrome.tabs.sendMessage(tabs[0].id!, {
type: "tab",
subtype: "get-tab-state",
});
if (!data) return;

chrome.tabs.query({ active: true, currentWindow: true }, async function (tabs) {
const { data } = await chrome.tabs.sendMessage(
tabs[0].id!,
{ type: "tab", subtype: "get-tab-state" }
);
if (!data) return;

if (data?.appState) {
setTabState(data?.appState);
if (
data?.appState === TAB_STATE.SELECT_IDENTIFIER ||
data?.appState === TAB_STATE.SELECT_CREDENTIAL
) {
setActiveSidebar(
data?.appState === TAB_STATE.SELECT_IDENTIFIER
? "Identifiers"
: "Credentials"
);
if (data?.appState) {
setTabState(data?.appState);
if (
data?.appState === TAB_STATE.SELECT_IDENTIFIER ||
data?.appState === TAB_STATE.SELECT_CREDENTIAL ||
data?.appState === TAB_STATE.SELECT_ID_CRED
) {
setActiveSidebar(
data?.appState === TAB_STATE.SELECT_IDENTIFIER ||
data?.appState === TAB_STATE.SELECT_ID_CRED
? "Identifiers"
: "Credentials"
);
}
}
}
}
});
);
};

useEffect(() => {
fetchTabState();
}, []);

const renderItems = () => {
if (tabState === TAB_STATE.SELECT_IDENTIFIER) return <SelectIdentifier />;

if (tabState === TAB_STATE.SELECT_CREDENTIAL) return <SelectCredential />;

switch (activeSidebar) {
case "Credentials":
if (
tabState === TAB_STATE.SELECT_CREDENTIAL ||
tabState === TAB_STATE.SELECT_ID_CRED
)
return <SelectCredential />;

return <CredentialList />;
case "Sign Ins":
return <SigninList />;

default:
if (
tabState === TAB_STATE.SELECT_IDENTIFIER ||
tabState === TAB_STATE.SELECT_ID_CRED
)
return <SelectIdentifier />;

return <IdentifierList />;
}
};
Expand All @@ -73,7 +85,7 @@ export function Main(props: IMain): JSX.Element {
active={activeSidebar}
onClickLink={setActiveSidebar}
onSignout={props.handleDisconnect}
disabled={isSidebarDisabled()}
// disabled={isSidebarDisabled()}
/>
<div className="rounded p-2 sm:ml-48 sm:mt-4 bg-gray-dark text-gray-light mr-4">
<div className="">
Expand Down
81 changes: 56 additions & 25 deletions src/pages/background/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,12 @@ import { userService } from "@pages/background/services/user";
import { signifyService } from "@pages/background/services/signify";
import { IMessage } from "@pages/background/types";
import { senderIsPopup } from "@pages/background/utils";
import { getCurrentDomain } from "@pages/background/utils";
import { updateDomainAutoSigninByIndex, deleteSigninByIndex } from "@pages/background/signins-utils";
import { removeSlash, getCurrentDomain } from "@pages/background/utils";
import {
updateDomainAutoSigninByIndex,
getSigninsByDomain,
deleteSigninByIndex,
} from "@pages/background/signins-utils";

console.log("Background script loaded");

Expand Down Expand Up @@ -148,8 +152,14 @@ chrome.runtime.onMessage.addListener(function (
});
}

if (message.type === "update-resource" && message.subtype === "auto-signin") {
const resp = await updateDomainAutoSigninByIndex(message?.data?.index, message?.data?.signin);
if (
message.type === "update-resource" &&
message.subtype === "auto-signin"
) {
const resp = await updateDomainAutoSigninByIndex(
message?.data?.index,
message?.data?.signin
);
sendResponse({
data: {
...resp,
Expand Down Expand Up @@ -179,29 +189,50 @@ chrome.runtime.onMessage.addListener(function (
return true;
});

chrome.runtime.onMessageExternal.addListener(async function (
request,
chrome.runtime.onMessageExternal.addListener(function (
message,
sender,
sendResponse
) {
console.log("Message received from external source: " + sender.url);
// if (sender.url === blocklistedWebsite)
// return; // don't allow this web page access
// if (request.openUrlInEditor)
// openUrl(request.openUrlInEditor);
// sendResponse({data: "received"})
const origin = sender.url!;
const signins = (await browserStorageService.getValue("signins")) as any;
// Validate that message comes from a page that has a signin
if (origin.startsWith(signins[0].domain)) {
const signedHeaders = await signifyService.signHeaders(
signins[0].identifier.name,
origin
);
let jsonHeaders: { [key: string]: string } = {};
for (const pair of signedHeaders.entries()) {
jsonHeaders[pair[0]] = pair[1];
(async () => {
console.log("Message received from external source: ", sender);
console.log("Message received from external request: ", message);
// if (sender.url === blocklistedWebsite)
// return; // don't allow this web page access
// if (request.openUrlInEditor)
// openUrl(request.openUrlInEditor);
// sendResponse({data: "received"})

if (
message.type === "fetch-resource" &&
message.subtype === "auto-signin-signature"
) {
// Validate that message comes from a page that has a signin

const origin = removeSlash(sender.url);
const signins = await getSigninsByDomain(origin);
console.log("signins", signins);
const autoSignin = signins?.find((signin) => signin.autoSignin);
if (!signins?.length || !autoSignin) {
sendResponse({
error: { code: 404, message: "auto signin not found" },
});
return;
}

const signedHeaders = await signifyService.signHeaders(
// sigin can either have identifier or credential
autoSignin?.identifier.name ?? autoSignin?.credential?.schema?.title,
origin
);
let jsonHeaders: { [key: string]: string } = {};
for (const pair of signedHeaders.entries()) {
jsonHeaders[pair[0]] = pair[1];
}
sendResponse({ data: { headers: jsonHeaders } });
}
sendResponse({ data: { headers: jsonHeaders } });
}
})();

// return true to indicate chrome api to send a response asynchronously
return true;
});
5 changes: 5 additions & 0 deletions src/pages/background/signins-utils.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,10 @@
import { browserStorageService } from "@pages/background/services/browser-storage";

export const getSigninsByDomain = async (domain: string) => {
const signins = await browserStorageService.getValue("signins");
return signins?.filter(signin => signin.domain === domain) ?? [];
};

export const updateDomainAutoSigninByIndex = async (index: number, signin) => {
let signins = await browserStorageService.getValue("signins");
if (signins?.length) {
Expand Down
8 changes: 6 additions & 2 deletions src/pages/background/utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ export const getCurrentTab = (): Promise<chrome.tabs.Tab> => {

export const getCurrentDomain = async () => {
const currentTab = await getCurrentTab();
console.log("Current tab: ", currentTab)
console.log("Current tab: ", currentTab);
return currentTab ? new URL(currentTab.url!) : null;
};

Expand All @@ -39,4 +39,8 @@ export const obfuscateString = (inputString: string) => {
const suffix = inputString.slice(-suffixLength);

return `${prefix}...${suffix}`;
}
};

export const removeSlash = (site:string) => {
return site.replace(/\/$/, "");
};
1 change: 1 addition & 0 deletions src/pages/content/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@ window.addEventListener(
switch (event.data.type) {
case TAB_STATE.SELECT_IDENTIFIER:
case TAB_STATE.SELECT_CREDENTIAL:
case TAB_STATE.SELECT_ID_CRED:
setTabState(TAB_STATE.DEFAULT);
const { data } = await chrome.runtime.sendMessage<IMessage<void>>({
type: "authentication",
Expand Down
6 changes: 5 additions & 1 deletion src/pages/dialog/Dialog.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,11 @@ export default function Dialog({
{!signins.length || !isConnected ? (
<p className="mt-2 text-sm text-green max-w-[280px] font-bold">
<span className="">{tabUrl}</span> requests authentication with{" "}
{eventType === TAB_STATE.SELECT_IDENTIFIER ? "AID" : "credential"}
{eventType === TAB_STATE.SELECT_IDENTIFIER
? "AID"
: eventType === TAB_STATE.SELECT_ID_CRED
? "AID or Credential"
: "Credential"}
</p>
) : null}

Expand Down
1 change: 1 addition & 0 deletions src/pages/popup/constants.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,5 +2,6 @@ export const TAB_STATE = {
DEFAULT: "default",
SELECT_IDENTIFIER: "select-identifier",
SELECT_CREDENTIAL: "select-credential",
SELECT_ID_CRED: "select-aid-or-credential",
NONE: "none"
}

0 comments on commit 7dda975

Please sign in to comment.