Skip to content
This repository has been archived by the owner on Sep 30, 2023. It is now read-only.

importing identity #54

Open
sirpy opened this issue Jan 22, 2020 · 10 comments
Open

importing identity #54

sirpy opened this issue Jan 22, 2020 · 10 comments

Comments

@sirpy
Copy link

sirpy commented Jan 22, 2020

I can't use orbitdb local keystore for stoarge
so I serialize the identity to JSON and save it on another storage
How can I import the saved identity back to orbitdb every time my server starts?

@sirpy
Copy link
Author

sirpy commented Feb 4, 2020

any one?

@bluelovers
Copy link

i want to know too

@sirpy
Copy link
Author

sirpy commented Feb 17, 2020

can anyone from the mainters comment on this?
pointer on how to implement?

@shamb0t
Copy link
Contributor

shamb0t commented Feb 18, 2020

@sirpy @bluelovers the keystore is required to be able to use the identity as that is where the signing keys are stored, so they will need to be stored in some persistent storage somewhere. The identity JSON does not contain key information and cannot be used to sign entries. To import and recreate the identity on start you should specify the keystore location and recreate the identity using createIdentity with some id (which you specify) as follows:

const Keystore = require('orbit-db-keystore')
const Identities = require('orbit-db-identity-provider')

const keystore = new Keystore('PATH_TO_KEYSTORE_IN_STORAGE')
const identity = await Identities.createIdentity({ keystore: keystore, id: 'myId' }) 
// should always return same identity if you use the same keystore and id

Are you able to recreate the identity this way?

@sirpy
Copy link
Author

sirpy commented Feb 18, 2020

@shamb0t
Yes I understand how it basically works, but as explained, I can't use localstorage and I want to save it in some other remote storage, so the question is how can this be done if at all

@sirpy
Copy link
Author

sirpy commented Apr 10, 2020

@shamb0t we would like to use an external source or to import an identity to the keystore

@choetech160
Copy link

choetech160 commented Feb 15, 2021

Anyone got an answer on this?
I have a packaged App which can't be used when moved on other devices because the identities aren't matching, thus cannot write to the database. I understand that one identity cannot be at multiple places at the same time, but would like to build the app somewhere and then distribute it, with the specific ID to someone else.
I don't understand how the IDs/keys are generated and everyone say "it's random" but I feel it uses some specific UID from the hardware because I get the same ID/keys across build when on the same machine.

@LucaPanofsky
Copy link

@sirpy I think that you could try to follow this example

https://github.com/libp2p/js-libp2p/blob/master/examples/webrtc-direct/listener.js

In particular, you have to find a way to store in Heroku either your peer id or a secret which enables you to to recreate in a deterministic way your id every time the server process starts. In this way your Ipfs node will always have the same peer id which means that you are also going to obtain the same orbit id.

I tried to do something similar here
https://github.com/LucaPanofsky/ipfs-wss-heroku-node (although the code needs improvement).

In addition I think that there is another option available.
You can try to implement your custom identity provider:
https://github.com/orbitdb/orbit-db-identity-provider
For instance, if you look at the Ethereum identity provider
https://github.com/orbitdb/orbit-db-identity-provider/blob/main/src/ethereum-identity-provider.js

const { Wallet, verifyMessage } = require('@ethersproject/wallet')

...

async getId (options = {}) {
    if (!this.wallet) {
      this.wallet = await this._createWallet(options)
    }
    return this.wallet.getAddress()
  }

...

it seems possible to write a custom identity provider which fetches identity data from wherever you desire.

@mateuszjarzewski
Copy link

mateuszjarzewski commented Mar 28, 2022

I did something like this and it works perfectly, it is a browser version, might need a little tweaking to work on node

var my_store_provider = {

  status: 'open',

  open: function(){

    //if ( window.console ){
      // console.log('open arguments:')
      // console.log(arguments)
    //}
  },
  put: function(){

    //if ( window.console ){
      // console.log('put arguments:')
      // console.log(arguments)
    //}
  },
  get: function(){

    //if ( window.console ){
      // console.log('get arguments:')
      // console.log(arguments)
    //}

    if ( 'myId' === arguments[0] ){

      return "{\"publicKey\":\"04c27a8828aec4d3352c30d7c8f8d5743c9317646e70f0ffb7c017d36aac28dae946606952edeca823828e3a6939637d277da53b6eaf510142b184aa2ffa6e4375\",\"privateKey\":\"7905676d074489f7ee1997f86c8f1f3cbd258f318eae76b7a9ac5b4104c15f71\"}";
    }

    if ( '03c27a8828aec4d3352c30d7c8f8d5743c9317646e70f0ffb7c017d36aac28dae9' === arguments[0] ){

      return "{\"publicKey\":\"0454b2e47526ede9d8a06e048b216609f969f50d456b6beeaa558f6a91cd83b3cb93044a6d10a25922095e77644b680a49e24afe9808cdfe7d813f56c6be20a4d0\",\"privateKey\":\"0f72d1451ca9cf9a267f1f26d242edc769c601daf5d16bc85b53c087bfa6ee6e\"}";
    }
  }
}

var keystore = new OrbitDB.Keystore(my_store_provider)
OrbitDB.Identities.createIdentity({ keystore: keystore, id: 'myId' }).then(function(e){

})

@mateuszjarzewski
Copy link

mateuszjarzewski commented Apr 1, 2022

Better still
I think this code will create so called "deterministic key" that will always be the same,
so no point migrating nothing when you can create key from password each time user logs in.
Same idea behind this: https://keybase.io/warp/

// cdn.jsdelivr.net/npm/[email protected]/dist/forge.min.js
// unpkg.com/[email protected]/dist/index.min.js
// unpkg.com/[email protected]/dist/orbitdb.js

var password = 'mystrongpassword';
var md = forge.md.sha256.create();
md.update(password);
var seed = md.digest().data
var ed25519 = forge.pki.ed25519;
var keypair = ed25519.generateKeyPair({seed: seed});

class MyIdentityProvider extends OrbitDB.Identities.IdentityProvider {
  static get type () { return 'MyIdentityType' } // return type
  async getId () {

    return Buffer.from(keypair.publicKey).toString('hex')
   } // return identifier of external id (eg. a public key)
    async signIdentity (data) {

    var signature = ed25519.sign({
      message: data,
      // also accepts `binary` if you want to pass a binary string
      encoding: 'utf8',
      // node.js Buffer, Uint8Array, forge ByteBuffer, binary string
      privateKey: keypair.privateKey
    });

    signature = forge.util.bytesToHex(signature)

    return signature

   } //return a signature of data (signature of the OrbtiDB public key)
  static async verifyIdentity (identity) {

    // verify a signature on a UTF-8 message
    return ed25519.verify({
      message: identity.publicKey + identity.signatures.id,
      encoding: 'utf8',
      signature: forge.util.hexToBytes(identity.signatures.publicKey),
      publicKey: forge.util.hexToBytes(identity.id)
    })
    // `verified` is true/false

  } //return true if identity.sigantures are valid
}

OrbitDB.Identities.addIdentityProvider(MyIdentityProvider)

OrbitDB.Identities.createIdentity({ type: `MyIdentityType`, id: 'myId' }).then(function(e){
  
})

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

6 participants