ioredis icon indicating copy to clipboard operation
ioredis copied to clipboard

No way to instantiate with url scheme with object parameter

Open wraithgar opened this issue 5 years ago • 4 comments

When instantiating ioredis you can either pass in a string or an object, the string can be a redis url (i.e. redis://localhost:5379 but there is no way to pass in a url like that when using the object form of instantiation. It would be nice to either have the existing host param recognize urls, or add an explicit url parameter so that one could instantiate ioredis with other options (like keyPrefix) and also pass in a redis url for the server to connect to.

wraithgar avatar Mar 19 '20 16:03 wraithgar

Also noticing this. I'm using ioredis directly using the URL like:

redis://localhost:6379/0

Now I've just updated apollo-server-cache-redis they're only using the object param and I can't re-use the same ENV var without some splitting magic. Originally I was trying path as the first param is called path but realised they're not the same in this case as I get errors.

For now I'll split the args into multiple env vars but it was a little confusing

intellix avatar Sep 07 '20 23:09 intellix

For anyone wanting to work around this for now, something like this should help:

import Redis from 'ioredis'

function createRedisClient (uri: string, options?: Redis.RedisOptions): Redis.Redis {
  const parsed = new URL(uri)

  if (parsed.protocol !== 'redis') {
    throw new Error(`Unknown Redis protocol: ${parsed.protocol}`)
  }

  return new Redis({
    port: parsed.port === '' ? undefined : Number(parsed.port),
    host: parsed.hostname,
    username: parsed.username === '' ? undefined : parsed.username,
    password: parsed.password === '' ? undefined : parsed.password,
    ...options
  })
}

edit: actually what I posted above already works with the default constructor, at least as of version 4.27.11 🤦‍♂️

LinusU avatar Oct 13 '21 11:10 LinusU

It's ridiculous that this isn't supported yet.

If you're afraid of such configs:

{
  url: 'redis://:password@host:1234',
  host: 'foobar',
  port: 5678
}

and your only question is "OMG I do not understand what the actual host and port would be??!!", then, I guess, you should do the very same thing that all other DB connection libraries did: prioritize the url param and write about that in the docs.

So the url param should overwrite everything else. Super simple.

andrew-sol avatar Jun 01 '22 13:06 andrew-sol

Is a URL parameter even still an option with version 5.x.x? The RedisOptions no longer includes string as a typescript type.

hunkydoryrepair avatar Aug 23 '23 18:08 hunkydoryrepair