Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

NodeJS: Creating a tree from a string for http routing

I am trying to create a tree like radix tree for http routing

My code:

interface Node {
  nodes?: Record<string, Node>
  methods?: Record<string, () => unknown>
}

class Tree {
  root: Node

  constructor() {
    this.root = {}
  }

  insert(path: string, method: string, handler: () => unknown): void {
    let node = this.root

    path.split('/').forEach((path: string): void => {
      path = path === '' ? '/' : path

      node.nodes = node.nodes ?? {}

      const child = node.nodes[path] ?? {}

      node.nodes[path] = child

      node = child
    })

    node.methods = node.methods ?? {}

    if (!node.methods[method]) {
      node.methods[method] = handler
    }
  }
}

const tree = new Tree()

tree.insert('/users', 'GET', (): string => {
  return 'users get handler'
})
tree.insert('/posts', 'GET', (): string => {
  return 'posts get handler'
})
tree.insert('/profile', 'GET', (): string => {
  return 'profile get handler'
})
tree.insert('/profile/posts', 'GET', (): string => {
  return 'profile posts get handler'
})
tree.insert('/profile/friends', 'GET', (): string => {
  return 'profile friends get handler'
})

console.log(
  JSON.stringify(tree),
)

Expected result:

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

{
  root: {
    nodes: {
      "/": {
        nodes: {
          users: {
            methods: {
              GET: handler,
            },
          },
          posts: {
            methods: {
              GET: handler,
            },
          },
          profile: {
            methods: {
              GET: handler,
            },
            nodes: {
              posts: {
                methods: {
                  GET: handler,
                },
              },
              friends: {
                methods: {
                  GET: handler,
                },
              },
            },
          },
        },
      },
    },
  },
}

I would like to replace the root variable with nodes in the Tree class:

class Tree {
  nodes: Record<string, Node>
}

To get the desired result:

{
  nodes: {
    "/": {
      nodes: {
        users: {
          methods: {
            GET: handler,
          },
        },
        posts: {
          methods: {
            GET: handler,
          },
        },
        profile: {
          methods: {
            GET: handler,
          },
          nodes: {
            posts: {
              methods: {
                GET: handler,
              },
            },
            friends: {
              methods: {
                GET: handler,
              },
            },
          },
        },
      },
    },
  },
}

I tried several times to implement what I wanted, but in the end I got confused with my own code…

PS: Thank you all in advance for your answers 🙂

>Solution :

To achieve that your class works with a nodes member instead of root, you only need to change the first statement in your insert method.

Replace:

    let node = this.root

with:

    let node = { nodes: this.nodes };
Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading