Cached assets to s3
The first part of https://github.com/huggingface/datasets-server/issues/1406 
Migration for cached-assets enabling only for a list of datasets initially (I added "asoria/image" dataset for the first testing, later, we can remove this logic and apply it for all datasets).
Note that the new logic: validates if the file exists in the bucket and if not, uploads it.
This might increase latency, but will see how it works once it is deployed on prod, for now, I just added a couple of tests to ensure behavior.
All /rows and /search resources will be stored in` /cached-assets` subfolder in the bucket and the infra team will help us configure a TTL policy at the folder level to delete the files created more than a day before.
Notice that I decided to apply the same approach as Audio for Images because of:
- We are doing mostly a IO-bound task
- According to best practices, it is better to use multithreading when working with IO-bound tasks
- This doc helped me to understand that we are taking the best approach initially for parallelizing requests to S3 https://superfastpython.com/threadpool-vs-pool-in-python/

> You should use the ThreadPool for IO-bound tasks in Python in general.
> 	- Reading or writing a file from the hard drive.
> 	- Downloading or uploading a file.

Also, I compared working /rows + s3 with threa_map vs multiprocessing.Pool and had the following results (might be affected by my internet connection but at least it can give us an idea about comparison):

**For an audio dataset https://huggingface.co/datasets/asoria/audio-sample:**
Multithreading (thread_map)
- First time (all files are uploaded to the bucket)  = 7s
- Second time (only validation for existing files is done) = 4s

Multiprocessing (multiprocessing.Pool)
- First time (all files are uploaded to the bucket)  = 14s
- Second time (only validation for existing files is done) = 5s

**For an Image dataset https://huggingface.co/datasets/asoria/image:**
Multithreading (thread_map)
- First time (all files are uploaded to the bucket)  = 6s
- Second time (only validation for existing files is done) = 3s

Multiprocessing (multiprocessing.Pool)
- First time (all files are uploaded to the bucket)  = 15s
- Second time (only validation for existing files is done) = 7s


Cached assets to s3: The first part of https://github.com/huggingface/datasets-server/issues/1406 
Migration for cached-assets enabling only for a list of datasets initially (I added "asoria/image" dataset for the first testing, later, we can remove this logic and apply it for all datasets).
Note that the new logic: validates if the file exists in the bucket and if not, uploads it.
This might increase latency, but will see how it works once it is deployed on prod, for now, I just added a couple of tests to ensure behavior.
All /rows and /search resources will be stored in` /cached-assets` subfolder in the bucket and the infra team will help us configure a TTL policy at the folder level to delete the files created more than a day before.
Notice that I decided to apply the same approach as Audio for Images because of:
- We are doing mostly a IO-bound task
- According to best practices, it is better to use multithreading when working with IO-bound tasks
- This doc helped me to understand that we are taking the best approach initially for parallelizing requests to S3 https://superfastpython.com/threadpool-vs-pool-in-python/

> You should use the ThreadPool for IO-bound tasks in Python in general.
> 	- Reading or writing a file from the hard drive.
> 	- Downloading or uploading a file.

Also, I compared working /rows + s3 with threa_map vs multiprocessing.Pool and had the following results (might be affected by my internet connection but at least it can give us an idea about comparison):

**For an audio dataset https://huggingface.co/datasets/asoria/audio-sample:**
Multithreading (thread_map)
- First time (all files are uploaded to the bucket)  = 7s
- Second time (only validation for existing files is done) = 4s

Multiprocessing (multiprocessing.Pool)
- First time (all files are uploaded to the bucket)  = 14s
- Second time (only validation for existing files is done) = 5s

**For an Image dataset https://huggingface.co/datasets/asoria/image:**
Multithreading (thread_map)
- First time (all files are uploaded to the bucket)  = 6s
- Second time (only validation for existing files is done) = 3s

Multiprocessing (multiprocessing.Pool)
- First time (all files are uploaded to the bucket)  = 15s
- Second time (only validation for existing files is done) = 7s

