Coder Social home page Coder Social logo

ishar-web's Introduction

About

Ishar is an online text-adventure RPG (commonly called a multi-user dungeon, or MUD) set in a large, unique world of fantasy and magic.

Players do battle with fearsome foes (and sometimes each other) to win great wealth and wrest rare prizes from the treasure hoards or bloody corpses of their enemies.

This page is simply the programming code - for the website, for the game.

Play Ishar MUD

If you are interested in playing Ishar MUD, please do not hesitate to visit the website, our frequently asked questions, or jump right in with the getting started guide, or even by downloading a MUD client!

More Information

The website is using a combination of Python, Django, MariaDB, nginx, and gunicorn, among other things.

The MUD itself is written in C, while relying upon "Mocha".

ishar-web's People

Contributors

ericoc avatar tyler-jacob-f avatar hyoungsooo avatar dependabot[bot] avatar

Stargazers

Etienne Jacquot avatar  avatar

Watchers

 avatar  avatar

Forkers

hyoungsooo

ishar-web's Issues

Reading helptab

Help File

Reading the help (helptab) file is very complicated and messy...

Two possible solutions to simplify things would be to:

  1. Migrate the helptab file to the database.
  2. Implement a custom Django Manager to read the existing helptab file.

Database

  • Should each help topic be a row in a single "help_topics" database table?
    • Create a help_topics table...

    • Each row would be a single unique help topic.

      • Columns would be similar to:
        • help_topic_id
          • int(10) primary key autoincrement not null
        • name
          • varchar(64) unique key not null
        • body
          • text not null
        • aliases
          • varchar(64) (comma-separate?)
        • syntax
        • minimum
        • saves
        • class
        • level
          • varchar(64) ?
    • Help topics could probably be edited from Django administrative interface.

Manager

  • Custom Django Manager to read the help topics from the helptab file?
    • Each object would represent a single unique help topic.
      • Commands
      • Spell Wizardlock
      • Inventory
      • etc.
    • Subsequently, each help_topic object would have (mostly string) attributes/properties similar to:
      • name
      • body
      • aliases
        • list/tuple of strings
      • syntax
      • minimum
      • saves
      • class
      • level

USE_I18N

I18N

Admin language translation support

This would have no real benefit other than improving my understanding of how the Django translation/language support works. This definitely is not a priority for the website at all.

It would be cool to wrap the help_text and verbose_name arguments throughout the models, as well as any admin text, using from django.utils.translation import gettext_lazy as _:

Challenges

https://staging.isharmud.com/challenges/

While the challenges page is working very well, I would like to eventually link the name of each player in the "winner_desc" column to their appropriate /player/ page (to replicate the functionality of the existing Flask website).

Patches

There needs to be a good way to upload a PDF patch file (via Django Admin, as God only), and have the file available immediately in a valid location for serving static content via nginx.

Quest rewards primary key

Problem

In order to administrate "Quest Rewards" from the Django administration interface, the quest_rewards table needs a new primary key column.

root@isharmud:~# mysql ishar -sse "SHOW CREATE TABLE quest_rewards \G;"
*************************** 1. row ***************************
       Table: quest_rewards
