1

When writing a multi-process program for web scraping, I passed an object of my custom RedisQueue class as an argument to the multi-process task function. This class contains a Redis object as one of its attributes, and when I ran the program, the following error occurred: "TypeError: can't pickle StrictRedis objects".

The RedisQueue class I wrote is as follows (in Python):

from redis import StrictRedis
class RedisQueue:
 def __init__(self, host: str = "localhost", port: int = 6379, password: str = None, db: int = 0,
 client: StrictRedis = None,name_in_redis: str = "rq"):
 if client is None:
 self.client = StrictRedis(host=host, port=port, password=password, db=db)
 else:
 self.client = client
 self.queue_name = name_in_redis
 def __len__(self):
 return self.client.llen(self.queue_name)
 def clear(self):
 self.client.delete(self.queue_name)
 def push(self, *values: str):
 return self.client.lpush(self.queue_name,*values)
 def pop(self):
 return self.client.rpop(self.queue_name)
 def close(self):
 if self.client is not None:
 self.client.close()

tried

I have tried recreating an instance of the RedisQueue class within the process task function to solve this issue, but this complicates the process of passing parameters to the process task function—requiring me to pass nearly all parameters needed for creating the Redis object.

expecting

I hope to rewrite the RedisQueue class so that its instances can be directly passed as parameters to the task function, eliminating the need to retrieve the required parameters and recreate the instance in the child process.

J_H
21k5 gold badges29 silver badges50 bronze badges
asked Oct 11 at 5:13

1 Answer 1

2

Clearly self.client is trouble, here.

You need to define something new, perhaps RedisProtoQueue, which knows how to make a Valkey client but doesn't actually contain an open TCP connection. Give it the user / pass / host connect string credentials, but not the open socket. Then once it is deserialized on some destination host it will be able to connect to Valkey as needed.

If you wish to serialize an object which has already opened a TCP connection, simply set that attribute to None, since that's easily serialized. Then re-create the TCP connection on the far side, after deserializing.

answered Oct 11 at 14:39
Sign up to request clarification or add additional context in comments.

1 Comment

That's definitely a great solution. It should fix the issue where the parameters I'm passing are too complex. Thank you for your help.

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.