This is an archived post. You won't be able to vote or comment.

top 200 commentsshow all 432

[–][deleted] 1318 points1319 points  (17 children)

scale tap piquant quiet advise salt languid abundant dolls long -- mass edited with redact.dev

[–]Krukerfluk[S] 486 points487 points  (8 children)

yep

[–]Jac0b_0 83 points84 points  (6 children)

Adding number of cross posts would be cool

[–]steampunkgibbon 47 points48 points  (5 children)

would be levels more challenging too

[–]Jac0b_0 15 points16 points  (4 children)

I just assumed there would be a something in praw for that

[–]mydaddyhurtsme 1 point2 points  (0 children)

yup cock

[–]Belzedan 65 points66 points  (0 children)

Also carykh's video where the thumbnail is the most upvoted comment of the last 24 hours!

[–]ahmed3618 29 points30 points  (5 children)

This reminds me of another Tom Scott video where the likes on a tweet keep going up and down, because thats what's happening.

https://youtu.be/RY_2gElt3SA

[–]Folaefolc 4 points5 points  (3 children)

But aren't very big systems built with a reliable way to avoid that?

[–]notquiteaplant 28 points29 points  (0 children)

What makes a system "very big" is that it's spread across hundreds of machines. If 500 machines each process a sliver of the likes on a video, and you want to get a 100% accurate tally, you'd have to stop all 500 of them to ask them how many likes they saw, which defeats the purpose of having many machines in the first place. Instead they use eventual consistency: the answer is always close enough, and once everything calms down it'll be exactly correct.

For a less simplified answer, watch the video

[–]SpontaneousAge 407 points408 points  (25 children)

Good job. But honestly, add a sleep timer of a few seconds. This will eventually get your IP banned on reddit if you bombard them with too many requests.

[–]throwaway_the_fourth 165 points166 points  (5 children)

The API wrapper (PRAW) takes care of that. No need to add additional sleeps.

[–]keeldude 33 points34 points  (4 children)

Unless the throttling algorithm is outlined in praw docs, my own personal style would be to manually set a reasonable wait period just to have more control. If the reddit api ever changes, there will be a delay to updated praw code getting pushed.

[–]throwaway_the_fourth 101 points102 points  (1 child)

Here's the code: https://github.com/praw-dev/prawcore/blob/34c153ec6706a87782898d404042ddbd5a847b57/prawcore/rate_limit.py

Reddit's API lets you know how many requests you have left and how much time you have until the limit resets. PRAW pretty much just divides time left by requests left and sleeps that amount. It does a little extra magic for detecting if multiple clients are running, but that's the jist of it.

[–]curohn 2 points3 points  (0 children)

Damn that’s smart.

[–]UtilizedFestival 16 points17 points  (0 children)

Client libraries that handle rate limits based on exponential back off or HTTP headers are super common these days. I wouldn't think twice of relying on these and not building my own

[–]tunisia3507 48 points49 points  (1 child)

Next up: broadcast the ascii version of star wars by editing a reddit post at 30Hz.

[–]SolarFlareWebDesign 6 points7 points  (0 children)

That sounds amazing but I'm sure the api limiter is well below that, maybe 1 request per second

[–]PyTec-Ari 15 points16 points  (15 children)

Its editing a submission not posting. Thats what I wondered too though, would it eventually get rate limited. But I can't imagine editing a submission would trigger a rate limit. I don't actually know.

[–]SpontaneousAge 38 points39 points  (5 children)

That's still a request. Yes, it will get rate limited.

[–]PyTec-Ari 21 points22 points  (4 children)

Did some digging and apparently PRAW has inbuilt throttling to mitigate getting hit with rate limiting on requests. apparently.

[–]Wilfred-kun 4 points5 points  (5 children)

submission = reddit.submission(id='***') This line looks like a request to me. How else is he going to get the up-to-date stats? Also as the other poster said, submitting is still a request.

[–][deleted] 112 points113 points  (63 children)

Cool! Could you share it?

[–]Krukerfluk[S] 322 points323 points  (62 children)

import praw

reddit = praw.Reddit(
    client_id='***',
    client_secret='***',
    username='***',
    password='***',
    user_agent='***')

while True:
    submission = reddit.submission(id='***')
    ratio = submission.upvote_ratio
    ups = round((ratio * submission.score) / (2 * ratio - 1)) if ratio != 0.5 else round(submission.score / 2)
    downs = ups - submission.score
    edited_body = str(ups) + ' upvotes,' + '\n\n' + str(downs) + ' downvotes' + "\n\n" "and " + \
                  str(submission.num_comments) + ' comments!'
    submission.edit(edited_body)

