Where communities thrive


  • Join over 1.5M+ people
  • Join over 100K+ communities
  • Free without limits
  • Create your own community
People
Repo info
Activity
  • Jan 16 08:22
    davay42 updated the wiki
  • Jan 16 08:20
    davay42 updated the wiki
  • Jan 16 06:22
    Orimay opened #1191
  • Jan 16 05:22

    amark on master

    Update README.md (#1181) (compare)

  • Jan 16 05:22
    amark closed #1181
  • Jan 16 05:22
    amark commented #1181
  • Jan 15 00:46
    mbround18 commented #404
  • Jan 15 00:39
    mbround18 commented #404
  • Jan 15 00:38
    mbround18 commented #404
  • Jan 15 00:38
    mbround18 commented #404
  • Jan 15 00:38
    mbround18 commented #404
  • Jan 15 00:29
    mbround18 commented #404
  • Jan 14 23:39
    Orimay synchronize #1189
  • Jan 14 23:36
    Orimay synchronize #1189
  • Jan 14 23:35
    Orimay synchronize #1189
  • Jan 14 14:13
    shemeshg edited #1190
  • Jan 14 12:55
    shemeshg opened #1190
  • Jan 14 12:54
    soulsam480 commented #1174
  • Jan 14 12:51
    shemeshg closed #1188
  • Jan 14 03:39
    draeder updated the wiki
mimiza
@mimiza
@amark if it is possible I want it to be fixed soon, but it's up to you to arrange your time. There are certify unit tests and some bus delayed for weeks now. I just want to finish them.
libensveto
@libensveto_twitter
@amark myself mainly, they get abit uptight if you do it in the wrong channel or start asking for help
Oscar Hilton
@oscarhilton
Major breakthrough in my understanding of GUN! Thank you everyone to helped me out!
@amark Konva is a canvas library that makes developing UIs in the canvas super simple! :)
mochic
@mochic
Hey so I’ve made a lot of progress since my last question. I have each gun instance listening to nodes and waiting for changes on certain nodes but I’m worried about the network being flooded with malicious “put” operations, making it hard to get data we actually want to see. I suppose I could maintain a blacklist for each client but I feel like that might spiral out of control since creating a new user is so easy that the blacklist would become untenable in size even via a complex implementation. Any suggestions? Is there any clever way for me to embed metadata in property names to use lex to filter out data from “bad” sources or is implementing an adapter more helpful for me here?
Barłomiej Bąk
@dweorh_twitter

hey guys, I have a pretty weird issue with .map()

gun.get('dict').map((data, key) => {
  if (data == 1) 
    return { data, key, status: 1}
else 
  return {data, key, status: 2}
}).once({ data, key, status } => {
  console.log(data, key, status)
})

that's just an example, thing is that pretty often .map() does not call .once(). Any idea why?

