Repository: praw-dev/praw

Issue:
Timeouts on media posts
## Issue Description
I find that frequently, when posting large images, the operation times out and I get something like this:
```
  File "/home/rolf/weather/redditSend.py", line 51, in post                                                                                                                                            
    api.submit_image(text, mergedImageName)                                                                                                                                                            
  File "/usr/local/lib/python3.7/site-packages/praw/models/reddit/subreddit.py", line 644, in submit_image
    return self._submit_media(data)                                                                                                                                                                                  
  File "/usr/local/lib/python3.7/site-packages/praw/models/reddit/subreddit.py", line 453, in _submit_media                                                                                           
    raise ClientException('Websocket error. Check your media file. '           
praw.exceptions.ClientException: Websocket error. Check your media file. Your post may still have been created.
```
When I looked into the source code of praw, I found several places that use "timeout=2" (https://github.com/praw-dev/praw/blob/master/praw/models/reddit/subreddit.py#L449). I'm assuming that's a 2-second timeout.  I'm also assuming that timeout is not sufficient for large images.  It would be nice if that were configurable.

## System Information

- PRAW Version: praw==6.1.1, prawcore==1.0.0
- Python Version: 3.7.2
- Operating System: Linux Mint 19.0



Discussion:
Could you provide an image that (sometimes) triggers this exception? I'd like to look into it more.

I'm not entirely happy with the websocket-based implementation in the file you linked, but it seems to be the only option.

If raising the timeout (or allowing it to be customized) alleviates the problem, I'm all for the change.
Here's an example of an image that I had trouble with: 
![big](https://user-images.githubusercontent.com/3651887/52984257-a6fd5800-33bc-11e9-8cf3-172e91ecb661.png)


Resolving patch:
diff --git a/praw/models/reddit/subreddit.py b/praw/models/reddit/subreddit.py
--- a/praw/models/reddit/subreddit.py
+++ b/praw/models/reddit/subreddit.py
@@ -410,7 +410,7 @@ def __init__(self, reddit, display_name=None, _data=None):
     def _info_path(self):
         return API_PATH['subreddit_about'].format(subreddit=self)
 
-    def _submit_media(self, data):
+    def _submit_media(self, data, timeout):
         """Submit and return an `image`, `video`, or `videogif`.
 
         This is a helper method for submitting posts that are not link posts or
@@ -446,9 +446,9 @@ def _submit_media(self, data):
         try:
             socket = websocket.create_connection(response['json']['data']
                                                  ['websocket_url'],
-                                                 timeout=2)
+                                                 timeout=timeout)
             ws_update = loads(socket.recv())
-            socket.close(timeout=2)
+            socket.close()
         except websocket.WebSocketTimeoutException:
             raise ClientException('Websocket error. Check your media file. '
                                   'Your post may still have been created.')
@@ -611,7 +611,7 @@ def submit(self, title, selftext=None, url=None, flair_id=None,
 
     def submit_image(self, title, image_path, flair_id=None,
                      flair_text=None, resubmit=True, send_replies=True,
-                     nsfw=False, spoiler=False):
+                     nsfw=False, spoiler=False, timeout=10):
         """Add an image submission to the subreddit.
 
         :param title: The title of the submission.
@@ -627,13 +627,17 @@ def submit_image(self, title, image_path, flair_id=None,
             (default: False).
         :param spoiler: Whether or not the submission should be marked as
             a spoiler (default: False).
+        :param timeout: Specifies a particular timeout, in seconds. Use to
+            avoid "Websocket error" exceptions (default: 10).
 
         .. note::
 
            Reddit's API uses WebSockets to respond with the link of the
            newly created post. If this fails, the method will raise
            :class:`.ClientException`. Occasionally, the Reddit post will still
-           be created. More often, there is an error with the image file.
+           be created. More often, there is an error with the image file. If
+           you frequently get exceptions but successfully created posts, try
+           setting the ``timeout`` parameter to a value above 10.
 
         :returns: A :class:`~.Submission` object for the newly created
             submission.
@@ -654,19 +658,19 @@ def submit_image(self, title, image_path, flair_id=None,
             if value is not None:
                 data[key] = value
         data.update(kind='image', url=self._upload_media(image_path))
-        return self._submit_media(data)
+        return self._submit_media(data, timeout)
 
     def submit_video(self, title, video_path, videogif=False,
                      thumbnail_path=None, flair_id=None, flair_text=None,
                      resubmit=True, send_replies=True, nsfw=False,
-                     spoiler=False):
+                     spoiler=False, timeout=10):
         """Add a video or videogif submission to the subreddit.
 
         :param title: The title of the submission.
         :param video_path: The path to a video, to upload and post.
         :param videogif: A ``bool`` value. If ``True``, the video is
-            uploaded as a videogif, which is essentially a silent video (
-            default: ``False``).
+            uploaded as a videogif, which is essentially a silent video
+            (default: ``False``).
         :param thumbnail_path: (Optional) The path to an image, to be uploaded
             and used as the thumbnail for this video. If not provided, the
             PRAW logo will be used as the thumbnail.
@@ -682,13 +686,17 @@ def submit_video(self, title, video_path, videogif=False,
             (default: False).
         :param spoiler: Whether or not the submission should be marked as
             a spoiler (default: False).
+        :param timeout: Specifies a particular timeout, in seconds. Use to
+            avoid "Websocket error" exceptions (default: 10).
 
         .. note::
 
            Reddit's API uses WebSockets to respond with the link of the
            newly created post. If this fails, the method will raise
            :class:`.ClientException`. Occasionally, the Reddit post will still
-           be created. More often, there is an error with the video file.
+           be created. More often, there is an error with the video file. If
+           you frequently get exceptions but successfully created posts, try
+           setting the ``timeout`` parameter to a value above 10.
 
         :returns: A :class:`~.Submission` object for the newly created
             submission.
@@ -712,7 +720,7 @@ def submit_video(self, title, video_path, videogif=False,
                     url=self._upload_media(video_path),
                     # if thumbnail_path is None, it uploads the PRAW logo
                     video_poster_url=self._upload_media(thumbnail_path))
-        return self._submit_media(data)
+        return self._submit_media(data, timeout)
 
     def subscribe(self, other_subreddits=None):
         """Subscribe to the subreddit.


Test patch: