jaredwray / cache-manager

Cache module for Node.JS
MIT License
1.4k stars 152 forks source link

Map object is not stored #680

Closed alko89 closed 2 months ago

alko89 commented 2 months ago

Describe the bug

When trying to store an object that contains a Map, it's being stored as {"_constructor-name_":"Map"} instead of the actual value.

How To Reproduce (best to provide workable code or tests!)

import { caching } from 'cache-manager';
import { redisInsStore } from 'cache-manager-ioredis-yet';
import { Redis } from 'ioredis';

(async () => {
  const redis = new Redis('redis://localhost:6379');
  const cache = await caching(redisInsStore(redis));

  const map = new Map();
  map.set('foo', 'bar');
  map.set('baz', 'qux');
  const data = {
    foo: 'bar',
    map: map 
  };

  // Set a value
  await cache.set('data', data);

  // Get a value
  const value = await cache.get('data');
  console.log(value); // Prints out: { foo: 'bar', map: Map {} }
})().then().catch();

image

zph commented 2 months ago

I just saw an error about a Map on another cache-manager plugin today and if default serialization is JSON.stringify, there's additional work needed to serialize transparently: https://github.com/rolandstarke/node-cache-manager-fs-hash/issues/14#issue-1635979064

alko89 commented 2 months ago

@zph seems like the library already uses some form of replacer, because the Map is being serialized as "map": {"_constructor-name_":"Map"}, by default it's just an empty object "map": {}.

I did end up using the method mentioned in SO and use redis client without cache module.

jaredwray commented 2 months ago

@alko89 have you tried using the redis driver instead of ioredis?

alko89 commented 2 months ago

hmm no, I haven't tried using different drivers, always use ioredis

jaredwray commented 2 months ago

@alko89 - please try it on redis as we added more around how to support things like this.