libensveto
@libensveto_twitter
Mark Nadal
@amark
@libensveto_twitter :+1:
@oscarhilton (?)
@mochic Iris' Web of Trust is what fixes this. Don't worry tho, launch your app first, do not over-engineer it, you can integrate Iris and stuff later.
@dweorh_twitter hmm, there are minimal tests for filter and transform functions in map. if you just do map().once((data,key) => { if(data === 1){ ... are there any issues?
@libensveto_twitter w0000 nice homepage!!! Clicking "start" didn't do anything tho
1 reply
libensveto
@libensveto_twitter
@amark yep havnt linked it up yet
Ronald Prato
@Ronald-Prato
Hey there! i've been reading the docs all day and i'm still having a question about delete data. What if i have a medium-deeply nested schema? if i set null to a node which have other relationships those get deleted as well ?
Wasis Haryo Sasoko
@yokowasis
@Ronald-Prato no.
kristof de spiegeleer
@despiegk
trying to figure out how to use gun with typescript, but the examples I found don't work, anyone an idea, would be great
deathg0d
@deathg0d
@amark Is there a way to log get requests on a node.js gun server?
yash deore
@yash-deore
How long does a gun js server hold on to data .
Asking because I made a chat app but some hours later it did not show the previous messages .
simjnd
@simjnd:matrix.org
[m]
Did you have a relay node set up or did you just use the browser's local storage?
mossmanpete
@mossmanpete
has anyone combined RxJS with gun?
Adam
@adam-12:matrix.org
[m]
@yash-deore i think the one click heroku peers delete data every 15 mins
rococtz
@rococtz:matrix.org
[m]
@yash-deore: if you are using some community gun relay (or even yours) that happen to be deployed on heroku free tier, the storage will be wiped after some minutes of inactivity. If you are using some real production environment it will be stored for ever.
@mossmanpete RxJS with Gun is a really good idea since they are both working with streams, definitely doable
Mark Nadal
@amark
@Ronald-Prato @despiegk @yash-deore @simjnd:matrix.org 👋👋
@rococtz:matrix.org 👏
@adam-12:matrix.org 👏
@simjnd:matrix.org 👏
@despiegk very few people seem to know how to fix typescript 😥 could someone on discord tag the typescript role and tell them to move here?
Mark Nadal
@amark
@deathg0d not an ways flag, but could add an adapter gun.on('in', cb
Tho it may need to be wired correctly, I need to update those docs...
Adam
@adam-12:matrix.org
[m]
I wonder if just using dts-gen to generate new typescript definition files would be better than what we have now.
yash deore
@yash-deore
@rococtz:matrix.org @adam-12:matrix.org @amark Thanks a lot for your anticipation guys 😀.
Devin Santamaria
@webprismdevin

hey amazing ppl - I'm building a nextjs app, and getting the following err thrown when using getServerSideProps - interestingly, neither page is using any gun functionality.

ERROR    Error: Cannot find module './lib/text-encoding'
Require stack:
- /var/task/node_modules/gun/sea.js

has anyone run into this, or is a next/gun wizard who'd be willing to take a peak at my code?

deathg0d
@deathg0d

@amark so the problem seems to be docker. My setup was:

ufw firewall
    - docker-compose
        - nginx proxy manager docker container
        - gundb node.js docker container

I could not debug the issue at all. All realtime updates are fine but unable to receive old data from the client side. I put logs on the node.js server to make sure it does have the data and it does. Connections also look fine. I have no idea what's wrong. It feels like when I spin up the docker instance and connect remote clients to it, the clients connect to a different gun instance that has no record of old file, which is so weird.

I changed the setup to:

ufw firewall
    - docker-compose 
       - nginx proxy manager docker container
    - gundb node.js run using pm2 instead of inside a docker container

And now the issue seems to be solved. I have some other pressing tasks right now so cannot really play around more for the time being, but it would be great if I could solve this using the docker container (docker compose). By doing this I could avoid node dependencies on the host machine. It would also be easier to maintain the server.

Mark Nadal
@amark
@webprismdevin look for any import or require statements of gun in your project (?)
@deathg0d wow that seems obscure, I can't believe you figured it out. Is it because Docker routes to a different container? I'm sure there is a way to force "sticky" sessions cause websockets in general need this.
MaciejDot
@MaciejDot
Hey, there seem to be problem with: https://gun-manhattan.herokuapp.com/gun . I remember there was list of community /fallback gun servers do you know where i can find them?
Mark Nadal
@amark
@MaciejDot may be end-of-month it only has so many hours per month it can run. https://github.com/amark/gun/wiki/volunteer.dht yipes, I need to get docs & Secure Render finished so I can get on AXE again (which will automatically choose peers for you)
MaciejDot
@MaciejDot
@amark thanks a lot for help
MaciejDot
@MaciejDot

@despiegk i had the same problem i wrote some proxy types but its bit hacky and i dont use all functions from api so i didnt need full interface also i restricted their usage to end on first on() or once()

import Gun, { SEA } from "gun";
import 'gun/axe'
import 'gun/sea'
import { IGunConstructorOptions } from "gun/types/options";
import { AckCallback } from "gun/types/types";

type AuthArgs = [username: string, password: string, callback: (data: { err?: string }) => any] | [ pair :SEAPair, callback: (data: { err?: string }) => any]

export interface GunUser<T> {
    is?: undefined
    recall: (opt?: { sessionStorage: typeof sessionStorage }) => GunUser<T> |AuthenticatedGunUser<T>
    auth: (...t: AuthArgs) => GunUser<T> |AuthenticatedGunUser<T> 
    create: (...t: AuthArgs) => GunUser<T> |AuthenticatedGunUser<T> 
}


export interface AuthenticatedGunUser<T >{
    is: {
        alias: string | SEAPair
        epub: string
        pub: string
    }
    get: <TKey extends keyof T>(name: TKey) => AuthenticatedGunUserTree<T, TKey> & Promise<T[TKey]>
    leave: () => void
}

type AuthenticatedGunUserTree<T  , TKey extends keyof T> = AuthenticatedGunUser<T[TKey]> & GunTree<T,TKey>;

interface GunGet<T> {
    get: <TKey extends keyof T>(name: TKey) =>  GunTree<T ,TKey> & GunGet<T[TKey]> &Promise<T[TKey]>
}

type GunTree<T  , TKey extends keyof T> = {
    on: (callback:(state:T[TKey], key: TKey) => any) => { off: ()=> void }
    once: (callback: (state:T[TKey], key: TKey) => any) => void
    put: (state: T[TKey], callback?: AckCallback, options ?: {opt ?: { cert ?: string}} ) => void,
    set: (state: T[TKey]) => void,
    map: (match?: any) => AuthenticatedGunUserTree<T[TKey], keyof T[TKey]>
}


export function isUserAuthenticated  <T>(user : GunUser<T> |AuthenticatedGunUser<T>): user is AuthenticatedGunUser<T>{
    return !!user.is
}


interface GunDefinition {
    user: <T>() => GunUser<T> | AuthenticatedGunUser<T>,
    get: <T,TKey extends keyof T>(name: TKey) =>  GunTree<T ,TKey> & GunGet<T[TKey]> &Promise<T[TKey]>,
    on: (eventName: 'auth', callback: () => any) => { off: ()=> void },
}

const TypedGun = Gun as any as {
    (options?: string | string[] | IGunConstructorOptions): GunDefinition;
    new (options?: string | string[] | IGunConstructorOptions): GunDefinition;
}

export interface SEAPair{
    epriv: string
    epub: string
    priv: string
    pub: string
}


type Authority = SEAPair

export const TypedSEA = SEA as any as {
    secret: (epubKey: string, pair: SEAPair) => Promise<string>
    pair: () => Promise<SEAPair>
    sign: (data:any, pair: SEAPair) => Promise<string>
    verify: <T>(data: string, pair: SEAPair | string) => Promise<T | undefined>
    encrypt: (data:any, pair: SEAPair | string) => Promise<string>
    decrypt: <T>(data:string, pair: SEAPair | string) => Promise<T| undefined>
    certify: (user : string | string[]| {pub:string} | {pub:string}[], policies: any, pair: Authority, callback: (cert:string) => any, opt?: { blacklist?: string, expiry?:number }) => Promise<string>
}

just use TypedGun or TypedSEA

awaisnazir21
@awaisnazir21

@amark. Please implement this Forum as multiple threads initiated by each user, not a single thread currently. It is just a mess. Shift this Forum to reddit, and leave gitter?

@amark how can I change the username or alias for gun.user()?

@amark. I want to implement state management on the Clent-side using gundb. I want to expose only a subset of nodes e.g. gun.get("sessionid") on Client-side. I searched a lot, but still have doubts what if client-side hacking may access full gun graph network using XSS/code-injection. What security measures should I take? Is including SEA library enough security measure?

@amark. I am implementing gundb for a production grade app.

shecky2000
@shecky2000
First post. Been stuck on reproducing the basic to-do list example on my desktop. Initialized the http server at local host and ran the following code. The list doesn't update or really do anything. Understand this is extremely basic, but I've been stuck for days now. Thanks!

// Clear out localstorage to give Gun a fresh start on every load
localStorage.clear()

// Import Gun as a dependency
import Gun from 'gun'

/
var gun = Gun();
/

const server = require('http').createServer().listen(8080);
const gun = Gun({web: server});

var items = gun.get('items');

$('form').on('submit', function(e){
e.preventDefault();
items.set($('input').val());
$('input').val("");
})

items.map().on(function(item, id){
var li = $('#' + id).get(0) || $('<li>').attr('id', id).appendTo('ul');
if(item){
$(li).text(item);
} else {
$(li).hide();
}
})

Barłomiej Bąk
@dweorh_twitter
@shecky2000 it seems you messed up browser and server side there
you can setup your own super peer using nodejs, but for now you can use a public server
so what you need to do is
const gun = Gun( / settings /)
and you are good to go
5 replies
remember that public servers are used by many other developers and reset data every 15 min or so
Magnus Furcifer
@magnusfurcifer_twitter

Hi,
Sorry if this is a silly question, but I've been going over the docs today and I don't quite understand conceptually how the scopes work. So I think I get how user contexts work with storing data like in the following snippet:
$('#said').on('submit', function(e){
e.preventDefault();
if(!user.is){ return }
user.get('said').set($('#say').val());
$('#say').val("");
});

where the get/set/map methods apply to that users space, but if any endpoint can set data into the global space doesn't that mean that the global data set can be flooded? or is there some logic in the relay servers that I'm not understanding that prevents arbitrary data from being ingested and stored?

If I created an instance of gun with a public peer, is there anything stopping me just smashing it with data?
sua yoo
@SuaYoo

thoughts on how i would achieve key pair rotation for users created with user.create? reading the docs, it seems that gun users are essentially key pairs generated with SEA.pair(). does this mean i need to keep my own way of mapping usernames/alias to a pair, something like:

SEA.pair(({pair}) => {
  gun.get('users').
    ('@some_username').get('activePublicKey').put(pair.pub)

  // use `.activePublicKey` to encrypt, certify, etc.
})

or will gun.user().create(oldUsername, oldPaassphrase) automatically update the keys? (nope that would return a "user already exists" error.)

Barłomiej Bąk
@dweorh_twitter
@SuaYoo I'm not sure what are you trying to achieve, but in general user is identified by SEA keys(), you should keep them secret, except for the public key. You can use them for encrytpion, but it's not a must, you can generate another pair of keys for encryption purposes. You can use user's keys for authentication instead of login/password. The advantage of using keys for authentication is that it does not require lookup which means it's faster than login/password way
1 reply
Barłomiej Bąk
@dweorh_twitter

@amark hey Mark, I guess I know why I had issue with missing data in .map().on(). It seem that 'on' cannot be async like

gun.get('docs').map().on(async data => { ... })

Maybe I'm wrong, but since I removed async from my code I have better results

rococtz
@rococtz:matrix.org
[m]
@magnusfurcifer_twitter: First of all, the global space should not be used because anyone can change it or even delete it. All data must be stored in user nodes (because only that particular user can change the data by default and nobody else) or using Content Addressing (nobody can change it, not even the creator).
Second of all, if someone decides to dump a lot of data in your network, the only problem is that you will end-up storing it for them and nothing else. The apps you build will not care about that data and they won't download it on their clients. If you still want to restrict write access to the network based on some rules, you can have a loot at https://github.com/zrrrzzt/bullet-catcher but I haven't used it myself, I only know of it. The problem is that it goes against the Gun philosophy on long term where everybody should be able to donate their relays to the network and we all use and enjoy the network together (with the purpose of better redundancy, wider distribution around the world and at lower costs)
1 reply
Mark Nadal
@amark
@despiegk :clap: @MaciejDot ! Can you contribute that to the Type Definitions or ... ANYONE, literally ANYONE, help edit this page? https://github.com/amark/gun/wiki/TypeScript
@awaisnazir21 :) :wave: . Sorry, :( that makes it hard for me to answer people versus a thread. I'm more than happy for the community to use a forum, but if a question fallsback to me... it needs to be accessible for me to process. :/
I think all you have to do is gun.get('@newAliasYouWant').set(user) (where user is logged in)
XSS is sadly every app owner's responsibility to handle, tho I think I figured out a new way to fix this, and hope to be demoing a prototype soon. The Iris app does do a local-only GUN peer for indexing tho, by local = GUN(); gun = GUN(peers);. Does this help?
Congrats!! How many active users does your app currently have!?
@shecky2000 a few days! Oh noooo! THat's not good, the rule is 5min!! (partly cause sometimes it takes a day to get a reply). :clap: @dweorh_twitter was fast tho! Were you able to get it fixed? Seems like it. Remember, browsers still require :( :( bootstrapping peers to make WebRTC connections or sync. Tho we're working with browsers... (they're so slow) to maybe fix this in the future. NodeJS is able to access UDP multicast tho, so its more powerful than browsers.
@magnusfurcifer_twitter :wave: . :clap: :clap: @rococtz:matrix.org well said! Also: User space only allows the user to write to it. Public space can be written to by anyone, yes. If you're worried about that, just don't use the public space - that's fine. But its an important feature for some apps. We'll be building DDoS protection and stuff into AXE, but not there yet (the real 60 million users is DDoSing things enough, that I'm trying to scale up for, not even bots!).
@SuaYoo :clap: @dweorh_twitter tho yeah, Iris plans to enable key rotation management in the future, but even it (probably the most advanced app on this stuff so far) hasn't built it yet either. So key rotation is important, but I haven't seen it demoed yet.
@dweorh_twitter hmmm. Any JS function should be allowed to be async, this would be very mysterious if true. Can you replicate?