Skip to content
This repository was archived by the owner on Feb 12, 2024. It is now read-only.

Commit 91faec6

Browse files
feat: ipns publish example (#3207)
This is an example for the /examples/ folder for how to `ipfs.name.publish` in `js-ipfs` and have that ipns record pubsub'd over to a friendly neighborhood `go-ipfs` node to get recorded on the `DHT`. Co-authored-by: DougA <[email protected]>
1 parent 9c36cb8 commit 91faec6

File tree

18 files changed

+855
-73
lines changed

18 files changed

+855
-73
lines changed

Diff for: examples/browser-browserify/package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
"browserify": "^16.2.3",
1818
"concat-stream": "^2.0.0",
1919
"execa": "^4.0.0",
20-
"http-server": "^0.11.1",
20+
"http-server": "^0.12.3",
2121
"ipfs": "^0.49.1",
2222
"test-ipfs-example": "^2.0.3"
2323
},

Diff for: examples/browser-exchange-files/package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313
"devDependencies": {
1414
"browserify": "^16.2.3",
1515
"execa": "^4.0.0",
16-
"http-server": "^0.11.1",
16+
"http-server": "^0.12.3",
1717
"ipfs-http-client": "^46.0.1",
1818
"uint8arrays": "^1.1.0"
1919
},

Diff for: examples/browser-ipns-publish/.gitignore

+3
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
bundle.js
2+
.cache
3+
/node_modules/

Diff for: examples/browser-ipns-publish/README.md