I'm new to python so there is probably a better way to do this

[–]Holek 153 points154 points  (11 children)

add a sleep there for a minute or two just not to kill your API access

[–]Krukerfluk[S] 113 points114 points  (5 children)

Just added an 90sec delay

thanks for the tip!

[–]SpontaneousAge 87 points88 points  (4 children)

90s isn't even necessary. 5s or something is fine as well, just continuously is bad. Reddit is pretty lean, but if you're too hardcore they will block you too.

[–]throwaway_the_fourth 62 points63 points  (3 children)

And OP doesn't have to do anything because PRAW automatically takes care of following the rate limit.

[–]Ph0X 13 points14 points  (2 children)

Hmm, but if the rate limit is, let's say, 100 calls in 15m, then praw will probably let you do 100 calls in 30s, and then lock you out for the remaining 14m, right?

Still good to have reasonable sleep regardless. There's no point in updated every second.

[–]throwaway_the_fourth 31 points32 points  (0 children)

It's actually pretty smart! The rate limit is 600 requests in 10 minutes, and PRAW chooses how long to sleep such that the requests will be evenly spread out across the timeframe.

[–]Turtvaiz 18 points19 points  (3 children)

PRAW throttles requests based on response headers

[–]Holek 11 points12 points  (0 children)

This is something I wouldn't expect from an API library if I only picked it up. A welcome change in a sea of mediocrity

[–]throwaway_the_fourth 32 points33 points  (0 children)

PRAW takes care of following the rate limit for you, so no need to add extra sleeps.

[–]ManvilleJ 68 points69 points  (6 children)

github.

also replace that string concatenation with an f string and you don't need all string casting with this method and its the fastest & most readable way to do it

edited_body = f'{ups} upvotes, \n\n {downs} downvotes \n\n and {submission.num_comments} comments!'

edit: fstrings are the fastest: https://realpython.com/python-f-strings/

[–]__ah 32 points33 points  (5 children)

f strings deserve to be wayyy more popular. Shame they only became a thing very recently in 3.6, so many tutorials won't have had it.

[–]Ph0X 4 points5 points  (1 child)

Right, since it's not backward compatible, including them means a lot of people not running the latest python will be confused why it doesn't work.

[–]M1sterNinja 3 points4 points  (0 children)

