3
\$\begingroup\$

I am making a Schema to store items from Wynncraft's API.

See an example assortment of items here:

https://api.wynncraft.com/public_api.php?action=itemDB&search=a

I have not finished making the Schema because I want to know if there's a better way I should approach it:

const mongoose = require('mongoose');
const uniqueValidator = require('mongoose-unique-validator');

const ItemSchema = new mongoose.Schema({
  name: {
    type: String,
    required: true,
    unique: true
  },
  tier: {
    type: String,
    enum: ['Unique', 'Rare', 'Legendary', 'Mythic', 'Set', 'Normal'],
    required: true
  },
  identified: {
    type: Boolean,
    required: true
  },
  set: {
    type: String,
    required: true
  },
  sockets: {
    type: Number,
    required: true
  },
  accessoryType: {
    type: String,
    required: () => this.category == 'accessory'
  },
  material: {
    type: String
  },
  restrictions: {
    type: String
  },
  damage: {
    type: String
  },
  fireDamage: {
    type: String
  },
  waterDamage: {
    type: String
  },
  airDamage: {
    type: String
  },
  thunderDamage: {
    type: String
  },
  earthDamage: {
    type: String
  },
  attackSpeed: {
    type: String
  },
  type: {
    type: String
  },
  armorType: {
    type: String
  },
  armorColor: {
    type: String
  },
  addedLore: {
    type: String
  },
  dropType: {
    type: String
  },
  health: {
    type: Number
  },
  fireDefense: {
    type: Number
  },
  waterDefense: {
    type: Number
  },
  airDefense: {
    type: Number
  },
  thunderDefense: {
    type: Number
  },
  earthDefense: {
    type: Number
  },
  level: {
    type: Number
  },
  quest: {
    type: String
  },
  classRequirement: {
    type: String
  },
  strength: {
    type: Number
  },
  dexterity: {
    type: Number
  },
  intelligence: {
    type: Number
  },
  agility: {
    type: Number
  },
  defense: {
    type: Number
  },
  healthRegen: {
    type: Number
  },
  manaRegen: {
    type: Number
  },
  spellDamage: {
    type: Number
  },
  damageBonus: {
    type: Number
  },
  lifeSteal: {
    type: Number
  },
  manaSteal: {
    type: Number
  },
  xpBonus: {
    type: Number
  },
  lootBonus: {
    type: Number
  },
  reflection: {
    type: Number
  },
  strengthPoints: {
    type: Number
  },
  dexterityPoints: {
    type: Number
  },
  intelligencePoints: {
    type: Number
  },
  agilityPoints: {
    type: Number
  },
  defensePoints: {
    type: Number
  },
  thorns: {
    type: Number
  },
  exploding: {
    type: Number
  },
  speed: {
    type: Number
  },
  attackSpeedBonus: {
    type: Number
  },
  poison: {
    type: Number
  },
  healthBonus: {
    type: Number
  },
  soulPoints: {
    type: Number
  },
  emeraldStealing: {
    type: Number
  },
  healthRegenRaw: {
    type: Number
  },
  spellDamageRaw: {
    type: Number
  },
  damageBonusRaw: {
    type: Number
  },
  bonusFireDamage: {
    type: Number
  },
  bonusWaterDamage: {
    type: Number
  },
  bonusAirDamage: {
    type: Number
  },
  bonusThunderDamage: {
    type: Number
  },
  bonusEarthDamage: {
    type: Number
  },
  bonusFireDefense: {
    type: Number
  },
  bonusWaterDefense: {
    type: Number
  },
  bonusAirDefense: {
    type: Number
  },
  bonusEarthDefense: {
    type: Number
  },
  category: {
    type: String,
    enum: ['accessory', 'armor', 'weapon'],
    required: true
  },
  // flags will be added as items are moved from Wynncraft's official API
  // into my database. The official API is inconsistent, I will put problems here,
  // e.g. "item.sockets undefined, setting to 0" and things like this.
  flags: {
    type: [String],
    required: true
  }
});

ItemSchema.plugin(uniqueValidator);

module.exports = mongoose.model('Item', ItemSchema);

There's so much repetition and it's just so long, I wonder if this schema can be created in a less verbose way.

\$\endgroup\$
0
\$\begingroup\$

As I see there is about 60 properties for each item in Wynncraft DB. I see two ways to improve your design:

  1. Distribute all properties across multiple schemas: basic item information (name, category, etc), defense information, bonus damage information and other. In this case those schemas will be related to each other. Maybe you don't even need to store all item's data (depends on goal of your application).
  2. If you want to identically map properties of item to your storage, then I guess you can get list of all properties as JSON (by using Wynncraft's public API) and convert it to schema definition. JSON with list of properties could be cached for better performance.
\$\endgroup\$
  • \$\begingroup\$ If I do (1) how do I make the large ItemSchema out of all the smaller ones? \$\endgroup\$ – theonlygusti Jun 15 '18 at 15:14
  • \$\begingroup\$ 2 is not an option because the API is too inconsistent \$\endgroup\$ – theonlygusti Jun 15 '18 at 15:14

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.