diff --git a/.gitignore b/.gitignore index 49fb0fb..5e4510e 100644 --- a/.gitignore +++ b/.gitignore @@ -125,5 +125,8 @@ pseud.json # Pseudbot last id file last_id +# Pandoc README.md preview +README.html + # The editor that people seem to like for some reason .vscode diff --git a/Makefile b/Makefile index 7e7d273..5f34e87 100644 --- a/Makefile +++ b/Makefile @@ -9,6 +9,9 @@ reinstall: $(MAKE) clean $(MAKE) install +readme-preview: + pandoc README.md -s -c img/pub.css -o README.html + format: black -v -l 80 pseudbot/* black -v -l 80 scripts/* diff --git a/README.md b/README.md new file mode 100644 index 0000000..204ef95 --- /dev/null +++ b/README.md @@ -0,0 +1,171 @@ +

+ pseudbot logo +

Pseudbot

+

+ +

+ + Twitter API: v1.1 + + + Code style: black + + + License: AGPLv3+CHRIST + + + Powered by Tweepy + +

+ +

+ *A friendly bot* 🤖*created by Rick Sanchez* 🧪 *from dimension C-137* 🌎*.* +

+ +📣 Mention it in a 🗐 thread 🪡🧵 and it'll 🗨 reply 🗣 to the 🚸 parent +🗮 tweet 🕊 with a Rick 🧠 and Morty 😜 quote 💯 in two minutes 🕓 or +less (if it's online 🖧). + +It picks up right where it left off in its mentions when it reboots ♻. + +> **"***As a reflection of my true and honest nihilistic outlook,
we're building a machine;
we're taking a wrench to the discourse!
Metaphorical cocks in the machine, if you will.***"** + +⚞***R&M♾100Y!***⚟ + +## Installation +The sections under here that follow are the current installation steps. +In the future, the *Set up your Python environment* section will +become optional. + +### Get access to the Twitter API +Before doing anything else, +[apply for access](https://developer.twitter.com/en/docs/twitter-api/getting-started/getting-access-to-the-twitter-api) +to the Twitter API. For this app, the "Standard" product track for +individual/hobbyist use *should* be more than sufficient for a Pseudbot +installation. + +It is recommended to use a dedicated Twitter account for your Pseudbot +instance (unless you don't mind clogging up your followers' notifications, of +course). + +Once you have gotten access to the Twitter API, you can begin setting up +Pseudbot. + +### Install your API keys +Create a file named `pseud.json` with your editor and paste in the API keys you +just created on Twitter's developer page in the previous step: +```json +{ + "consumer": "key goes here", + "consumer_secret": "key goes here", + "bearer_token": "key goes here", + "tok": "key goes here", + "tok_secret": "key goes here" +} +``` + +### Set up your Python environment (recommended for now) +Currently only use in a `venv` within this repository's root directory +is tested and supported. Most things should work outside of a `venv`, but +you'll have to be mindful of where your config and `last_id` files are. + +Set up your Python virtual environment (a `venv`, in this case): +``` +$ python3 -m venv .venv +``` + +Activate the `venv` by sourcing the appropriate `activate` for your running +shell: +``` +$ . .venv/bin/activate +``` + +### Install Pseudbot +Install the bot by running its `setup.py` via Pseudbot's `Makefile`: +``` +$ make install +``` + +If everything worked out okay, you should now have the `pseudbot` command +within your shell's search path. + + +## Testing your API keys +You can send a test tweet from `pseudbot` by running the `hello` action: +``` +$ pseudbot hello + ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⢀⡤⠶⢶⣶⣦⣄⡀⠀⠀ + ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⣠⣾⣿⡄⠒⠪⢝⠻⣿⣿⣦⡀ + ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⣴⣿⡿⢉⡀⠀⠈⠐⠄⢿⣿⣿⣷ + ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⣼⣿⡇⠀*⠈⡄⠤⢀⠈⣾⣿⣿⣿ + ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⢀⡾⣿⣟⣕⡤⡠⠘⠀*⠀⢱⣿⣿⣿⣿ + ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⢠⣾⣾⣿⣞⣄⠮⠔⠈⡢⠄⣠⣾⣿⣿⣿⣿ + ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠠⢿⣿⢽⡻⣿⣿⣿⣽⣵⣾⡽⣿⣿⣿⣿⣿⡏ + ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⢠⣗⣿⡟⠈⠉⠚⢽⣻⢷⡝⣿⡿⣿⣿⣿⣿⡿⠀ + ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⢠⣿⣿⣿⠇⠀⠀⠀⠀⠀⢩⣯⣭⣾⣿⣿⣿⣿⠁⠀ + ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⣰⣿⣿⣿⠃⠀⠀⠀⠀⠀⣰⣿⣿⣿⣿⣿⣿⣿⠃⠀⠀ + ⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⣴⣿⣿⡿⠃⠀⠀⠀⠀⣠⣼⣿⣿⣿⣿⣿⣿⣿⠃⠀⠀⠀ + ⠀⠀⠀⠀⠀⠀⠀⠀⠀⢀⢞⣿⣿⡿⠁⠀⠀⠀⣠⣾⣿⣿⣿⣿⣿⣿⣿⣿⠃⠀⠀⠀⠀ + ⠀⠀⠀⠀⠀⠀⠀⠀⣰⣿⣾⣿⠏⠀⠀⠀⠀⣾⣿⣿⣿⣿⣿⣿⡟⣿⣿⠏⠀⠀⠀⠀⠀ + ⠀⠀⠀⠀⠀⠀⣠⣾⣿⣿⣿⠃⠀⠀⠀⠀⣸⣿⣿⣿⣿⣿⣟⣷⣾⣿⠏⠀⠀⠀⠀⠀⠀ + ⠀⠀⠀⠀⢀⣾⣿⣿⣿⣿⠃⠀⠀⠀⢀⣴⣿⣿⣿⣿⣿⣿⣿⣿⣿⠋⠀⠀⠀⠀⠀⠀⠀ + ⠀⠀⠀⡰⢿⣿⣿⣯⡶⠁⠀⠀⢀⣴⣿⣿⣿⣿⣿⣿⣿⣿⣿⡿⠃⠀⠀⠀⠀⠀⠀⠀⠀ + ⠀⢀⣼⣟⣿⣿⡿⠃⠀⠀⢀⣴⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⡟⠁⠀⠀⠀⠀⠀⠀⠀⠀⠀ + ⢀⣾⣿⣿⡯⣿⠀⠀⢠⣴⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⠏⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀ + ⣾⣿⣿⣿⣿⣿⣶⣶⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⡿⠁⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀ + ⠿⣿⡿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⣿⢿⡿⠋⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀ + ⠀⠛⠀⠈⠀⠻⣿⣿⣿⣿⣿⣟⣛⣿⣿⡭⠋⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀ + ⠢⡀⠀⠀⠀⠀⠻⣿⣿⣿⣿⣿⣭⠟⠉⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀ + ⠀⠈⠐⠤⢀⡀⠀⢀⣙⣿⠿⠋⠁⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀⠀ + +___ + | _.._ _ _ ._ _._ _ _..__|_ +_|_ (_|| | | \/(/_|\/ _>| | |(_|| |_ + / + +[TWEET]: "🕑1635207388: Running method: "hello"" (https://twitter.com/pseudbot/status/1452791284683481092) +[TWEET]: "🕑1635207388: Hello pseudbot" (https://twitter.com/pseudbot/status/1452791287623700481) +``` + +If `hello` ran without any errors and the parenthesized URLs work, you can move +on to actually running the bot! + +## Running the bot +In a long-lived shell session, start your Pseudbot instance with the `run_bot` +action: +``` +$ pseudbot run_bot +... +[TWEET]: "Powered on at 1635208674" (https://twitter.com/pseudbot/status/1452796682056388618) +[TWEET]: "@SoloDeath1 This copypasta was never even funny to begin with. I've never even seen the show, and it was obviously a joke. What kind of idiot do you have to be to think that was ever said seriously?" (https://twitter.com/pseudbot/status/1452748584877711367) +[TWEET]: "@pseudbot But it makes fun of something which is popular, and therefore popular to shit on among the contrarians on Reddit. Come on, really. I actually do have to wonder about the IQs of people who like that pretentious copypasta." (https://twitter.com/pseudbot/status/1452748594449158146) +[TWEET]: "@pseudbot You know, I sometimes can't help but superiorly smirk as I imagine their dumb faces struggling to understand words on a mere internet webpage." (https://twitter.com/pseudbot/status/1452748603978616842) +[TWEET]: "@pseudbot In fact, I sometimes find myself in paroxysms of ironic Schadenfreude as I envision the visages of the aforementioned Slow-in-the-minds waging war with the Cultural Artifact they proclaim to be analyzing," (https://twitter.com/pseudbot/status/1452748613466140679) +[TWEET]: "@pseudbot only to fall, slack-jawed, back into their insensate stupor, the proverbial Undiscovered Country, "from whose bourn no traveler returns" ." (https://twitter.com/pseudbot/status/1452748623075287051) +Finished chain with 1452748623075287051 +``` + +If you installed the bot in a `venv`, make sure you've activated your `venv` in +your current shell before starting the bot (rerun the `activate` command +mentioned above in *Set up your Python environment*). + +### A note about mentions +If you want the bot to respond to mentions from accounts it isn't following, +go to your bot account's +[notification filter settings page](https://twitter.com/settings/notifications/filters) +and *uncheck* the `Quality filter` ☑ checkbox: + + +### Shutting down the bot +To shut down your bot, simply send the keyboard interrupt signal (usually by +pressing `Ctrl`**+**`C` on your keyboard): +``` +... +[TWEET]: "@pseudbot 🥒 IM PIIICKLE 🥒 RIIIIIICK!!! 😂 👌 💯 🥒 IM PIIICKLE 🥒 RIIIIIICK!!! 😂 👌 💯 🥒 IM PIIICKLE 🥒 RIIIIIICK!!! 😂 👌 💯" (https://twitter.com/pseudbot/status/1452754226820571148) +Finished chain with 1452754226820571148 +^C +[TWEET]: Tweeted "Shut down for maintenance at 1635208498" (https://twitter.com/pseudbot/status/1452795944324550659) +``` + +The next time you restart your bot, it will resume where it left off using the +`last_id` file. diff --git a/img/black-badge.svg b/img/black-badge.svg new file mode 100644 index 0000000..d2ae121 --- /dev/null +++ b/img/black-badge.svg @@ -0,0 +1 @@ +code style: blackcode styleblack \ No newline at end of file diff --git a/img/license-badge.svg b/img/license-badge.svg new file mode 100644 index 0000000..372bf57 --- /dev/null +++ b/img/license-badge.svg @@ -0,0 +1 @@ +license: AGPLv3+CHRISTlicenseAGPLv3+CHRIST \ No newline at end of file diff --git a/img/pseudbot-icon-1000.png b/img/pseudbot-icon-1000.png new file mode 100644 index 0000000..bef440b Binary files /dev/null and b/img/pseudbot-icon-1000.png differ diff --git a/img/pub.css b/img/pub.css new file mode 100644 index 0000000..3529593 --- /dev/null +++ b/img/pub.css @@ -0,0 +1,365 @@ +/* + * CSS stylesheet for readable pages, built for HTML generated by Pandoc. + * + * Credits to: + * + * - https://github.com/huyng/latex-simple-css + * - https://gist.github.com/ryangray/1882525 + */ + +body { + /* Serif options */ + /*font-family: "Times New Roman", Times, serif;*/ + /*font-family: "Palatino Linotype", "Book Antiqua", Palatino, serif */ + + /*Sans Serif options */ + /*font-family: "Helvetica", Arial, Freesans, clean, sans-serif;*/ + font-family: "Helvetica Neue", "Ubuntu", "Open Sans", Arial, Freesans, clean, sans-serif; + /*font-family: "Lucida Sans Unicode", "Lucida Grande", sans-serif;*/ + /*font-family: "Trebuchet MS", Helvetica, sans-serif;*/ + /*font-family: Verdana, Geneva, sans-serif;*/ + /*font-family: Tahoma, Geneva, sans-serif;*/ + /*font-family: Baskerville, 'Times New Roman', Times, serif;*/ + + padding:1em; + font-size: 14px; + //font-weight:300; + line-height: 20px; + + //margin:10em; + //max-width:42em; + margin: 0 auto; + width: 700px; + + background:#fefefe; + color:#222; +} + +h1, h2, h3, h4, h5, h6 { + font-weight: bold; + //margin: 2em 0px 15px 0px; +} + +h1 { + color: #000; + font-size: 2em; +} + +h2 { + font-size: 2em; +} + +h3 { + font-size: 1.6em; +} + +h4 { + font-size: 1.3em; +} + +h5 { + font-size: 1em; +} + +h6 { + color: #777777; + background-color: inherit; + font-size: 1em; +} + +hr { + height: 0.2em; + border: 0; + color: #CCCCCC; + background-color: #CCCCCC; +} + +blockquote { + border-radius: 3px; + background-color: #DDD; + color: inherit; + padding: 0 0.5em; +} + +code, pre { + border-radius: 3px; + background-color: #F8F8F8; + color: inherit; +} + +code { + border: 1px solid #EAEAEA; + margin: 0 2px; + padding: 0 5px; +} + +pre { + border: 1px solid #CCCCCC; + line-height: 1.25em; + overflow: auto; + padding: 6px 10px; +} + +pre > code { + border: 0; + margin: 0; + padding: 0; +} + +/* ---- Links (anchors) ---- */ + +a { + color: #4183C4; + background-color: inherit; + /* Keep links clean. On screen, they are colored; in print, they do nothing anyway. */ + text-decoration: none; +} + +@media screen { + a:hover { + /* On hover, we indicate a bit more that it is a link. */ + text-decoration: underline; + } +} + +@media print { + a { + /* In print, a colored link is useless, so un-style it. */ + color: black; + background: transparent; + } + + a[href^="http://"]:after, a[href^="https://"]:after { + /* However, links that go somewhere else, might be useful to the reader, + so for http and https links, print the URL after what was the link + text in parens + */ + content: " (" attr(href) ") "; + font-size: 90%; + } +} + +/* ---- Images ---- */ +img + { + /* Let it be inline left/right where it wants to be, but verticality make + it in the middle to look nicer, but opinions differ, and if in a multi-line + paragraph, it might not be so great. + */ + vertical-align: middle; + max-width: 100%; + } + +div.figure /* Pandoc figure-style image */ + { + /* Center the image and caption */ + margin-left: auto; + margin-right: auto; + text-align: center; + font-style: italic; + } + +p.caption /* Pandoc figure-style caption within div.figure */ + { + /* Inherits div.figure props by default */ + } + +div#header, header { + /* Put border on bottom. Separates it from TOC or body that comes after it. */ + border-bottom: 1px solid #aaa; + margin-bottom: 0.5em; +} + +/* Pandoc title header (h1.title) */ +.title { + font-size: 3em; + text-align: center; +} + +/* Pandoc author(s) and date headers (h2.author and h3.date) */ +.author, .date { + text-align: center; + font-size: 1.2em; + margin: 2px; +} + +nav#TOC ul li { + margin: 0; +} + +div#TOC, nav#TOC { + /* Put border on bottom to separate it from body. */ + border-bottom: 1px solid #aaa; + margin-bottom: 0.5em; +} + +@media print { + div#TOC, nav#TOC { + /* Don't display TOC in print */ + display: none; + } +} + +/* ---- Tables ---- */ + +/* A clean textbook-like style with horizontal lines above and below and under + the header. Rows highlight on hover to help scanning the table on screen. +*/ +table { + border-collapse: collapse; + border-spacing: 0; /* IE 6 */ + + border-bottom: 2pt solid #000; + border-top: 2pt solid #000; /* The caption on top will not have a bottom-border */ + + /* Center */ + margin-left: auto; + margin-right: auto; + margin-top: 1em; + margin-bottom: 1em; +} + +thead /* Entire table header */ + { + border-bottom: 1pt solid #000; + background-color: #eee; /* Does this BG print well? */ + } + +tr.header /* Each header row */ + { + } + +tbody /* Entire table body */ + { + } + +/* Table body rows */ + +tr { + } +tr.odd:hover, tr.even:hover /* Use .odd and .even classes to avoid styling rows in other tables */ + { + background-color: #eee; + } + +/* Odd and even rows */ +tr.odd {} +tr.even {} + +td, th /* Table cells and table header cells */ + { + vertical-align: top; /* Word */ + vertical-align: baseline; /* Others */ + padding-left: 0.5em; + padding-right: 0.5em; + padding-top: 0.2em; + padding-bottom: 0.2em; + } + +/* Removes padding on left and right of table for a tight look. Good if thead has no background color*/ +/* +tr td:last-child, tr th:last-child + { + padding-right: 0; + } +tr td:first-child, tr th:first-child + { + padding-left: 0; + } +*/ + +th /* Table header cells */ + { + font-weight: bold; + } + +tfoot /* Table footer (what appears here if caption is on top?) */ + { + } + +caption /* This is for a table caption tag, not the p.caption Pandoc uses in a div.figure */ + { + caption-side: top; + border: none; + font-size: 0.9em; + font-style: italic; + text-align: center; + margin-bottom: 0.3em; /* Good for when on top */ + padding-bottom: 0.2em; + } + +/* ---- Definition lists ---- */ + +dl /* The whole list */ + { + border-top: 2pt solid black; + padding-top: 0.5em; + border-bottom: 2pt solid black; + } + +dt /* Definition term */ + { + font-weight: bold; + } + +dd+dt /* 2nd or greater term in the list */ + { + border-top: 1pt solid black; + padding-top: 0.5em; + } + +dd /* A definition */ + { + margin-bottom: 0.5em; + } + +dd+dd /* 2nd or greater definition of a term */ + { + border-top: 1px solid black; /* To separate multiple definitions */ + } + +/* ---- Footnotes ---- */ + +a.footnote, a.footnoteRef { /* Pandoc, MultiMarkdown footnote links */ + //font-size: small; + vertical-align: text-top; +} + +a[href^="#fnref"], a.reversefootnote /* Pandoc, MultiMarkdown, ?? footnote back links */ + { + } + +@media print + { + a[href^="#fnref"], a.reversefootnote /* Pandoc, MultiMarkdown */ + { + /* Don't display these at all in print since the arrow is only something to click on */ + display: none; + } + } + +div.footnotes /* Pandoc footnotes div at end of the document */ + { + } + +div.footnotes li[id^="fn"] /* A footnote item within that div */ + { + } + +/* You can class stuff as "noprint" to not print. + Useful since you can't set this media conditional inside an HTML element's + style attribute (I think), and you don't want to make another stylesheet that + imports this one and adds a class just to do this. +*/ + +@media print + { + .noprint + { + display:none; + } + } + +.highlight { + background-color: #FF0; +} \ No newline at end of file diff --git a/img/quality-box.png b/img/quality-box.png new file mode 100644 index 0000000..70b6669 Binary files /dev/null and b/img/quality-box.png differ diff --git a/img/tweepy.svg b/img/tweepy.svg new file mode 100644 index 0000000..d0fe141 --- /dev/null +++ b/img/tweepy.svg @@ -0,0 +1 @@ +tweepytweepy \ No newline at end of file diff --git a/img/twitter-api1.1-badge.svg b/img/twitter-api1.1-badge.svg new file mode 100644 index 0000000..2b0fbad --- /dev/null +++ b/img/twitter-api1.1-badge.svg @@ -0,0 +1 @@ +API version: v1.1API versionv1.1 \ No newline at end of file