From 6266d6b701d13fff69dbaf64ea7ff5b0ca06b360 Mon Sep 17 00:00:00 2001 From: Akhilesh Thite Date: Thu, 14 Apr 2022 18:29:59 +0530 Subject: [PATCH 01/10] add dscan link in explore page --- explore.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/explore.md b/explore.md index 1f3c018..2bf1d82 100644 --- a/explore.md +++ b/explore.md @@ -8,6 +8,9 @@ Feel free to [submit a pull request](https://github.com/AgregoreWeb/website/) on - [Chat example](https://github.com/AgregoreWeb/agregore-chat-example) - [Drag and drop file upload example](https://github.com/AgregoreWeb/agregore-drag-and-drop) +### Extensions: +- [DScan: Decentralized QR code generator](https://chrome.google.com/webstore/detail/dscan-decentralized-qr-co/idpfgkgogjjgklefnkjdpghkifbjenap) + ### Blogs / Homepages - [Mauve's Blog](hyper://blog.mauve.moe/) From 8949aec9a533596636f64448a9a6b3ad072f4059 Mon Sep 17 00:00:00 2001 From: Akhilesh Thite Date: Wed, 30 Apr 2025 16:23:33 +0530 Subject: [PATCH 02/10] fix(p2p-editor): use raw file bytes and unique Hyperdrive keys for uploads --- docs/examples/p2pad/dweb.js | 126 ++++++++++++++++++++++++------------ 1 file changed, 85 insertions(+), 41 deletions(-) diff --git a/docs/examples/p2pad/dweb.js b/docs/examples/p2pad/dweb.js index c47e9c6..e01cf37 100644 --- a/docs/examples/p2pad/dweb.js +++ b/docs/examples/p2pad/dweb.js @@ -34,74 +34,112 @@ uploadButton.addEventListener('click', assembleCode); // Upload code to Dweb async function uploadFile(file) { const protocol = protocolSelect.value; + console.log(`[uploadFile] Uploading ${file.name}, protocol: ${protocol}`); - const formData = new FormData(); - - // Append file to the FormData - formData.append('file', file, file.name); - - - // Construct the URL based on the protocol - let url; if (protocol === 'hyper') { - const hyperdriveUrl = await generateHyperdriveKey('p2pad'); - url = `${hyperdriveUrl}`; + const hyperdriveUrl = await generateHyperdriveKey(); + const url = `${hyperdriveUrl}${encodeURIComponent(file.name)}`; + const cleanUrl = url.replace(/index\.html$/, ''); + console.log(`[uploadFile] Hyper URL: ${url}`); + + try { + const response = await fetch(url, { + method: 'PUT', + body: file, // Send raw file bytes + headers: { + 'Content-Type': file.type || 'text/html' + } + }); + + console.log(`[uploadFile] Response status: ${response.status}, ok: ${response.ok}`); + if (!response.ok) { + const errorText = await response.text(); + console.error(`[uploadFile] Error uploading ${file.name}: ${errorText}`); + addError(file.name, errorText); + return; + } + + addURL(cleanUrl); + } catch (error) { + console.error(`[uploadFile] Error uploading ${file.name}:`, error); + addError(file.name, error.message); + } finally { + showSpinner(false); + } } else { - url = `ipfs://bafyaabakaieac/`; - } - - // Perform the upload for each file - try { - const response = await fetch(url, { - method: 'PUT', - body: formData, - }); - - if (!response.ok) { - addError(file, await response.text()); + // IPFS upload with FormData + const formData = new FormData(); + console.log(`[uploadFile] Appending file for IPFS: ${file.name}`); + formData.append('file', file, file.name); + + const url = `ipfs://bafyaabakaieac/`; + console.log(`[uploadFile] IPFS URL: ${url}`); + + try { + const response = await fetch(url, { + method: 'PUT', + body: formData, + }); + + console.log(`[uploadFile] IPFS Response status: ${response.status}, ok: ${response.ok}`); + if (!response.ok) { + const errorText = await response.text(); + console.error(`[uploadFile] IPFS Error: ${errorText}`); + addError(file.name, errorText); + return; + } + + const locationHeader = response.headers.get('Location'); + console.log(`[uploadFile] IPFS Location header: ${locationHeader}`); + addURL(locationHeader); + } catch (error) { + console.error(`[uploadFile] Error uploading to IPFS:`, error); + addError(file.name, error.message); + } finally { + showSpinner(false); } - const urlResponse = protocol === 'hyper' ? response.url : response.headers.get('Location'); - addURL(urlResponse); - } catch (error) { - console.error(`Error uploading ${file}:`, error); - } finally { - showSpinner(false); } } +async function generateHyperdriveKey() { + // Generate a unique name using timestamp and random string + const timestamp = Date.now(); + const randomStr = Math.random().toString(36).substring(2, 8); + const uniqueName = `p2p-editor-${timestamp}-${randomStr}`; + console.log(`[generateHyperdriveKey] Generating key for name: ${uniqueName}`); - -async function generateHyperdriveKey(name) { try { - const response = await fetch(`hyper://localhost/?key=${name}`, { method: 'POST' }); + const response = await fetch(`hyper://localhost/?key=${encodeURIComponent(uniqueName)}`, { method: 'POST' }); if (!response.ok) { throw new Error(`Failed to generate Hyperdrive key: ${response.statusText}`); } - return await response.text(); // This returns the hyper:// URL + const hyperUrl = await response.text(); + console.log(`[generateHyperdriveKey] Hyperdrive URL: ${hyperUrl}`); + return hyperUrl; // Returns the hyper:// URL } catch (error) { - console.error('Error generating Hyperdrive key:', error); + console.error('[generateHyperdriveKey] Error generating Hyperdrive key:', error); throw error; } } - function addURL(url) { + console.log(`[addURL] Adding URL: ${url}`); const listItem = document.createElement('li'); const link = document.createElement('a'); link.href = url; link.textContent = url; const copyContainer = document.createElement('span'); - const copyIcon = '⊕' + const copyIcon = '⊕'; copyContainer.innerHTML = copyIcon; copyContainer.onclick = function() { navigator.clipboard.writeText(url).then(() => { - copyContainer.textContent = '☑'; + copyContainer.textContent = ' Copied!'; setTimeout(() => { copyContainer.innerHTML = copyIcon; }, 3000); }).catch(err => { - console.error('Error in copying text: ', err); + console.error('[addURL] Error in copying text: ', err); }); }; @@ -110,13 +148,14 @@ function addURL(url) { uploadListBox.appendChild(listItem); } - function addError(name, text) { - uploadListBox.innerHTML += `
  • Error in ${name}: ${text}
  • ` + console.log(`[addError] Error in ${name}: ${text}`); + uploadListBox.innerHTML += `
  • Error in ${name}: ${text}
  • `; } // The fetchFromDWeb function detects which protocol is used and fetches the content async function fetchFromDWeb(url) { + console.log(`[fetchFromDWeb] Fetching URL: ${url}`); if (!url) { alert("Please enter a CID or Name."); return; @@ -129,10 +168,11 @@ async function fetchFromDWeb(url) { try { const response = await fetch(url); + console.log(`[fetchFromDWeb] Response status: ${response.status}`); const data = await response.text(); parseAndDisplayData(data); } catch (error) { - console.error("Error fetching from DWeb:", error); + console.error("[fetchFromDWeb] Error fetching from DWeb:", error); alert("Failed to fetch from DWeb."); } } @@ -145,6 +185,7 @@ fetchButton.addEventListener('click', () => { // Parse the data and display it in the code editor function parseAndDisplayData(data) { + console.log(`[parseAndDisplayData] Parsing received data`); const parser = new DOMParser(); const doc = parser.parseFromString(data, 'text/html'); @@ -165,8 +206,11 @@ function parseAndDisplayData(data) { const htmlContent = doc.body.innerHTML; // Get the content inside the body tag without script/style tags // Displaying the content in respective textareas + console.log(`[parseAndDisplayData] Setting HTML: ${htmlContent.substring(0, 50)}...`); + console.log(`[parseAndDisplayData] Setting CSS: ${cssContent.substring(0, 50)}...`); + console.log(`[parseAndDisplayData] Setting JS: ${jsContent.substring(0, 50)}...`); $('#htmlCode').value = htmlContent; $('#cssCode').value = cssContent; $('#javascriptCode').value = jsContent; update(0); -} \ No newline at end of file +} From 6e61be0322db0c854c668cf32f9c31bcfd0c07e6 Mon Sep 17 00:00:00 2001 From: Akhilesh Thite Date: Wed, 30 Apr 2025 16:37:47 +0530 Subject: [PATCH 03/10] docs: add Galacteek browser and DP indexer, remove Brave, and reorder list --- explore.md | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/explore.md b/explore.md index e3df815..f8cbd96 100644 --- a/explore.md +++ b/explore.md @@ -10,11 +10,12 @@ Feel free to [submit a pull request](https://github.com/AgregoreWeb/website/) on - [Drag and Drop File Uploads](/docs/examples/drag-and-drop/) - [Theme Builder](/docs/examples/themebuilder) - [Pin Manager](https://agregoreweb.github.io/pin-manager/) for talking to IPFS pinning services -- [Sutty CMS, static site generator with dweb publishing](https://sutty.nl/en/) - [P2Pad Code Editor](/docs/examples/p2pad/) +- [Sutty CMS, static site generator with dweb publishing](https://sutty.nl/en/) - [Distributed Press Social Reader](//reader.distributed.press/) -- [LLM App Generator](/docs//examples/llm-appgen/) - [Distributed Press CLI](https://github.com/hyphacoop/distributed-press-cli/) +- [DWeb Explorer](https://explore.distributed.press/) +- [LLM App Generator](/docs//examples/llm-appgen/) - [LLM Chat Example](/docs/examples/llm-chat.html) - [LLM Tonal Lenses](/docs/examples/llm-lenses-chat/) - [Quick Code Snippet Generator](/docs/examples/quickcode.html) @@ -25,9 +26,6 @@ Feel free to [submit a pull request](https://github.com/AgregoreWeb/website/) on - [DScan: Own Your Identity, Own Your Data](https://chrome.google.com/webstore/detail/dscan-decentralized-qr-co/idpfgkgogjjgklefnkjdpghkifbjenap) -### Extensions: -- [DScan: Decentralized QR code generator](https://chrome.google.com/webstore/detail/dscan-decentralized-qr-co/idpfgkgogjjgklefnkjdpghkifbjenap) - ### Blogs / Homepages - [Mauve's Blog](//blog.mauve.moe) @@ -46,7 +44,8 @@ Feel free to [submit a pull request](https://github.com/AgregoreWeb/website/) on ### Other browsers: - [Peersky](https://peersky.p2plabs.xyz/) -- [IPFS in Brave](https://blog.ipfs.io/2021-01-21-how-we-put-ipfs-in-brave/) +- ~~[IPFS in Brave][(https://blog.ipfs.io/2021-01-21-how-we-put-ipfs-in-brave/)](https://github.com/brave/brave-browser/issues/37735)~~ +- [Galacteek](https://galacteek.gitlab.io/) - [Hybrid](https://github.com/HybridWare/hybrid-browser) --- From 22ab27075fce1f63bce45b1be9fb91a83a74b83f Mon Sep 17 00:00:00 2001 From: Akhilesh Thite Date: Wed, 30 Apr 2025 16:40:18 +0530 Subject: [PATCH 04/10] docs: improve readability --- explore.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/explore.md b/explore.md index f8cbd96..59bb865 100644 --- a/explore.md +++ b/explore.md @@ -44,7 +44,7 @@ Feel free to [submit a pull request](https://github.com/AgregoreWeb/website/) on ### Other browsers: - [Peersky](https://peersky.p2plabs.xyz/) -- ~~[IPFS in Brave][(https://blog.ipfs.io/2021-01-21-how-we-put-ipfs-in-brave/)](https://github.com/brave/brave-browser/issues/37735)~~ +- ~~[IPFS in Brave](https://github.com/brave/brave-browser/issues/37735)~~ - [Galacteek](https://galacteek.gitlab.io/) - [Hybrid](https://github.com/HybridWare/hybrid-browser) From 9ada9ee0bc08268892970d83407392ee368a672a Mon Sep 17 00:00:00 2001 From: Akhilesh Thite Date: Fri, 2 May 2025 22:26:13 -0700 Subject: [PATCH 05/10] Revert "docs: add Galacteek browser and DP indexer, remove Brave, and reorder list" This reverts commit 6e61be0322db0c854c668cf32f9c31bcfd0c07e6. --- explore.md | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/explore.md b/explore.md index 59bb865..b1a9bef 100644 --- a/explore.md +++ b/explore.md @@ -10,12 +10,11 @@ Feel free to [submit a pull request](https://github.com/AgregoreWeb/website/) on - [Drag and Drop File Uploads](/docs/examples/drag-and-drop/) - [Theme Builder](/docs/examples/themebuilder) - [Pin Manager](https://agregoreweb.github.io/pin-manager/) for talking to IPFS pinning services -- [P2Pad Code Editor](/docs/examples/p2pad/) - [Sutty CMS, static site generator with dweb publishing](https://sutty.nl/en/) +- [P2Pad Code Editor](/docs/examples/p2pad/) - [Distributed Press Social Reader](//reader.distributed.press/) -- [Distributed Press CLI](https://github.com/hyphacoop/distributed-press-cli/) -- [DWeb Explorer](https://explore.distributed.press/) - [LLM App Generator](/docs//examples/llm-appgen/) +- [Distributed Press CLI](https://github.com/hyphacoop/distributed-press-cli/) - [LLM Chat Example](/docs/examples/llm-chat.html) - [LLM Tonal Lenses](/docs/examples/llm-lenses-chat/) - [Quick Code Snippet Generator](/docs/examples/quickcode.html) @@ -26,6 +25,9 @@ Feel free to [submit a pull request](https://github.com/AgregoreWeb/website/) on - [DScan: Own Your Identity, Own Your Data](https://chrome.google.com/webstore/detail/dscan-decentralized-qr-co/idpfgkgogjjgklefnkjdpghkifbjenap) +### Extensions: +- [DScan: Decentralized QR code generator](https://chrome.google.com/webstore/detail/dscan-decentralized-qr-co/idpfgkgogjjgklefnkjdpghkifbjenap) + ### Blogs / Homepages - [Mauve's Blog](//blog.mauve.moe) @@ -44,7 +46,7 @@ Feel free to [submit a pull request](https://github.com/AgregoreWeb/website/) on ### Other browsers: - [Peersky](https://peersky.p2plabs.xyz/) -- ~~[IPFS in Brave](https://github.com/brave/brave-browser/issues/37735)~~ +- [IPFS in Brave](https://blog.ipfs.io/2021-01-21-how-we-put-ipfs-in-brave/) - [Galacteek](https://galacteek.gitlab.io/) - [Hybrid](https://github.com/HybridWare/hybrid-browser) From 98767d0a468fff76e2e5eb743f7c499c8f7009f3 Mon Sep 17 00:00:00 2001 From: Akhilesh Thite Date: Fri, 2 May 2025 22:28:33 -0700 Subject: [PATCH 06/10] docs: remove duplicate extension --- explore.md | 3 --- 1 file changed, 3 deletions(-) diff --git a/explore.md b/explore.md index b1a9bef..bbe481a 100644 --- a/explore.md +++ b/explore.md @@ -25,9 +25,6 @@ Feel free to [submit a pull request](https://github.com/AgregoreWeb/website/) on - [DScan: Own Your Identity, Own Your Data](https://chrome.google.com/webstore/detail/dscan-decentralized-qr-co/idpfgkgogjjgklefnkjdpghkifbjenap) -### Extensions: -- [DScan: Decentralized QR code generator](https://chrome.google.com/webstore/detail/dscan-decentralized-qr-co/idpfgkgogjjgklefnkjdpghkifbjenap) - ### Blogs / Homepages - [Mauve's Blog](//blog.mauve.moe) From ebaad713c43100aa9c5e1c8fd1b27eb4d858bb55 Mon Sep 17 00:00:00 2001 From: Akhilesh Thite Date: Sat, 3 May 2025 11:03:54 +0530 Subject: [PATCH 07/10] Revert "docs: Galacteek browser" Addressed in https://github.com/AgregoreWeb/website/pull/73 --- explore.md | 1 - 1 file changed, 1 deletion(-) diff --git a/explore.md b/explore.md index bbe481a..fc9f19f 100644 --- a/explore.md +++ b/explore.md @@ -44,7 +44,6 @@ Feel free to [submit a pull request](https://github.com/AgregoreWeb/website/) on - [Peersky](https://peersky.p2plabs.xyz/) - [IPFS in Brave](https://blog.ipfs.io/2021-01-21-how-we-put-ipfs-in-brave/) -- [Galacteek](https://galacteek.gitlab.io/) - [Hybrid](https://github.com/HybridWare/hybrid-browser) --- From 355f92ef3fdeb5f603e2aeea71c0e3ace605d8e7 Mon Sep 17 00:00:00 2001 From: Akhilesh Thite Date: Wed, 7 May 2025 01:37:49 -0700 Subject: [PATCH 08/10] feat: add title input for deriving unique file names --- docs/examples/p2pad/index.html | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/docs/examples/p2pad/index.html b/docs/examples/p2pad/index.html index df6b5dd..e06a534 100644 --- a/docs/examples/p2pad/index.html +++ b/docs/examples/p2pad/index.html @@ -27,20 +27,20 @@
    + - +
    - +
    - +
      From 1e31203565ff67af2f8045c1e529020ec40080ac Mon Sep 17 00:00:00 2001 From: Akhilesh Thite Date: Wed, 7 May 2025 01:41:03 -0700 Subject: [PATCH 09/10] feat: reuse single Hyperdrive and IPFS collection for publishing --- docs/examples/p2pad/dweb.js | 53 +++++++++++++++++++------------------ 1 file changed, 27 insertions(+), 26 deletions(-) diff --git a/docs/examples/p2pad/dweb.js b/docs/examples/p2pad/dweb.js index e01cf37..dcb4b42 100644 --- a/docs/examples/p2pad/dweb.js +++ b/docs/examples/p2pad/dweb.js @@ -1,8 +1,14 @@ import { update, showSpinner, basicCSS } from './codeEditor.js'; import { $, uploadButton, protocolSelect, fetchButton, fetchCidInput } from './common.js'; -// assemble code before uploading +// Assemble code before uploading export async function assembleCode() { + const title = document.getElementById("titleInput").value.trim(); + if (!title) { + alert("Please enter a title for your project."); + return; + } + // Display loading spinner showSpinner(true); @@ -22,7 +28,8 @@ export async function assembleCode() { // Convert the combined code into a Blob const blob = new Blob([combinedCode], { type: 'text/html' }); - const file = new File([blob], "index.html", { type: 'text/html' }); + const fileName = `${title.replace(/\s+/g, '-').toLowerCase()}.html`; + const file = new File([blob], fileName, { type: 'text/html' }); // Upload the file await uploadFile(file); @@ -37,9 +44,8 @@ async function uploadFile(file) { console.log(`[uploadFile] Uploading ${file.name}, protocol: ${protocol}`); if (protocol === 'hyper') { - const hyperdriveUrl = await generateHyperdriveKey(); + const hyperdriveUrl = await getOrCreateHyperdrive(); const url = `${hyperdriveUrl}${encodeURIComponent(file.name)}`; - const cleanUrl = url.replace(/index\.html$/, ''); console.log(`[uploadFile] Hyper URL: ${url}`); try { @@ -59,7 +65,7 @@ async function uploadFile(file) { return; } - addURL(cleanUrl); + addURL(url); } catch (error) { console.error(`[uploadFile] Error uploading ${file.name}:`, error); addError(file.name, error.message); @@ -101,25 +107,24 @@ async function uploadFile(file) { } } -async function generateHyperdriveKey() { - // Generate a unique name using timestamp and random string - const timestamp = Date.now(); - const randomStr = Math.random().toString(36).substring(2, 8); - const uniqueName = `p2p-editor-${timestamp}-${randomStr}`; - console.log(`[generateHyperdriveKey] Generating key for name: ${uniqueName}`); +let hyperdriveUrl = null; - try { - const response = await fetch(`hyper://localhost/?key=${encodeURIComponent(uniqueName)}`, { method: 'POST' }); - if (!response.ok) { - throw new Error(`Failed to generate Hyperdrive key: ${response.statusText}`); +async function getOrCreateHyperdrive() { + if (!hyperdriveUrl) { + const name = 'p2pad'; + try { + const response = await fetch(`hyper://localhost/?key=${encodeURIComponent(name)}`, { method: 'POST' }); + if (!response.ok) { + throw new Error(`Failed to generate Hyperdrive key: ${response.statusText}`); + } + hyperdriveUrl = await response.text(); + console.log(`[getOrCreateHyperdrive] Hyperdrive URL: ${hyperdriveUrl}`); + } catch (error) { + console.error('[getOrCreateHyperdrive] Error generating Hyperdrive key:', error); + throw error; } - const hyperUrl = await response.text(); - console.log(`[generateHyperdriveKey] Hyperdrive URL: ${hyperUrl}`); - return hyperUrl; // Returns the hyper:// URL - } catch (error) { - console.error('[generateHyperdriveKey] Error generating Hyperdrive key:', error); - throw error; } + return hyperdriveUrl; } function addURL(url) { @@ -191,11 +196,7 @@ function parseAndDisplayData(data) { // Extracting CSS const styleElements = Array.from(doc.querySelectorAll('style')); - - // Remove the first element (agregore theme CSS) - styleElements.shift(); - - // Now combine the CSS from the remaining