Create Table: CREATE TABLE `quest_rewards` (
  `reward_num` int(11) NOT NULL,
  `reward_type` tinyint(2) NOT NULL,
  `quest_id` int(11) unsigned NOT NULL,
  `class_restrict` tinyint(4) NOT NULL DEFAULT -1,
  PRIMARY KEY (`reward_num`,`quest_id`),
  KEY `quests_rewards_quest_id` (`quest_id`),
  CONSTRAINT `quests_rewards_quest_id` FOREIGN KEY (`quest_id`) REFERENCES `quests` (`quest_id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci

I actually removed the primary key definition on the ishar_test.quest_rewards MySQL table, just to see if it made a difference:

root@isharmud:~# mysql ishar_test -sse "SHOW CREATE TABLE quest_rewards \G;"
*************************** 1. row ***************************
       Table: quest_rewards
Create Table: CREATE TABLE `quest_rewards` (
  `reward_num` int(11) NOT NULL,
  `reward_type` tinyint(2) NOT NULL,
  `quest_id` int(11) NOT NULL,
  `class_restrict` tinyint(4) NOT NULL DEFAULT -1,
  KEY `quests_rewards_quest_id` (`quest_id`),
  CONSTRAINT `quests_rewards_quest_id` FOREIGN KEY (`quest_id`) REFERENCES `quests` (`quest_id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci

Cause

However, it turns out, "only single-column primary keys are supported" within Django...

https://docs.djangoproject.com/en/dev/faq/models/#do-django-models-support-multiple-column-primary-keys

"Do Django models support multiple-column primary keys?

"No. Only single-column primary keys are supported."

Temporary Half-Fix

Currently, I have primary_key=True set on the reward_num column within the Django model, in order to have the "Quests" page on the Django administration interface displaying at all:

https://github.com/IsharMud/ishar-web/blob/django/ishar/apps/quest/models/reward.py#L15

However, edits to quest rewards likely fail with various 500-level error codes at this time.

Solution

I am still not sure of the right move here, but I suspect that our best option may be to copy the way that "quest_steps" works - since there is a primary key of step_id.

https://github.com/IsharMud/ishar-web/blob/django/ishar/apps/quest/models/step.py

As far as I am aware, management of Quest Steps does indeed work properly and correctly in the Django administration interface.

root@isharmud:~# mysql ishar -sse "SHOW CREATE TABLE quest_steps \G;"
*************************** 1. row ***************************
       Table: quest_steps
Create Table: CREATE TABLE `quest_steps` (
  `step_id` tinyint(4) NOT NULL AUTO_INCREMENT,
  `step_type` tinyint(4) NOT NULL,
  `target` int(11) NOT NULL,
  `num_required` int(11) NOT NULL,
  `quest_id` int(11) unsigned NOT NULL,
  `time_limit` int(11) NOT NULL DEFAULT -1,
  `mystify` tinyint(1) NOT NULL DEFAULT 0,
  `mystify_text` varchar(80) NOT NULL DEFAULT '',
  PRIMARY KEY (`step_id`),
  KEY `quest_steps_quest_id` (`quest_id`),
  CONSTRAINT `quest_steps_quest_id` FOREIGN KEY (`quest_id`) REFERENCES `quests` (`quest_id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB AUTO_INCREMENT=71 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci
root@isharmud:~# mysql ishar_test -sse "SHOW CREATE TABLE quest_steps \G;"
*************************** 1. row ***************************
       Table: quest_steps
Create Table: CREATE TABLE `quest_steps` (
  `step_id` tinyint(4) NOT NULL AUTO_INCREMENT,
  `step_type` tinyint(4) NOT NULL,
  `target` int(11) NOT NULL,
  `num_required` int(11) NOT NULL,
  `quest_id` int(11) NOT NULL,
  `time_limit` int(11) NOT NULL DEFAULT -1,
  `mystify` tinyint(1) NOT NULL DEFAULT 0,
  `mystify_text` varchar(80) NOT NULL DEFAULT '',
  PRIMARY KEY (`step_id`),
  KEY `quest_steps_quest_id` (`quest_id`),
  CONSTRAINT `quest_steps_quest_id` FOREIGN KEY (`quest_id`) REFERENCES `quests` (`quest_id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB AUTO_INCREMENT=72 DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci

DataTables overflowing

DataTables on the "leaders" and "challenges" pages are overflowing the layout (especially on mobile); for example:

Screenshot 2024-07-07 at 2 24 02 PM

Leaderboard broken if a player has >1,000 total_renown

Screenshot 2024-02-10 at 3 52 57 PM

image

The https://isharmud.com/leaders/#leaders ("Leader board") page blank for classic players because the Toetums player has >1000 renown. Django templating is formatting the value for GridJS with an extra comma (as 1,001, rather than 1001). This likely is currently only breaking rendering of the page client-side when Toetums appears within the GridJS data, but would affect other numeric values beyond total_renown as well.

Screenshot 2024-02-10 at 3 53 49 PM

Split each model (and admin) into its own file

Model/Admin Separation

It would be nice to get rid of any instances of multiple Django database model classes in a single models.py file.

I would prefer to create admin/ and models/ folders in each "app" to split things up. I would prefer to place any inline-administration classes in their own files as well.

Hopefully this should not be too difficult and can easily be done by the end of season 6?

Include Shaman in settings.CLASS_STATS

With the introduction of the Shaman class, there is a need to include this new class within the Django settings.CLASS_STATS (settings.example.py):

# Order of character statistics based on player class
CLASS_STATS = {
"Warrior": (
"Strength", "Agility", "Endurance", "Willpower", "Focus", "Perception"
),
"Rogue": (
"Agility", "Perception", "Strength", "Focus", "Endurance", "Willpower"
),
"Cleric": (
"Willpower", "Strength", "Perception", "Endurance", "Focus", "Agility"
),
"Magician": (
"Perception", "Focus", "Agility", "Willpower", "Endurance", "Strength"
),
"Necromancer": (
"Focus", "Willpower", "Perception", "Agility", "Strength", "Endurance"
),
# Alphabetic as last resort
None: (
"Agility", "Endurance", "Focus", "Perception", "Strength", "Willpower"
)
}

player_stats property of Player model (ishar/apps/players/models/__init__.py):

# Put players stats in appropriate order, based on their class.
stats_order = settings.CLASS_STATS.get(None)
class_name = self.common.player_class.class_name
if class_name in settings.CLASS_STATS:
stats_order = settings.CLASS_STATS.get(class_name)
for stat_order in stats_order:
stats[stat_order] = players_stats[stat_order]

Including Shaman in settings.py will return Shaman players' statistics sorted appropriately, based upon the value of CLASS_STATS.

Permissions

Use Django Permissions

I would like to translate the existing concept of using players levels to Django permissions:

Current

If an account has a player with a level in settings.IMMORTAL_LEVELS, that account (and that player) is considered to be an "immortal", and subsequently "is_staff" is "True" to Django.

Players

Immortal Levels

settings.IMMORTAL_LEVELS is a dictionary with the key being the player level and the value of that key being the in-game type/rank of immortal:

# Player immortal levels
IMMORTAL_LEVELS = {
    26: 'God',
    25: 'Forger',
    24: 'Eternal',
    23: 'Artisan',
    22: 'Immortal',
    21: 'Consort'
}

Accounts

A player character's level indicating status as an "immortal"-type player is used to determine whether the users account is a staff member (is_staff) or otherwise an administrator allowing them to log in to the Django administration portal:

If there is an immortal-type player within the users account, they are appropriately considered a staff member or administrator.

Solution

Figure out what I do not know by repeatedly re-reading https://docs.djangoproject.com/en/dev/topics/auth/default/#permissions-and-authorization to implement actual Django permissions correctly...

Multiple columns next season

The next upcoming season introduces multiple columns into various tables of the MySQL database:

  • accounts.immortal_level
  • skill_components.component_count
  • skills.special_int
  • skills.obj_display

staging...main

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.