+85
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
# Publish to IPNS from the browser
2+
3+
> Use ipns from the browser!
4+
5+
This example is a demo web application that allows you to connect to a go-IPFS node, and publish your IPNS record to the go-DHT network but using your js-ipfs private key. We'll start two IPFS nodes; one in the browser and one on a go-Server. We'll use `ipfs-http-client` to connect to the go-Node to ensure our pubsub messages are getting through, and confirm the IPNS record resolves on the go-Node. We're aiming for something like this:
6+
7+
```
8+
+-----------+ websocket +-----------+
9+
| +-------------------> |
10+
| js-ipfs | pubsub | go-ipfs |
11+
| <-------------------+ |
12+
+-----^-----+ +-----^-----+
13+
| |
14+
| IPFS in browser | HTTP API
15+
| |
16+
+-------------------------------------------------+
17+
| Browser |
18+
+-------------------------------------------------+
19+
| | | |
20+
| | | |
21+
| IPFS direct | | js-http-client |
22+
| a.k.a. ipfsNode | | a.k.a. ipfsAPI |
23+
| | | |
24+
+-------------------------------------------------+
25+
```
26+
27+
## 1. Get started
28+
29+
With Node.js and git installed, clone the repo and install the project dependencies:
30+
31+
```sh
32+
git clone https://github.com/ipfs/js-ipfs.git
33+
cd examples/browser-ipns-publish
34+
npm install # Installs browser-pubsub app dependencies
35+
```
36+
37+
Start the example application:
38+
39+
```sh
40+
npm start
41+
```
42+
43+
You should see something similar to the following in your terminal and the web app should now be available if you navigate to http://127.0.0.1:1234 using your browser:
44+
45+
```sh
46+
Starting up http-server, serving ./
47+
Available on:
48+
http://127.0.0.1:1234
49+
```
50+
51+
## 2. Start two IPFS nodes
52+
53+
The first node is the js-ipfs made in the browser and the demo does that for you.
54+
55+
The second is a go-ipfs node on a server. To get our IPNS record to the DHT, we'll need [a server running go-IPFS](https://blog.ipfs.io/22-run-ipfs-on-a-vps/) with the API enabled on port 5001.
56+
57+
Right now the easiest way to do this is to install and start a `go-ipfs` node.
58+
59+
### Install and start the Go IPFS node
60+
61+
Head over to https://dist.ipfs.io/#go-ipfs and hit the "Download go-ipfs" button. Extract the archive and read the instructions to install.
62+
63+
After installation:
64+
65+
```sh
66+
ipfs init
67+
# Configure CORS to allow ipfs-http-client to access this IPFS node
68+
ipfs config --json API.HTTPHeaders.Access-Control-Allow-Origin "[\"*\"]"
69+
# Configure go-ipfs to listen on a websocket address
70+
npx json -I -f ~/.ipfs/config -e "this.Addresses.Swarm.push('/ip4/127.0.0.1/tcp/4003/ws')"
71+
# Start the IPFS node, enabling pubsub and IPNS over pubsub
72+
ipfs daemon --enable-pubsub-experiment --enable-namesys-pubsub
73+
```
74+
75+
## 3. Open the demo in a browser and connect to the go-node
76+
77+
Now, open up the demo in a browser window.
78+
79+
In the "CONNECT TO GO-IPFS VIA API MULTIADDRESS" field enter `/ip4/YourServerIP/tcp/5001` (where `YourSeverIP` is your server's IP address or use `/dns4/yourdomain.com/tcp/5001`) and click connect. Once it connects, put your go-IPFS websocket address in the next field `/dns4/yourdomain.com/tcp/4003/wss/p2p/QmPeerIDHash` and hit the second "Connect" button.
80+
81+
This connects the API to the go-Node and connects your js-IPFS node via websocket to the go-IPFS node so pubsub will work.
82+
83+
You can choose whether to publish this record under the PeerId of the node that is running in the browser ('self') or choose to add a custom key to the IPFS keychain and publish under that instead. Either should work.
84+
85+
Finally, enter `/ipfs/QmSomeHash` as the content you want to publish to IPNS. You should see the messages sent from the browser to the server appear in the logs below, ending with "Success, resolved" if it all worked.

Diff for: examples/browser-ipns-publish/index.html

+209
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,209 @@
1+
<!DOCTYPE html>
2+
<html>
3+
<head>
4+
<title>Publish to IPNS from the browser</title>
5+
<link
6+
rel="stylesheet"
7+
href="https://unpkg.com/[email protected]/css/tachyons.min.css"
8+
/>
9+
<link rel="stylesheet" href="https://unpkg.com/[email protected]/ipfs.css" />
10+
</head>
11+
<body class="sans-serif">
12+
<header class="pv3 ph2 ph3-l bg-navy cf mb4">
13+
<a href="https://ipfs.io/" title="ipfs.io">
14+
<img
15+
src="https://ipfs.io/images/ipfs-logo.svg"
16+
class="v-mid"
17+
style="height: 50px;"
18+
/>
19+
</a>
20+
<h1 class="aqua fw2 montserrat dib ma0 pv2 ph1 v-mid fr f3 lh-copy">
21+
IPNS Publish from JS to Go Peer
22+
</h1>
23+
</header>
24+
<div class="ph3 mb3">
25+
<div class="fw2 tracked ttu f6 teal-muted mb2">
26+
IPNS PUBLISH SET-UP STEPS
27+
</div>
28+
<main class="page" data-v-4f5abb4a="">
29+
<div class="theme-default-content content__default" data-v-4f5abb4a="">
30+
<div
31+
class="custom-block callout"
32+
style="font-size: 0.75em; width: 75%; margin: 1em;"
33+
>
34+
<p>
35+
Code repo for this demo
36+
<a
37+
href="https://github.com/js-ipfs/examples/browser-ipns-publish/"
38+
>on Github</a
39+
>
40+
</p>
41+
<p>
42+
The idea is to publish from js-ipfs so you control your own
43+
private keys, but publish to go-ipfs to benefit from the DHT.
44+
Since the DHT in js-ipfs is still in the experimental phase, we need to use PubSub
45+
and have a go-ipfs node subscribed to that PubSub to get our IPNS
46+
record onto the DHT. In order to use PubSub between these two
47+
nodes, you'll need a websocket to connect them.
48+
</p>
49+
<div>
50+
To make this demo work, you're going to need:
51+
<ul>
52+
<li style="list-style-type: none;">
53+
<b>1. Access to a go-ipfs node and it's API</b>, a-la
54+
<pre>/dns4/domain.com/tcp/5001</pre>
55+
</li>
56+
<li>
57+
This is how the demo talks to the server, to ensure things
58+
like:
59+
</li>
60+
<ul>
61+
<li>
62+
A) pubsub is enabled, { EXPERIMENTAL: { ipnsPubsub: true } }
63+
and --enable-pubsub-experiment
64+
</li>
65+
<li>
66+
B) go-ipfs is connected to the js-ipfs node in the browser,
67+
via node.swarm.peers(),
68+
</li>
69+
<li>
70+
C) the pubsub messages are getting through to the go node,
71+
via node.pubsub.subscribe().
72+
</li>
73+
</ul>
74+
</ul>
75+
<ul>
76+
<li style="list-style-type: none;">
77+
<b>2. Access to a go-ipfs Websocket port</b>, a-la
78+
<pre>/dns4/domain.com/tcp/4003/wss/p2p/QmTheDomainPeerId</pre>
79+
</li>
80+
<li>
81+
Since we need PubSub for IPNS to reach the go-IPFS node (and
82+
further replicate through the go-DHT network) we need to
83+
connect our pubsub enabled JS-IPFS node in the browser to our
84+
go-IPFS node on the server. The way we connect is via
85+
Websocket. See
86+
<a
87+
href="https://github.com/ipfs/js-ipfs/tree/master/packages/ipfs-http-client/examples/browser-pubsub"
88+
>this example</a
89+
>
90+
for reference.
91+
</li>
92+
</ul>
93+
<p>
94+
Once we can talk to go-IPFS and we're connected via Websocket,
95+
then we can publish in our browser node, have the pubsub push it
96+
to the go-IPFS server, and then check with the server that it's
97+
confirmed as published. Once it's on the go-IPFS node it should
98+
replicate throughout the rest of the DHT amongst the go-Nodes.
99+
</p>
100+
</div>
101+
</div>
102+
</div>
103+
</main>
104+
</div>
105+
<div class="ph3 mb3">
106+
<div class="fw2 tracked ttu f6 teal-muted mb2">
107+
1. Connect to Go-IPFS via API MultiAddress
108+
</div>
109+
<input
110+
id="api-url"
111+
class="dib w-50 ph1 pv2 monospace input-reset ba b--black-20 border-box"
112+
placeholder="/dns4/yourdomain.com/tcp/5001"
113+
disabled="disabled"
114+
/>
115+
<button
116+
id="node-connect"
117+
class="dib ph3 pv2 input-reset ba b--black-20 border-box"
118+
disabled="disabled"
119+
>
120+
Connect
121+
</button>
122+
</div>
123+
<div class="ph3 mb3">
124+
<div class="fw2 tracked ttu f6 teal-muted mb2">
125+
2. Connect to Go-IPFS via Websocket MultiAddress (for PubSub to work)
126+
</div>
127+
<input
128+
id="peer-addr"
129+
class="dib w-50 ph1 pv2 monospace input-reset ba b--black-20 border-box"
130+
placeholder="/dns4/yourdomain.com/tcp/4003/wss/p2p/QmTheirServerPeerId"
131+
disabled="disabled"
132+
/>
133+
<button
134+
id="peer-connect"
135+
class="dib ph3 pv2 input-reset ba b--black-20 border-box"
136+
disabled="disabled"
137+
>
138+
Connect
139+
</button>
140+
</div>
141+
142+
<div class="ph3 mb3">
143+
<div class="fw2 tracked ttu f6 teal-muted mb2">
144+
3. Choose a key:
145+
</div>
146+
<form>
147+
<ul style="list-style-type: none;">
148+
<li>
149+
<input type="radio" id="male" name="keyName" value="self" checked />
150+
<label for="male"
151+
>Self (the
152+
<a
153+
href="https://github.com/ipfs/js-ipfs/blob/master/docs/core-api/KEY.md#ipfskeylistoptions"
154+
target="_blank"
155+
>PeerId of the runing node</a
156+
>)</label
157+
><br />
158+
</li>
159+
<li>
160+
<input type="radio" id="female" name="keyName" value="custom-key" disabled="disabled" />
161+
<label for="female"
162+
>Custom Key (<a
163+
href="https://github.com/ipfs/js-ipfs/blob/master/docs/core-api/KEY.md#ipfskeyimportname-pem-password-options"
164+
target="_blank"
165+
>imported</a
166+
>
167+
onto the keychain) [waiting for <a href="https://github.com/ipfs/go-ipfs/issues/6360">#6360</a> to work]</label
168+
><br />
169+
</li>
170+
</ul>
171+
</form>
172+
</div>
173+
<div class="ph3 mb3">
174+
<div class="fw2 tracked ttu f6 teal-muted mb2">
175+
4. IPFS hash to publish
176+
</div>
177+
<input
178+
id="topic"
179+
class="dib w-50 ph1 pv2 monospace input-reset ba b--black-20 border-box"
180+
disabled="disabled"
181+
/>
182+
<button
183+
id="publish"
184+
class="dib ph3 pv2 input-reset ba b--black-20 border-box"
185+
disabled="disabled"
186+
>
187+
Publish to IPNS
188+
</button>
189+
</div>
190+
191+
<div class="ph3 mb3">
192+
<div class="fw2 tracked ttu f6 teal-muted mb2">Browser Console</div>
193+
<div
194+
id="console"
195+
class="f7 db w-100 ph1 pv2 monospace input-reset ba b--black-20 border-box overflow-scroll"
196+
style="height: 300px;"
197+
></div>
198+
</div>
199+
<div class="ph3 mb3">
200+
<div class="fw2 tracked ttu f6 teal-muted mb2">Server Console</div>
201+
<div
202+
id="server-console"
203+
class="f7 db w-100 ph1 pv2 monospace input-reset ba b--black-20 border-box overflow-scroll"
204+
style="height: 300px;"
205+
></div>
206+
</div>
207+
<script src="index.js"></script>
208+
</body>
209+
</html>

0 commit comments

Comments
 (0)