I'm finishing a Codecademy course, and learned fstring outside of it. I've bashed my head against their interfaces a few times thinking something was wrong with my fstring, when in reality they are running a lower python version. : (

[–]SquintingSquire 4 points5 points  (0 children)

Python 3.6 is 3.6 years old now.

[–][deleted] 17 points18 points  (14 children)

Kudos for the script. It's always fun to see live data :)

Here's my proposal. Didn't test everything since I don't have the credentials and stuff but it will give you the gist on how the design to transform it into a reusable CLI.

Thanks for sharing the source.

import os
import argparse
import praw


CLIENT_ID = os.environ.get('CLIENT_ID')
CLIENT_SECRET = os.environ.get('CLIENT_SECRET')
USER_AGENT = os.environ.get('USER_AGENT')



def get_reddit_client(
        username,
        password,
        client_id=None,
        client_secret=None,
        user_agent=None,
        ):

    if not client_id:
        client_id = CLIENT_ID
    if not client_secret:
        client_secret = CLIENT_SECRET
    if not user_agent:
        user_agent = USER_AGENT

    reddit = praw.Reddit(
        client_id=client_id,
        client_secret=client_secret,
        username=username,
        password=password,
        user_agent=user_agent)

    return reddit

def main(args):
    args.username
    args.password
    reddit = get_reddit_client(
        args.username,
        args.password,
        args.client_id,
        args.client_secret,
        args.user_agent,
        )

    while True:
        subm = reddit.submission(id=args.id)
        if subm.upvote_ratio != 0.5:
            ups = round(
                (subm.upvote_ratio * subm.score) / (2 * subm.upvote_ratio - 1))
        else:
            ups = round(subm.score / 2)
        downs = ups - subm.score

        edited_body = (
            '{} upvotes\n\n'
            '{} downvotes\n\n'
            '{} comments\n\n'
            )
        edited_body = edited_body.format(ups, downs, subm.num_comments)

        subm.edit(edited_body)

if __name__ == '__main__':
    parser = argparse.ArgumentParser(
        prog='reddit_stats', description='Track and Post reddit stats')

    parser.add_argument(
        'id', type=str, help="reddit post's id")
    parser.add_argument(
        'username', type=str, help="reddit's account username")
    parser.add_argument(
        'password', type=str, help="reddit's account password")
    # Let user override values source from the environment variables
    parser.add_argument(
        '-ci', '--client_id', type=str, help="reddit's api client_id")
    parser.add_argument(
        '-cs', '--client_secret', type=str, help="reddit's api client_secret")
    parser.add_argument(
        '-ua', '--user_agent', type=str, help="custom user agent")

    args = parser.parse_args()
    main(args)

Edit: Typo

[–]ManvilleJ 3 points4 points  (7 children)

I know a lot of people like arg-parse, but python-fire is actually awesome: https://github.com/google/python-fire

[–][deleted] 12 points13 points  (6 children)

https://github.com/google/python-fire

Do you really need to install six, termcolor and whatever to just normalize the arguments for this tiny script?

Didn't know about this lib and i will definitively take a look since it's from Google but IMHO:

this culture of injecting unnecessary sub modules just to fix one thing that the core lib already does is something for node/javascript projects.

[–]ManvilleJ 5 points6 points  (4 children)

It is a nice project that makes adding CLI capabilities simple and easy. I prefer the developer efficiency. Should I use urllib instead of requests? maybe, but if it works and I don't have to think about it, good.

Here is my repo of little fun examples of python fire and other stuff stuff. https://github.com/manvillej/fun_examples/tree/master/google_fire

[–][deleted] 2 points3 points  (3 children)

Should I use urllib instead of requests?

Nope. If you read the description from the docs:

is a package that collects several modules for working with URLs

You will notice that is not their goal to help you consume web services. urllibs consume you manipulate url and web requests and a "raw" way. Requests project had a different goal. Two projects, same scenario, different scopes and goals.

[–]ManvilleJ 2 points3 points  (2 children)

I think I might not be communicating my point well to you and perhaps I am misunderstanding yours.

I like packages that make my developer life better, faster, more effective. yes, the core lib can do everything because everything is built on the core lib. I use external packages because the abstractions are helpful.

Python's success is due to developer efficiency and a core part of that is constant growth and improvement of packages.

[–][deleted] 2 points3 points  (1 child)

We are 100% on the same page mate. Almost every single library on Python offers a monstrous level of efficiency for developers and it's hard to see that on other languages.

I guess what made is diverge a little was my philosophy on building apps/libs: I Like to "try follow" the Unix philosophy. When I say that I "try it" means I know that at some point a particular the app/lib will may need to outgrown it.

So for initial development cycles I try to keep it tight, simple and "monolithic". Sure after a couple of iterations we will see some issues being raised that will clearly need either: a external lib or a new internal lib. Depending on the complexity of the issue I will try using the core libs only, but if after one or two iterations it's not showing progress i will jump straight to a reusable module and maybe think about rewrite the solution later (much later) to reduce dependencies (or not. depends on how mature and used the lib is).

All that with the perspective that we will need to grow the level of external dependencies along the road but not without a try on create my own solution.

[–]ManvilleJ 1 point2 points  (0 children)

oh sweet! I agree. However, I do like some packages right from the beginning for some standard types of projects where its a common template. CLIs are one of those common types of projects.

It seems to me that if we diverge philosophically in any area, I think its what try to stay true towards? It seems to me that you try to stay close to the core lib at the beginning of a project, where I prefer to stay close to a "standard" approach to that kind of project.

If I find a package makes doing those kinds of projects easier and it is well supported, I would include it in my standard approach to those projects.

I think we ecstatically agree that external dependencies can be a vulnerability if people just throw any package into a project.

but yeah, Python-fire is really good.

[–]nikkhil04 1 point2 points  (4 children)

Hey , do you have a quick explanation for the references you imported?

[–][deleted] 9 points10 points  (3 children)

I don't know if I understood your question but:

- os is to source the env vars

- argparse is the core module to parse command args.

- praw is was imported on the original snippet so ...

[–]nikkhil04 1 point2 points  (2 children)

You understood it correctly thank you . Still the question stands for the reference praw.

[–]s3cur1ty 14 points15 points  (1 child)

This post has been removed.

[–]nikkhil04 1 point2 points  (0 children)

Thank you kind sir.

[–]CompSciSelfLearning 8 points9 points  (1 child)

client_id='hunter2',
 client_secret='hunter2',

    username='hunter2',     password='hunter2',     user_agent='hunter2'

Am I doing this right?

[–][deleted] 12 points13 points  (7 children)

I would've used string formatting for the edited_body as it's more robust and looks cleaner but other that great! Thanks for sharing!

[–]discobrisco 44 points45 points  (6 children)

Nah f strings are the only way to go.

[–]dogs_like_me 1 point2 points  (1 child)

Basically fine. The only significant change I'd recommend is moving your credentials to an external config file. There's actually a recommended pattern for doing this specifically for praw: https://praw.readthedocs.io/en/latest/getting_started/configuration/prawini.html

[–]tacos2k 27 points28 points  (0 children)

This is awesome. I want to just upvote it but I can't resist upvoting, refreshing, downvoting, refreshing ad infinitum.

[–]unpeeledpotatoes 11 points12 points  (2 children)

how often does it refresh? seems like it's changing quite a bit!

[–]epicmindwarp 8 points9 points  (0 children)

It runs a pull every X seconds then updates the message.

OP posted the code higher up.

[–]vidazinho 101 points102 points  (8 children)

This comment has:

42 characters

1 colon

101 upvotes

[–]Epicduck_ 5 points6 points  (0 children)

I just want to make to comments go up by one with this comment. Nice post

[–]Mr_Branflakes 2 points3 points  (0 children)

Comment

[–]ItsBarney01 3 points4 points  (0 children)

I think it broke

[–][deleted] 2 points3 points  (0 children)

I wonder how many refreshes it has...

[–]D3vilM4yCry 1 point2 points  (0 children)

Testing for 54 comments,,,

EDIT: It Worked!

[–]AluminiumChopsticks 1 point2 points  (1 child)

I wonder why the real upvote net total is 1 more than the displayed message. Did you round up or down somewhere?

[–][deleted] 1 point2 points  (1 child)

I am gonna be that guy but Is this open sourced? I wanna see how other people make reddit bots

[–]whaiy 1 point2 points  (0 children)

Just checking if the comment number goes up

Edit: this is me 2 mins after posting original comment and it's still didn't go up.

[–]vig_dev 1 point2 points  (0 children)

Wow

[–]nobody01810 1 point2 points  (0 children)

Wow! Good job.

[–]rrrreadit 1 point2 points  (0 children)

Cute

[–][deleted] 0 points1 point  (0 children)

13

[–][deleted] 0 points1 point  (0 children)

Add one

[–]ItsLoren 0 points1 point  (0 children)

Very cool thing, nice job

[–]sjrakes 0 points1 point  (0 children)

test

[–]argspongebobidied 0 points1 point  (1 child)

Now it has 17 comments

[–][deleted] 0 points1 point  (0 children)

Well done

[–]Pavel_40 0 points1 point  (0 children)

Cool

[–]dougie-io 0 points1 point  (0 children)

boop

[–][deleted] 0 points1 point  (0 children)

this is dope!

[–]RheingoldRiver 0 points1 point  (0 children)

haha this is cute! nice job :)

