Skip to content
This repository has been archived by the owner on Aug 9, 2021. It is now read-only.

Commit

Permalink
Merge pull request #14 from 3box/feat/idw-iframe
Browse files Browse the repository at this point in the history
Feat/idw iframe
  • Loading branch information
zachferland committed Apr 14, 2020
2 parents 2993814 + 20bc6f9 commit ab79a3a
Show file tree
Hide file tree
Showing 23 changed files with 37,617 additions and 5,025 deletions.
97 changes: 97 additions & 0 deletions .circleci/config.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
version: 2.1

orbs:
aws-s3: circleci/[email protected]

jobs:
test-and-build:
working_directory: ~/3id-connect
docker:
- image: circleci/node:10
steps:
- checkout

# Download and cache dependencies
- restore_cache:
keys:
- dependencies-cache-{{ checksum "package.json" }}

- run:
name: install dependencies
command: |
sudo npm i -g codecov node-gyp
npm i
# - run:
# name: test
# command: npm test && codecov
#
# - run:
# name: lint
# command: npm run lint

- run:
name: build
command: npm run build

# - run:
# name: code-coverage
# command: bash <(curl -s https://codecov.io/bash)

- persist_to_workspace:
root: .
paths:
- public

- save_cache:
key: dependency-cache-{{ checksum "package.json" }}
paths:
- ./node_modules
deploy-dev:
working_directory: ~/3id-connect
docker:
- image: 'circleci/python:3.8'
steps:
- attach_workspace:
at: .
- aws-s3/sync:
arguments: '--acl public-read --cache 604800'
from: public
overwrite: true
to: 's3://3id-connect-dev'
- run:
name: "Invalidate CloudFront Cache"
command: aws cloudfront create-invalidation --distribution-id E3SV2UNQUEOU2O --paths /*

deploy-prod:
working_directory: ~/3id-connect
docker:
- image: 'circleci/python:3.8'
steps:
- attach_workspace:
at: .
- aws-s3/sync:
arguments: '--acl public-read --cache 604800'
from: public
overwrite: true
to: 's3://3id-connect-prod'
- run:
name: "Invalidate CloudFront Cache"
command: aws cloudfront create-invalidation --distribution-id E1CFVBE8FYHOZ0 --paths /*

workflows:
build-deploy:
jobs:
- test-and-build
- deploy-dev:
requires:
- test-and-build
# filters:
# branches:
# only: develop
- deploy-prod:
requires:
- test-and-build
filters:
branches:
only: master
13 changes: 13 additions & 0 deletions Dockerfile.example
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
FROM node:10

WORKDIR /3id-connect

COPY package.json package-lock.json ./

COPY src ./src
COPY webpack*.config.js .babelrc ./
COPY public ./public

EXPOSE 30001

CMD npm run start
36 changes: 34 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,35 @@
# 3box-account
This is a simple iframe page that is used to authenticate 3box accounts for the 3box-js library.
[![Discord](https://img.shields.io/discord/484729862368526356.svg?style=for-the-badge)](https://discordapp.com/invite/Z3f3Cxy)
[![Twitter Follow](https://img.shields.io/twitter/follow/3boxdb.svg?style=for-the-badge&label=Twitter)](https://twitter.com/3boxdb)

# <a name="intro"></a> 3ID-Connect

3ID-Connect is a 3ID account management service run in an iframe. It allows you to authenicate, manage, and permission your 3ID keys to applications. Used by default in [3box-js](https://github.com/3box/3box-js). [identity-wallet-js](https://github.com/3box/identity-wallet-js) handles most operations and the parent window (application) communicates with iframe service over RPC layer as defined by [3ID JSON-RPC](https://github.com/3box/3box/blob/master/3IPs/3ip-10.md)

Right now you authenticate and link ethereum accounts to mange your 3ID, in the future other keypairs, blockchain accounts, and authentication methods can be added.

## <a name="structure"></a> Structure

* **/src** - Core logic and consumable interfaces for clients and iframe
* **/threeIdConnect.js** - Application interface (RPC client) to load iframe and return 3ID provider.
* **/threeIdConnectService.js** - Identity wallet instance and RPC 'server' to handle requests
* **/threeIdProviderProxy.js** - 3ID provider interface that relays request through RPC layer
* **/iframe** - all html, css, js, design assets for iframe and flow
* **/public** - build assets deployed for iframe

## <a name="development"></a> Development

Clone and install dependencies

#### Run Locally

Will serve iframe locally on port 30001

```
$ npm run start
```

#### Build

```
$ npm run build
```
120 changes: 120 additions & 0 deletions iframe/html/3IDConnect/assets/assets.js

Large diffs are not rendered by default.

Empty file.
39 changes: 39 additions & 0 deletions iframe/html/3IDConnect/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
const style = require('style-loader!./../style.scss')
const template = require('./template.js').default

const providerTemplate = (data) => template(data, providerSelect())

