I can use canisters defined in the same project, for instance I can use my my_canister canister from within the my_canister_assets by using the following import statement:
import 'ic:canisters/my_canister';
But what if I want to interact with that canister from a completely different project? The same import statement, expectedly, gives me Target of URI doesn't exist: 'ic:canisters/my_canister'.
How can I import and interact with the canister from an external project?
You can create an instance of an actor using the id of your external canister and give it a type that matches only the methods in that canister which you want to call, see this example: Calling another canister's methods
Use the canister id that dfx gives you when you deploy (note the ids no longer have an “ic:” prefix).
Thanks for the reply. Good news that I can use external canisters from Motoko, but is it possible to use them in JavaScript? Is there the concept of an “actor” there? What would I import to be able to create one?
I’m trying to write an interop library for my canisters so I can use them in Dart/Flutter. If I can access the canister in JavaScript in a remote project, it’s trivial to expose it to Dart.
Is there something I need to do to make sure ic is available in a JavaScript file launched with Node? I’m currently getting an error in the @dfinity/agent npm library stating that global.ic is not defined.
Here’s my code:
import Agent from '@dfinity/agent';
import candid from '../../.dfx/local/canisters/credits/credits.did.js';
const actor = Agent.Actor.createActor(candid, { canisterId: '75hes-oqbaa-aaaaa-aaaaa-aaaaa-aaaaa-aaaaa-q' });
(async () => {
var v = await actor.getValue();
print(v);
})();
On the actor.getValue line, I get TypeError: Cannot read property 'agent' of undefined in /node_modules/@dfinity/agent/src/actor.js:35:25 which is the global.ic.agent line here:
Awesome, it’s working! I had to polyfill a couple more libraries that it was complaining about: fetch and crypto. I used node-fetch and node-webcrypto-ossl.
In addition to copying the createAgent function from the project you linked, here’s everything I needed:
import fetch from "node-fetch";
import { Crypto } from "node-webcrypto-ossl";
const { HttpAgent, IDL, Principal } = ic;
global.fetch = fetch;
global.crypto = new Crypto();
global.ic = { agent: createAgent(host), HttpAgent, IDL };
node-webcrypto-ossl’s readme says At this time this solution should be considered suitable for research and experimentation, further code and security review is needed before utilization in a production application. Other libraries, such as NfWebCrypto, say similar things.
Is it possible to do this securely at this time? Or am I trying to do something inherently insecure?