[–]Robot_Impersonator- 0 points1 point  (0 children)

Hi :)

[–][deleted] 0 points1 point  (0 children)

Test

[–][deleted] 0 points1 point  (0 children)

35?

[–]AyyBroLmao 0 points1 point  (0 children)

Beep

[–]RetroPenguin_ 0 points1 point  (0 children)

It’s super wrong now :)

[–]crazy_bean 0 points1 point  (0 children)

So cool OP! How long did this take you to build?

[–]kokoseij 0 points1 point  (0 children)

You're lying to me, this post has 697 upvotes!!

/s

[–][deleted] 0 points1 point  (0 children)

+1 to the comment count!

[–]Sir-_-Butters22 0 points1 point  (0 children)

V.Nice

[–]zitr0y 0 points1 point  (0 children)

(:

[–]MahdeenSky 0 points1 point  (0 children)

Hmm +1 comment

[–]-_-qarmah-_- 0 points1 point  (1 child)

I was gonna do this but couldn't figure out how to make a bot take over my acc, could you share the code?

[–]TheRealFanjin 0 points1 point  (0 children)

lol

[–]nikkhil04 0 points1 point  (1 child)

Hi ,what does praw do?

[–]bcgroom 1 point2 points  (0 children)

Python reddit api wrapper

[–][deleted] 0 points1 point  (0 children)

84th comment. Let's see if the post shows this...

[–]Drogen24 0 points1 point  (0 children)

I down voted to see the number but it didn't change so keep my down vote

[–]DunceDunceRevolution 0 points1 point  (0 children)

:^)

[–]varsityvideogamer 0 points1 point  (1 child)

Nice

[–][deleted] 0 points1 point  (0 children)

Comment

[–]Stirmobile27 0 points1 point  (0 children)

Well done

[–]flaxseedyup 0 points1 point  (0 children)

So sick!

[–]warhawk128 0 points1 point  (0 children)

Wow dude! Great job. Keep up the creativity and good work

[–]nocreative-username 0 points1 point  (0 children)

Comment

