Selaa lähdekoodia

storage-node cli: add development commands

Mokhtar Naamani 4 vuotta sitten
vanhempi
commit
a7a4f91bd7

+ 15 - 0
storage-node/packages/cli/bin/cli.js

@@ -58,6 +58,10 @@ const cli = meow(`
                       ID, as well as an output filename.
     head              Send a HEAD request for a file, and print headers.
                       Requires a storage node URL and a content ID.
+
+  Dev Commands:       Commands to run on a development chain.
+    dev-init          Setup chain with Alice as lead and provider.
+    dev-check         Check the chain is setup with Alice as lead and provider.
   `,
   { flags: FLAG_DEFINITIONS })
 
@@ -67,6 +71,17 @@ function assert_file (name, filename) {
 }
 
 const commands = {
+  // add Alice well known account as storage provider
+  'dev-init': async (runtime_api) => {
+    let dev = require('./dev')
+    return dev.init(runtime_api)
+  },
+  // Checks that the setup done by dev-init command was successful.
+  'dev-check': async (runtime_api) => {
+    let dev = require('./dev')
+    return dev.check(runtime_api)
+    // await runtime_api.assets.checkLiaisonForDataObject(providerId, '')
+  },
   'upload': async (runtime_api, url, filename, do_type_id) => {
     // Check parameters
     assert_file('file', filename)

+ 93 - 0
storage-node/packages/cli/bin/dev.js

@@ -0,0 +1,93 @@
+function aliceKeyPair (runtime_api) {
+  return runtime_api.identities.keyring.addFromUri('//Alice', null, 'sr25519')
+}
+
+// Setup Alice account on a developement chain that was
+// just launched as the storage lead, and a storage provider using the same
+// key as the role key
+const init = async (runtime_api) => {
+  const alice = aliceKeyPair(runtime_api).address
+  const providerId = 0 // first assignable id
+
+  // Check if setup already completed
+  if (await runtime_api.workers.isRoleAccountOfStorageProvider(providerId, alice)) {
+    console.log('Alice already setup as a storage provider')
+    return
+  }
+
+  // make sure alice is sudo - indirectly checking this is a dev chain
+  const sudo = await runtime_api.api.query.sudo.key()
+
+  if (!sudo.eq(alice)) {
+    throw new Error('Setup requires Alice to be sudo. Are you sure you are running a devchain?')
+  }
+
+  // register alice as a member if not already registered
+  console.log(`Registering Alice as a member`)
+  const aliceMemberId = 0 // first assignable id
+  runtime_api.identities.registerMember(alice, {
+    handle: 'alice'
+  })
+
+  // Make alice the storage lead
+  // prepare set storage lead tx
+  const setLeadTx = runtime_api.api.tx.storageWorkingGroup.setLead(aliceMemberId, alice)
+  // make sudo call
+  console.log('Setting Alice as Lead')
+  runtime_api.signAndSend(
+    alice,
+    runtime_api.api.tx.sudo.sudo(setLeadTx)
+  )
+
+  // create an openinging, apply, start review, fill opening
+  // Assumption opening id and applicant id, provider id will all be the first ids == 0
+  // so we don't await each tx to finalize to get the ids. this allows us to
+  // batch all the transactions into a single block.
+  console.log('Making Alice a storage provider')
+  const openTx = runtime_api.api.tx.storageWorkingGroup.addWorkerOpening('CurrentBlock', {
+    application_rationing_policy: {
+      'max_active_applicants': 1
+    },
+    max_review_period_length: 1000
+    // default values for everything else..
+  }, 'opening0')
+  runtime_api.signAndSend(alice, openTx)
+  const openingId = 0 // first id
+  const applyTx = runtime_api.api.tx.storageWorkingGroup.applyOnWorkerOpening(
+    aliceMemberId, openingId, alice, null, null, 'alice'
+  )
+  runtime_api.signAndSend(alice, applyTx)
+  const applicantId = 0 // first applicant id
+
+  const reviewTx = runtime_api.api.tx.storageWorkingGroup.beginWorkerApplicantReview(openingId)
+  runtime_api.signAndSend(alice, reviewTx)
+
+  const fillTx = runtime_api.api.tx.storageWorkingGroup.fillWorkerOpening(openingId, [applicantId], null)
+
+  await runtime_api.signAndSend(alice, fillTx)
+
+  // const worker = await runtime_api.workers.storageWorkerByProviderId(providerId)
+  if (await runtime_api.workers.isRoleAccountOfStorageProvider(providerId, alice)) {
+    console.log('Setup Successful')
+  } else { throw new Error('Setup Failed') }
+}
+
+const check = async (runtime_api) => {
+  const providerId = 0
+  const roleAccountId = aliceKeyPair(runtime_api).address
+
+  if (await runtime_api.workers.isRoleAccountOfStorageProvider(providerId, roleAccountId)) {
+    console.log('Alice is correctly setup as a storage provider')
+  } else { throw new Error('Alice is not setup as a storage provider') }
+
+  const currentLead = await runtime_api.api.query.storageWorkingGroup.currentLead()
+
+  if (currentLead.isSome && currentLead.unwrap().role_account_id.eq(roleAccountId)) {
+    console.log('Alice is correctly setup as the storage lead')
+  } else { throw new Error('Alice is not the storage lead') }
+}
+module.exports = {
+  init,
+  check,
+  aliceKeyPair
+}

+ 3 - 3
storage-node/packages/runtime-api/assets.js

@@ -76,12 +76,12 @@ class AssetsApi
       throw new Error(`No DataObject created for content ID: ${contentId}`);
     }
 
-    if (obj.raw.liaison.neq(storageProviderId)) {
+    if (obj.liaison.neq(storageProviderId)) {
       throw new Error(`This storage node is not liaison for the content ID: ${contentId}`);
     }
 
-    if (obj.raw.liaison_judgement.type != 'Pending') {
-      throw new Error(`Expected Pending judgement, but found: ${obj.raw.liaison_judgement.type}`);
+    if (obj.liaison_judgement.type != 'Pending') {
+      throw new Error(`Expected Pending judgement, but found: ${obj.liaison_judgement.type}`);
     }
 
     return obj.unwrap();

+ 16 - 0
storage-node/packages/runtime-api/identities.js

@@ -189,6 +189,22 @@ class IdentitiesApi
 
     return filename;
   }
+
+  async registerMember (accountId, userInfo) {
+    const subscribed = [['members', 'MemberRegistered']]
+    const tx = this.base.api.tx.members.buyMembership(0, userInfo)
+    return new Promise(async (resolve, reject) => {
+      try {
+        await this.base.signAndSend(accountId, tx, 1, subscribed, (events) => {
+          events.forEach((event) => {
+            resolve(event[1].MemberId)
+          })
+        })
+      } catch (err) {
+        reject(err)
+      }
+    })
+  }
 }
 
 module.exports = {