const providerSelect = () => `
<div class='${style.promptHeader}'>
<div class='${style.promptText}'>
<div class='${style.primaryText}'> <span class='${style.primaryHighlight}'> Select Your Wallet </span> </div>
<div class='${style.subText}'> This must match the wallet used for dasboard.3box.io </div>
</div>
<div class='${style.promptImage}'></div>
</div>
<div class='${style.divider}'></div>
<div class='${style.providerBox}'>
<div class='${style.providerRow}'>
<div class='${style.provider}' onClick="providerNameFunc('injected', null, 'MetaMask')">
<div class='${style.providerImage}'> </div>
<div class='${style.providerText}'> Metamask </div>
</div>
<div class='${style.provider}' onClick="providerNameFunc('fortmatic', null, 'Fortmatic')">
<div class='${style.providerImage}'> </div>
<div class='${style.providerText}'> Fortmatic </div>
</div>
</div>
<div class='${style.providerRow}' onClick="providerNameFunc('portis', null, 'Portis')">
<div class='${style.provider}'>
<div class='${style.providerImage}'> </div>
<div class='${style.providerText}'> Portis </div>
</div>
<div class='${style.provider}'>
<div class='${style.providerImage}' onClick="providerNameFunc('authereum', null, 'Authereum')"> </div>
<div class='${style.providerText}'> Authereum </div>
</div>
</div>
</div>
`

export default providerTemplate
65 changes: 65 additions & 0 deletions iframe/html/3IDConnect/providerSelect.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
const style = require('style-loader!../../style.scss')
const assets = require('./assets/assets.js')

const providerSelect = (data, isMobile) => `
<div class='${style.actions}'>
<div class='${style.walletSelect} ${isMobile ? style.walletSelectMobile : ''}' onClick="handleOpenWalletOptions()" id="walletSelect">
<div class='${style.walletSelect_content}'>
<div class='${style.providerImage}' id='chosenWallet'>
${getProviderDisplayImage(data.request.opts.address)}
</div>
<h5 id='selectedWallet' class='${style.providerImageText}'>
${getProviderDisplayName(data.request.opts.address) || `Choose wallet`}
</h5>
</div>
</div>
<div class='${style.providerBox} ${isMobile ? style.providerBoxMobile : ''}' id='walletOptions' onClick="handleOpenWalletOptions()">
<div class='${style.provider}' onClick="providerNameFunc('injected', '${data.request.opts.address}', 'MetaMask')">
<div class='${style.providerImage}'>
${assets.MetaMask}
</div>
<div class='${style.providerText}'> Metamask </div>
</div>
<div class='${style.provider}' onClick="providerNameFunc('fortmatic', '${data.request.opts.address}', 'Fortmatic')">
<div class='${style.providerImage}'>
${assets.Fortmatic}
</div>
<div class='${style.providerText}'> Fortmatic </div>
</div>
<div class='${style.provider}' onClick="providerNameFunc('portis', '${data.request.opts.address}', 'Portis')">
<div class='${style.providerImage}'>
${assets.Portis}
</div>
<div class='${style.providerText}'> Portis </div>
</div>
<div class='${style.provider}' onClick="providerNameFunc('authereum', '${data.request.opts.address}', 'Authereum')">
<div class='${style.providerImage}'>
${assets.Authereum}
</div>
<div class='${style.providerText}'> Authereum </div>
</div>
<div class='${style.provider}' onClick="providerNameFunc('wallet', '${data.request.opts.address}', 'WalletConnect')" >
<div class='${style.providerImage}'>
${assets.WalletConnect}
</div>
<div class='${style.providerText}'> WalletConnect</div>
</div>
</div>
<button id='accept' class='${style.primaryButton}'>
Continue
</button>
<button id='decline' class='${style.secondaryButton}' onClick="hideIframe()">
Cancel
</button>
</div>
`

export default providerSelect
6 changes: 6 additions & 0 deletions iframe/html/3IDConnect/requestCard.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
const template = require('./template.js').default
const providerSelect = require('./providerSelect.js').default

const requestCard = (data, isMobile) => template(data, providerSelect(data, isMobile), isMobile)

export default requestCard
62 changes: 62 additions & 0 deletions iframe/html/3IDConnect/template.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
const style = require('style-loader!../../style.scss')
const assets = require('./assets/assets.js')

const capitalizeFirst = string => string.charAt(0).toUpperCase() + string.slice(1)
const spaceString = (spaces) => spaces.join(', ')

const template = (data, content, isMobile) => `
<div class='${style.card} ${isMobile ? style.cardMobile : ''}'>
<div class=${style.controls}>
<a
href="https://3box.io"
rel="noopener noreferrer"
target="_blank"
class=${style.controls_logo}
>
${assets.Logo}
</a>
<div class='${style.close}' onClick="hideIframe()">
<div class='${style.close_line} ${style.flip}'></div>
<div class='${style.close_line}'></div>
</div>
</div>
<div class='${style.content} ${isMobile ? style.contentMobile : ''}' id='content' >
<div class='${style.header}'>
<img
src='${`https://${data.request.origin}/favicon.ico`}'
class='${style.headerLogo}'
onError='handleBrokenImage(this)'
id='siteFavicon'
/>
<div class='${style.headerText}'>
<div class='${style.primary}'>
${data.request.origin}
</div>
<p class='${style.sub}'> wants to access your data </p>
</div>
<div class='${style.promptText}'>
<div class='${style.subText}'>
<p>
<span>${capitalizeFirst(data.request.origin)}</span> uses 3ID to give you privacy and control over your data.
This app wants to access: ${spaceString(data.request.spaces)}.
</p>
${data.error ? error(data) : ``}
</div>
</div>
</div>
<div class='${style.promptBox}'>
${content}
</div>
</div>
</div>
<div class='${style.onClickOutside}' id='onClickOutside' onClick="handleOpenWalletOptions()"></div>
`
export default template

const error = (data) => `
<p class='${style.walletSelect_error}'>${data.error}</p>
`
Loading

0 comments on commit ab79a3a

Please sign in to comment.