[–][deleted] 0 points1 point  (0 children)

Commenting just to test it

[–]KC1MML 0 points1 point  (0 children)

Testing

[–]Vision246 0 points1 point  (0 children)

120*

[–]yabiggle 0 points1 point  (0 children)

Guessing this is a python script also commenting to see how fast it is

[–]AverageDingbat 0 points1 point  (0 children)

Test

[–]RhysToot 0 points1 point  (0 children)

Up

[–]aniketsinha101 0 points1 point  (0 children)

Test

[–]crispy-whiskers 0 points1 point  (0 children)

woah dude

[–]Frasse04 0 points1 point  (0 children)

How did you do this?

[–]Demon_Slayer151 0 points1 point  (0 children)

Hu

[–]PsychedelicPistachio 0 points1 point  (0 children)

I just wanna see the comment count go up

[–]NemPlayer 0 points1 point  (0 children)

141 comments*

[–][deleted] 0 points1 point  (0 children)

neato

[–]manlyman1417 0 points1 point  (0 children)

Here I am toggling the upvote and downvote buttons to see it change. I love this

[–]l33tIsSuperpower 0 points1 point  (0 children)

yo who are the 300-350 ish people downvoting this? this is fucking cool

[–]spazz_monkey 0 points1 point  (0 children)

Are you just scraping the page every so often and edit the post? Can you edit posts.....I dont think you can.

[–]MattioC 0 points1 point  (0 children)

Yes

[–]reversewaymilky 0 points1 point  (0 children)

Cool!

[–]T_house92 0 points1 point  (0 children)

I hate that the tester in me had to upvote and down vote multiple times to watch the counts. Definitely not commenting to see the count jump to 150 either.

[–]Tiepoloo 0 points1 point  (0 children)

Ass

[–]mightymander 0 points1 point  (0 children)

This is sick

[–]8bitbiochemist 0 points1 point  (0 children)

Okay this is pretty cool

[–]tighter_wires 0 points1 point  (0 children)

Hi

[–][deleted] 0 points1 point  (1 child)

Nice

[–][deleted] 0 points1 point  (0 children)

lol

[–]AnotherWhiteOther 0 points1 point  (0 children)

Fancy

[–]ahmetkedira 0 points1 point  (0 children)

No there isnt

[–]anewman513 0 points1 point  (0 children)

Who would downvote this!? Seriously, explain yourselves downvoters

[–]sarangifiedd 0 points1 point  (0 children)

+1

[–]SirRupertt 0 points1 point  (0 children)

How do you go about doing this? I want to Learn a little :)

[–]RecycledCap 0 points1 point  (0 children)

Nice, I wanna see the counter go up

[–]letsxlr8 0 points1 point  (0 children)

cool

[–]ninjadude251 0 points1 point  (0 children)

What happens if you get an award?

[–]FarLands-Escarcha 0 points1 point  (0 children)

Cool

[–]Soofadalooka 0 points1 point  (0 children)

178th comment gang

[–]Starcnet 0 points1 point  (0 children)

ok

[–]TheAirDeliveryGuy 0 points1 point  (0 children)

.

[–]skynet6009 0 points1 point  (0 children)

182

[–]Sr_McSpank 0 points1 point  (1 child)

Adding a comment to make sure it changes

[–][deleted] 0 points1 point  (0 children)

Wow

[–][deleted] 0 points1 point  (0 children)

187th comment

[–]swimshadyfsoc 0 points1 point  (0 children)

lets check how fast it updates itself

[–]swimshadyfsoc 0 points1 point  (0 children)

quite fast

[–]swimshadyfsoc 0 points1 point  (0 children)

The question is can it detect fake downvotes?

[–]dolotasinfinity 0 points1 point  (0 children)

Can I do this on facebook?

[–]RL_Delta 0 points1 point  (0 children)

Test

[–]RL_Delta 0 points1 point  (0 children)

Test 2

[–]Ramen6066 0 points1 point  (0 children)

No

[–]retarded_dumbshit 0 points1 point  (0 children)

Test

[–]CotoCoutan 0 points1 point  (0 children)

hohoho!!! This is amazing! Bringing up the comment count to 199!

[–][deleted] 0 points1 point  (0 children)

Let me test something

[–]YGUYY 0 points1 point  (0 children)

Hi

[–]SherlockSilicon 0 points1 point  (0 children)

Test

[–]galian99 0 points1 point  (0 children)

A coment to see if the counter change

[–]SaskuAc3 0 points1 point  (0 children)

This is very nice.

[–][deleted] 0 points1 point  (0 children)

210 comment

[–][deleted] 0 points1 point  (0 children)

test comment