mirror of
https://codeberg.org/vlw/misskey-microblogger.git
synced 2025-09-13 19:03:41 +02:00
doc(feat): add README
This commit is contained in:
parent
ac5b9f3955
commit
3dc25ee994
1 changed files with 254 additions and 0 deletions
254
README.md
Normal file
254
README.md
Normal file
|
@ -0,0 +1,254 @@
|
||||||
|
# Misskey Microblogger
|
||||||
|
|
||||||
|
This is a bot for Misskey (and compatible forks) that simulates a whole community of independent microbloggers with posts, reactions, and replies. Users have unique personalities, friend groups, partners, and even enemies to whom they will act and respond differently to, sometimes not at all.
|
||||||
|
|
||||||
|
----
|
||||||
|
|
||||||
|
[**Live (Sharkey) demo instance**](https://misskey-microblogger.sites.vlw.se)
|
||||||
|
|
||||||
|
----
|
||||||
|
|
||||||
|
## Background
|
||||||
|
I have never been into "microblogging" personally and it really confuses and amazes me when I see individuals able to gain popularity by consistently putting their current-thoughts-on-whatever into a short text dump and send it out into the ether for others to read on platforms like Ex-Twitter or BlueSky.
|
||||||
|
|
||||||
|
Recently, I learned about the existance of this "interplanetary microblogging platform" called Misskey, which turned my thoughts on microblogging on its head! Misskey makes it really easy to browse recent public posts from all users, across federated instances - something they call the "global timeline". I saw the complete opposite side of microblogging, there were so many people with varying backgrounds and ideas, but had little to no following. They were seemingly posting random thoughts and pictures about their interests to.. no one, everyone? Seeing this is what made me inspired to make this program. What if I could have a bunch of users with different personalities and circles interact with each other's posts about.. anything.
|
||||||
|
|
||||||
|
What if I could make up a language of randomly picked words that allowed just enough information about the tone, mood, and type of sentence to be derived for other users to react and reply accordingly. The words themselves don't mean much, it's more about who says something and how they say it that influences how other users respond.
|
||||||
|
|
||||||
|
# Get started
|
||||||
|
|
||||||
|
## Installation
|
||||||
|
You'll need Python 3.10+ with pip installed.
|
||||||
|
|
||||||
|
1. **Clone the repo**
|
||||||
|
```sh
|
||||||
|
git clone https://codeberg.org/vlw/misskey-microblogger --depth 1
|
||||||
|
```
|
||||||
|
|
||||||
|
2. **Install dependencies**
|
||||||
|
```sg
|
||||||
|
pip install -r requirements.txt
|
||||||
|
```
|
||||||
|
|
||||||
|
## The config files
|
||||||
|
|
||||||
|
This program has two types of config files. There's the "global" config which contain settings for the program iteself, and then there are the "user" config files. These contain settings for each individual user this bot will control.
|
||||||
|
|
||||||
|
## Global config
|
||||||
|
|
||||||
|
1. **Copy config file**
|
||||||
|
```sh
|
||||||
|
cp -p .config.example.json .config.json
|
||||||
|
```
|
||||||
|
|
||||||
|
2. **Edit config**
|
||||||
|
```json
|
||||||
|
{
|
||||||
|
"server": {
|
||||||
|
// Base URL of the target Misskey instance
|
||||||
|
"url": str "http://localhost:3000"
|
||||||
|
},
|
||||||
|
"global": {
|
||||||
|
// A number between 0-100 that will be rolled against each minute to check if ANY activity at all should be performed this minute.
|
||||||
|
"activity": int 100
|
||||||
|
},
|
||||||
|
// Array of username strings. Usernames in this list has bot activity enabled.
|
||||||
|
"active_users": list<str> []
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### User config files
|
||||||
|
|
||||||
|
----
|
||||||
|
|
||||||
|
[**I recommend that you check out my example fork of this repository. It contains configs of 100 randomly generated users.**](https://git.vlw.se/config/misskey-microblogger-demo/src/branch/master/data/users)
|
||||||
|
|
||||||
|
----
|
||||||
|
|
||||||
|
### (Option 1) Manual (best result)
|
||||||
|
|
||||||
|
1. **Create users config directory**
|
||||||
|
```
|
||||||
|
mkdir data/users
|
||||||
|
```
|
||||||
|
2. **Create user config file from template**
|
||||||
|
```
|
||||||
|
cp -p data/users_template.json data/users/<example>.json
|
||||||
|
```
|
||||||
|
Replace `<example>` with the **username** of your user.
|
||||||
|
|
||||||
|
3. **Edit user config**
|
||||||
|
```json
|
||||||
|
{
|
||||||
|
// Replace with the API key generated from Misskey's GUI. The key needs all privileges.
|
||||||
|
"key": str "<API_KEY>",
|
||||||
|
"online": {
|
||||||
|
// An array of objects containing the user's potential "active hours"
|
||||||
|
"intervals": list<dict> [
|
||||||
|
{
|
||||||
|
// The user will start being active at a random time between from and to.
|
||||||
|
"start": {
|
||||||
|
"from": float<2.2> 0.00, // 24-hour time. Example: 14.40 = 2:40 PM
|
||||||
|
"to": float<2.2> 0.00 // 24-hour time. Example: 14.40 = 2:40 PM
|
||||||
|
},
|
||||||
|
// The user will stop being active at a random time between from and to
|
||||||
|
"end": {
|
||||||
|
"from": float<2.2> 0.00, // 24-hour time. Example: 14.40 = 2:40 PM
|
||||||
|
"to": float<2.2> 0.00 // 24-hour time. Example: 14.40 = 2:40 PM
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"actions": {
|
||||||
|
// User posting a new note
|
||||||
|
"posts": {
|
||||||
|
// User posting a public note
|
||||||
|
"public": {
|
||||||
|
// Likelyhood that the user will post a new public note
|
||||||
|
"percent": int 0 // Value is weighted, please see:
|
||||||
|
// Time in seconds before the user can post another public note since last
|
||||||
|
"cooldown": int 100
|
||||||
|
},
|
||||||
|
// User sending another user a direct message
|
||||||
|
"specified": {
|
||||||
|
// Likleyhood that user will send a direct message to another user from relationship
|
||||||
|
"percent": Relationships<Enum> {
|
||||||
|
"partner": int<3> 0,
|
||||||
|
"friends": int<3> 0,
|
||||||
|
"neutral": int<3> 0,
|
||||||
|
"enemies": int<3> 0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
// User replying to an existing note
|
||||||
|
"replies": {
|
||||||
|
"public": {
|
||||||
|
// Likelyhood that user will reply to a public note by another user from relationship
|
||||||
|
"percent": Relationships<Enum> {
|
||||||
|
"partner": int<3> 0,
|
||||||
|
"friends": int<3> 0,
|
||||||
|
"neutral": int<3> 0,
|
||||||
|
"enemies": int<3> 0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"specified": {
|
||||||
|
// Likelyhood that user will reply to a direct message from another user given relationship
|
||||||
|
"percent": Relationships<Enum> {
|
||||||
|
"partner": int<3> 0,
|
||||||
|
"friends": int<3> 0,
|
||||||
|
"neutral": int<3> 0,
|
||||||
|
"enemies": int<3> 0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"reacts": {
|
||||||
|
// Likelyhood that user will react to a public note from another user given relationship
|
||||||
|
"percent": Relationships<Enum> {
|
||||||
|
"partner": int<3> 0,
|
||||||
|
"friends": int<3> 0,
|
||||||
|
"neutral": int<3> 0,
|
||||||
|
"enemies": int<3> 0
|
||||||
|
},
|
||||||
|
// Override reaction symbol of src.Users.Users.DEFAULT_REACTION for a public note from another user given relationship
|
||||||
|
"preferred_reactions": Relationships<Enum> {
|
||||||
|
"partner": str<1>|None "",
|
||||||
|
"friends": str<1>|None "",
|
||||||
|
"neutral": str<1>|None "",
|
||||||
|
"enemies": str<1>|None ""
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
// Various personality stats. Users with matching stats have higher probability to follow same personality patterns when conversing
|
||||||
|
"personality": {
|
||||||
|
"tone": {
|
||||||
|
"probility" NoteTones<Enum> {
|
||||||
|
"informal": int<3> 0,
|
||||||
|
"formal": int<3> 0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"tone": {
|
||||||
|
"probility" NoteMoods<Enum> {
|
||||||
|
"funny": int<3> 0,
|
||||||
|
"decent": int<3> 0,
|
||||||
|
"annoyed": int<3> 0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"type": {
|
||||||
|
"probility" NoteTypes<Enum> {
|
||||||
|
"question": int<3> 0,
|
||||||
|
"exaggerated": int<3> 0,
|
||||||
|
"statement": int<3> 0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"note": {
|
||||||
|
"text_length": {
|
||||||
|
// note.text_length.average will always fluctuate plus or minus a random amount between note.text_length.average and this
|
||||||
|
"flux": int 0,
|
||||||
|
// The average text length (in words) this user will write. It natually fluctuates between ~6 words due to grammar requirements
|
||||||
|
"average": int 0
|
||||||
|
}
|
||||||
|
},
|
||||||
|
// Lists of unidirectional relationships for this user. Add this user's username to other user's config if relationship should be mutual.
|
||||||
|
// Any username not mentioned in any of these lists will be considered as src.Enums.RelationshipType.NEUTRAL
|
||||||
|
"relationships": RelationshipType<Enum> {
|
||||||
|
// List of username strings that this user considers to be friends
|
||||||
|
"friends": list<str> [],
|
||||||
|
// List of username strings that this user considers to be enemies
|
||||||
|
"friends": list<str> [],
|
||||||
|
// A string or null that this user considers to be their partner
|
||||||
|
"partner": str|None ""
|
||||||
|
}
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
4. **Add username to global config**
|
||||||
|
Activate your user by adding their username to the `active_users` array in `.config.json`
|
||||||
|
```json
|
||||||
|
// .config.json
|
||||||
|
{
|
||||||
|
...
|
||||||
|
"active_users": [
|
||||||
|
"<example_username>"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### (Option 2) Generate random users (will generate unhinged users and circles)
|
||||||
|
|
||||||
|
1. **Run `generate.py`**
|
||||||
|
```
|
||||||
|
python3 generate.py <int NUMBER_OF_USERS>
|
||||||
|
```
|
||||||
|
Replace `<int NUMBER_OF_USERS>` with the amount of users you wish to generate. [The default amount](https://codeberg.org/vlw/misskey-microblogger/src/branch/master/generate.py#L11) will be used if no argument is specified
|
||||||
|
|
||||||
|
2. **Create user and generate API key**
|
||||||
|
```
|
||||||
|
Generating user: 1
|
||||||
|
1. Create username: <RANDOM_USERNAME>
|
||||||
|
2. Paste API key:
|
||||||
|
```
|
||||||
|
You'll unfortunately have to create the user, and API key yourself through Misskey's GUI. Misskey doesn't provide an API endpoint for this.
|
||||||
|
|
||||||
|
Create a user with the randomly generated username given under `<RANDOM_USERNAME>`. Log in as that user and generate an API key with all privileges enabled. Copy the API key and paste it into the CLI prompt.
|
||||||
|
|
||||||
|
----
|
||||||
|
|
||||||
|
[**I created a crappy Jitbit macro that you can run in a VM to automate the whole process**](https://git.vlw.se/gists/misskey-microblogger-macro)
|
||||||
|
|
||||||
|
----
|
||||||
|
|
||||||
|
3. **Repeat**
|
||||||
|
Repeat until you've generated your users. The program will then generate random relationships between your users. This process can take a while as a lot of follow requests are made to Misskey when the relationship binding is done.
|
||||||
|
|
||||||
|
## Start the bot
|
||||||
|
Start the `run.py` script to run though a single session.
|
||||||
|
|
||||||
|
```sh
|
||||||
|
python3 run.py
|
||||||
|
```
|
||||||
|
|
||||||
|
I recommend that you set up automation that runs this script once every minute. Here's a crontab example:
|
||||||
|
```
|
||||||
|
* * * * * cd /path/to/misskey-microblogger && /usr/bin/python3 /path/to/misskey-microblogger/run.py
|
||||||
|
```
|
Loading…
Add table
Reference in a new issue