# Eaglercraft 1.6.4

![eagler](eagler.png)
:-:
Eaglercraft is real Minecraft 1.6.4 that you can play in any regular web browser. That includes school chromebooks, it works on all chromebooks. It currently only supports multiplayer.

# Quick Start

### Client: [github.com/catfoolyou/Project164](javascript/)

### Offline Client Download: [Offline_Download_Version.html](javascript/Eaglercraft_1.6.4_Offline.html)

**(right click the link and press 'Save link as...' to download the file)**

# Table Of Contents:
| [Multiplayer](#Multiplayer)                                                     | [Others](#Others)                                     |
|---------------------------------------------------------------------------------|-------------------------------------------------------|
| [Self hosting (singleplayer)](#Singleplayer?)                       | [Plugin Development](#Plugin-Development)             |
| [Creating a Server - Bukkit](#Creating-a-server---Bukkit)                       | [Compiling](#Compiling)                               |
| [Creating a Server - EaglercraftBungee](#Creating-a-server---EaglercraftBungee) | [Creating a resource pack](#Creating-a-resource-pack) |
| [Creating a Client](#Creating-a-Client)                                         | [Contributing](#Contributing)                         |
| [EaglercraftBungee Configuration](#EaglercraftBungee-Configuration)             |                                                       |
| [Creating a Reverse Proxy - NGINX](#Creating-a-Reverse-Proxy---NGINX)           |                                                       |
| [NGINX Configuration](#NGINX-Configuration)                                     |                                                       |

## Singleplayer?

You can self host a server (see the "How to make a server" section below), and connect to `ws://localhost:25565` in your client and play one there, it will be essentially an integrated server but with extra steps. 
You're pretty much Shit Outta Luck if you're on a chromebook though. 

## Issues?

I got tired of closing duplicate 'how to maek sever' issues almost every day so I disabled it because honestly I don't really care anymore, find me on the Eagler discord and ping me if you've got an issue to report that you are confident can be backed up with source code

## How to make a server

There are ***multiple parts*** **to a server**, mainly consisting of a **regular 1.6.4 Bukkit server**, and a **modified version of Bungeecord** called **EaglercraftBungee**, which on top of the regular Bungeecord functionality, it translates WebSocket connections to raw TCP connections which Bukkit can understand.

You may also want to set up your own **client**, allowing you to *control default server listings, resource packs, and an overall faster connection due to less load.*

If you want to use a domain for your server, **a reverse proxy** can be set up to enable extra functionality within EaglercraftBungee. **NGINX** is recommended, and a tutorial is included **[here](#Creating-a-Reverse-Proxy---NGINX)**. **This is optional, and can be skipped by just connecting with the IP.**

### If Gitpod/Github Codespaces are acceptable, you can use this:

### [https://github.com/catfoolyou/Eagler-Server-1.6.4](https://github.com/catfoolyou/Eagler-Server-1.6.4)

## Creating a server - Bukkit

1. **Check if Java is installed.** You can download it from [https://www.java.com/en/download/](https://www.java.com/en/download/)
2. Download the [mp-server.zip](mp-server.zip) file from this repository
3. Extract the ZIP file you downloaded to a new folder
4. Open the new folder, go into the `java/bukkit_command` folder
5. Open a new terminal and run `java -jar craftbukkit-1.6.4-R2.0.jar` to start the bukkit server
6. To add some bukkit plugins, download the plugin's JAR file for CraftBukkit 1.6.4 and place it in `java/bukkit_command/plugins`
(See [https://github.com/lax1dude/eaglercraft-plugins/](https://github.com/lax1dude/eaglercraft-plugins/) to download some supported plugins)

## Creating a server - EaglercraftBungee
1. In the same new folder, go into the `java/bungee_command` folder
2. In Windows, double-click `run.bat`. It should open a second terminal window  
Keep both the first and second terminal window you opened, just minimize them, don't close
3. On macOS or Linux, repeat step 5 in [Creating a Server - Bukkit](#Creating-a-server---Bukkit), but navigate to `java/bungee_command` this time and run `bungee-dist.jar`
4. To add some bungee plugins, download the plugin's JAR file and place it in `java/bungee_command/plugins`

There are alot more configurations in bungeecord, but this should set you up

**Your server is now ready.** Visit any client, and go to 'Multiplayer' from the main menu. Select 'Direct Connect', type `ws://127.0.0.1:25565` and press 'Join Server'
**It should allow you to connect, if not, check the two terminal windows for errors**


### If voice chat causes moderation problems, set `voice_enabled: false` in config.yml

**To enable the /login and /register commands in EaglercraftBungee, you can edit this portion of config.yml**

```yaml
authservice:
  enabled: false
  register_enabled: true
  authfile: auths.db
  ip_limit: 0
  join_messages:
  - '&3Welcome to my &aEaglercraftBungee &3server!'
  login_timeout: 30
```

- `enable` Turns login commands on and off

- `register_enabled` Turns register command on and off

- `authfile` Sets the authentication database file, which is **compatible with AuthMe**

- `ip_limit` Sets the max number of registrations per IP, 0 = unlimited

- `join_messages` List of messages to show the player when they join

- `login_timeout` Sets how many seconds players have to log in before they are kicked

**EaglercraftBungee has a built in domain blacklist that updates automatically, you can disable it by setting this in config.yml:**

```yaml
enable_web_origin_blacklist: false
```

**To block all clients on replit from joining, set this to true in config.yml:**

```yaml
origin_blacklist_block_replit_clients: true
```

**To block all offline-download clients, set this to true in config.yml:**

```yaml
origin_blacklist_block_offline_download: true
```

**To block the debug runtime (or other desktop clients), set this to true in config.yml:**

```yaml
origin_blacklist_block_missing_origin_header: true
```

**To add your own blacklisted domains**, create a file called `origin_blacklist.txt` in your bungeecord directory and put the regular expressions inside, one on each line. There 's also a `domain` command in the console to view a player's domain, and a `block-domain` and `block-domain-name` and `unblock-domain` command to manage the local `origin_blacklist.txt` from the bungee console (if you don't know how to edit a file on your own). The list reloads automatically when changes to the file are detected.

### To configure bungee to block connections from all clients except your own, set this option:

```yaml
origin_blacklist_use_simple_whitelist: true
```

### Then, add your domain to `origin_blacklist_simple_whitelist` like this:

```yaml
origin_blacklist_simple_whitelist:
- type the name of your client's domain here
```

### Then, unless still you want it as an option for your players, disable the offline download so hackers don't use it to bypass the whitelist, as it is not blocked in whitelist mode by default:

```yaml
origin_blacklist_block_offline_download: true
```

### To stop people from using bookmarklets to load a client from a different URL onto your official URL via XXS, add these headers to NGINX:

```
add_header X-Frame-Options "SAMEORIGIN";
add_header Referrer-Policy "strict-origin";
add_header X-XSS-Protection "1; mode=block";
add_header Content-Security-Policy "default-src 'self' 'unsafe-inline'; img-src 'self' 'unsafe-inline' data: blob:; connect-src 'self' ws: wss:; upgrade-insecure-requests";
```

(not fully tested, excuse the scroll bar)

### To use IP bans and rate limiting, enable `forward_ip` and pass a X-Real-IP header from your proxy to the bungeecord's websocket port

Nginx example: add `proxy_set_header X-Real-IP $remote_addr` to your proxy configuration

**The server has built in DoS protection, reset it via typing 'eag-ratelimit reset' in the bungee console**

```yaml
ratelimit:
  ip:
    enable: true
    period: 90
    limit: 60
    limit_lockout: 80
    lockout_duration: 1200
    exceptions: []
```

- `enable` enable rate limiting

- `period` and `limit` set the number of requests (`limit`) can be made in (`period`) number of seconds

- `limit_lockout` and `lockout_duration` set the number of requests (`limit_lockout`) that can be made in (`period`) seconds before the IP is blocked for `lockout_duration` number of seconds

- `exceptions` a list of IP addresses that should never get rate limited. **Local IPs like 127.0.0.1 and 192.168.\*.\* and such are set as exceptions by default**

**you need `forward_ip` configured to use rate limiting, otherwise it will be disabled by default**

### Redirecting the client to a new WebSocket

If you would like to signal the client to disconnect from your bungeecord and reconnect to a different bungeecord, configure an entry in the `servers` part of config.yml like this:

```yaml
test:
  redirect: wss://ServerHere/
  restricted: false
```

In this example, sending a player to the server `test`, such as when they enter a portal or type `/server test`, will trigger their client to disconnect from your bungeecord and then automatically reconnect to `wss://ServerHere/` as if it was entered via "Direct Connect"

## Creating a Reverse Proxy - NGINX

Here is a quick crash course of setting up NGINX on Linux, specifically on Debian distributions.

Here are some google searches for other distributions:

- [Windows](https://www.google.com/search?q=set+up+nginx+on+windows)
- [Mac](https://www.google.com/search?q=set+up+nginx+on+mac)
- [Linux - Arch](https://www.google.com/search?q=set+up+nginx+on+arch)
- [Linux - Fedora](https://www.google.com/search?q=set+up+nginx+on+fedora)

1. Open up your terminal, and run  
	``sudo apt update``
  and
	``sudo apt install nginx``
2. Open any web browser, and search for `localhost` in your search bar. You should see something like this:![Welcome to nginx](https://ubuntucommunity.s3.dualstack.us-east-2.amazonaws.com/optimized/2X/7/7504d83a9fe8c09d861b2f7c49e144ac773f0c0d_2_690x288.png)
3. Navigate to NGINX's configuration with `cd /etc/nginx/sites-enabled`.

4. Create a new configuration file with your domain name, for example `nano eaglercraft.example.com`

5. Paste in the following code into the file. Replace `example.com` with your own domain, and `app_server_address` as the `ip:port` of your EaglercraftBungee server you want the URL to connect to.
```
server {
    listen 80;
    listen [::]:80;

    server_name example.com eaglercraft.example.com;
        
    location / {
        proxy_pass app_server_address;
        include proxy_params;
    }
}
```

6. Now, restart NGINX with `sudo service nginx restart` and you should be good to go!

## NGINX Configuration

### To implement the following configuration, add the lines below the `proxy_pass` line.
- **To stop people from using bookmarklets to load a client from a different URL onto your official URL via XXS, add these headers to NGINX:**

```
add_header X-Frame-Options "SAMEORIGIN";
add_header Referrer-Policy "strict-origin";
add_header X-XSS-Protection "1; mode=block";
add_header Content-Security-Policy "default-src 'self' 'unsafe-inline'; img-src 'self' 'unsafe-inline' data: blob:; connect-src 'self' ws: wss:; upgrade-insecure-requests";
```

- **To use IP bans and rate limiting, add `proxy_set_header X-Real-IP $remote_addr` to your proxy configuration**

### Plugin Development

**To develop a plugin, download [stable-download/java/bungee_command/bungee_dist.jar](https://github.com/lax1dude/eaglercraft/blob/main/stable-download/java/bungee_command/bungee-dist.jar) and add it to the Build Path of your Java IDE. Develop the plugin just like a regular BungeeCord plugin, see [EaglerMOTD](https://github.com/lax1dude/eaglercraft-motd/) for an example.**

**Test your plugin by exporting it as a jar and putting it in the '/plugins' directory of EaglercraftBungee and then clicking 'run.bat'**

### New Events:

- **[net.md_5.bungee.api.event.WebsocketMOTDEvent](https://github.com/lax1dude/eaglercraft/blob/main/eaglercraftbungee/src/main/java/net/md_5/bungee/api/event/WebsocketMOTDEvent.java)**: Triggered when a client or website requests the MOTD

- **[net.md_5.bungee.api.event.WebsocketQueryEvent](https://github.com/lax1dude/eaglercraft/blob/main/eaglercraftbungee/src/main/java/net/md_5/bungee/api/event/WebsocketQueryEvent.java)**: Triggered when a client or website requests a query. This happens when a site opens a text WebSocket to a listener and sends a single string `Accept: <query>` packet. Can be used to provide additional custom statistics to server list sites supporting integrated WebSocket queries

**Register event handlers using the standard BungeeCord** `@EventHandler` **annotation in your** `Listener` **class**

## Compiling

To compile for the web, run the gradle 'generateJavascript' compile target to generate the classes.js file.

The LWJGL runtime is supported, you will need to uncomment the lines `//sourceSets.main.resources.srcDirs += 'src/lwjgl/java/javazoom/jl/decoder'` and `//implementation fileTree(dir: './lwjgl-rundir/', include: '*.jar')` in `build.gradle` as well as changing `"src/teavm/java"` to `"src/lwjgl/java"`
You will then need to run `BuildUnpackDebugJar.sh` (You're pretty much SOL on windows unless you want to compile it manually) 

## Contributing

All I really have to say is, tabs not spaces, and format the code to be like the eclipse auto format tool on factory settings, but also run-on lines of code long enough to go off the screen and single line if statements and other format violations in that category are welcome if it helps enhance the contrast between the less important code and the more important code in a file. Don't commit changes to `javascript/classes.js` or `javascript/classes_server.js` or `javascript/assets.epk` or anything in `stable-download/`. I'll recompile those myself when I merge the pull request.
