Recipes
Strengthening recipes define target matching, economy cost, star limits, base success rates, required materials, effects, and actions. Recipe files are placed in recipes/*.yml, and the file name is normally used as the recipe id.
Top-level fields
| Field | Description |
|---|---|
id | Unique recipe id. |
display_name | Display name. |
gui_template | GUI template id. |
economy | Economy cost configuration for each attempt. |
limits | Maximum star, temper limit, and chance cap. |
success_rates | Base success chance for each target star. |
matcher | Non-item-source conditions (component, PDC, lore, variable) deciding which items can use this recipe. See Match rules. |
source_patterns | Item source matching by regex, AND-combined with matcher. This is where item source conditions go at the top level. |
slot_groups | Slot group matching, AND-combined with matcher. See Match rules. |
stats_any | Attribute matching, AND-combined with matcher. |
match | Deprecated and no longer read. See Migrating from match. |
name_actions | Global name operations applied after success. |
lore_actions | Global lore operations applied after success. |
stars | Per-star material, effect, and action definitions. |
Economy
economy:
enabled: true
currencies:
- provider: "vault"
currency_id: ""
base_cost: 320
cost_formula: "%base_cost% * %star%"
display_name: "<gold>Coins</gold>"cost_formula can reference variables such as %base_cost% and %star%.
Limits
limits:
max_star: 12
max_temper: 4
temper_chance_bonus_per_level: 5.0
success_chance_cap: 90.0| Field | Description |
|---|---|
max_star | Maximum reachable star. |
max_temper | Maximum temper level accumulated from failures. |
temper_chance_bonus_per_level | Success chance bonus per temper level. |
success_chance_cap | Upper success chance after all bonuses. |
Match rules
Target matching is decided by four top-level fields, combined with AND:
slot_groups:
- "weapon"
# Item source condition at the top level goes in source_patterns.
# Anchor the pattern to bind one exact source.
source_patterns:
- "^emakiitem-example_item$"| Field | Type | Description |
|---|---|---|
matcher | object | Non-item-source conditions only: component, PDC, lore, variable. Item source conditions written inside it (type: item_source and aliases) are rejected at load time and never match. Syntax is in Item Matcher. |
source_patterns | list | Match the item source shorthand by regex. Case-insensitive partial match, so anchor it (^...$) to bind one exact source. Matching any one pattern passes. |
slot_groups | list | Coarse slot/equipment type groups (weapon/armor/offhand/generic), not concrete slots such as main_hand or helmet. |
stats_any | list | Has any of the given attributes. |
Migrating from match
The old match block is no longer read. Where each field goes:
| Old field | Current form |
|---|---|
match.source_ids | An anchored entry in the top-level source_patterns, such as "^minecraft-diamond_sword$" |
match.lore_contains | A type: component child with component: lore and operator: contains, one per fragment |
match.slot_groups | Promoted to a top-level slot_groups |
match.stats_any | Promoted to a top-level stats_any |
match.source_patterns | Promoted to a top-level source_patterns |
match.source_types | Cannot be converted automatically; rewrite it as a matcher condition by hand |
/emakistrengthen convert-legacy performs the conversion:
| Command | Behaviour |
|---|---|
/emakistrengthen convert-legacy | Dry run; prints the diff it would produce without touching files. |
/emakistrengthen convert-legacy confirm | Rewrites recipes/*.yml and leaves a .bak backup per file. |
--apply is equivalent to confirm. The command requires emakistrengthen.admin.
WARNING
Files containing match.source_types are reported as unconvertible and skipped. Files declaring both match and an existing matcher (or the corresponding top-level field) are reported as conflicts and skipped. Both cases need manual handling.
match.source_ids is converted automatically into anchored regexes merged into the top-level source_patterns, never into a node inside matcher, so the output needs no manual fix-up. Those regexes are exact matches: ^ / $ anchors are added and special characters in the ID are escaped, giving entries like ^\Qemakiitem-xxx\E$.
Legacy material normalization and rejection
Stage-material parsing normalizes a legacy scalar item into item_sources, then resolves material_id in this order: explicit material_id, legacy id, count_key, a single source, and finally the stage index. An omitted count_key falls back to material_id. When no identity is declared but multiple sources are supplied, the parser cannot choose a safe unique identity and rejects the material without rewriting the source map. These rules are established by the current JVM parser and local tests; old configuration and persisted-save behavior has not been verified on a live Paper or Folia server.
TIP
Anchor a source_patterns entry for exact binding so a recipe does not accidentally match every weapon.
General item matcher
Recipes accept a matcher in two places: the top-level matcher narrows the target item, and stars.*.materials[].matcher re-verifies strengthening materials. Both use the same syntax, but they express the item source differently:
| Location | How the item source is expressed |
|---|---|
Top-level matcher | Through the top-level source_patterns (regex). source_patterns, matcher, slot_groups, and stats_any are ANDed; all must hold. |
materials[].matcher | Through the sibling item_sources. The material is selected by its item_sources token first, then matcher re-checks the actual item; both must hold. |
NOTE
Item source conditions never belong inside matcher here either — at the top level use source_patterns, in materials use the sibling item_sources.
Full syntax is in Item Matcher.
id: enchanted_sword_strengthen
# Item source condition: only diamond swords
source_patterns:
- "^minecraft-diamond_sword$"
# Component condition: with Sharpness 3+
matcher:
type: component
component: enchantments
path: sharpness
operator: '>='
value: 3
stars:
1:
materials:
# item_sources selects the material, matcher re-verifies it
- item_sources:
- minecraft-copper_ingot
matcher:
type: component
component: custom_name
operator: absent
amount: 3WARNING
Item sources use a hyphen (minecraft-copper_ingot), not a colon. Written as minecraft:copper_ingot in item_sources the parser treats it as invalid and silently discards it, leaving the item source unrestricted. See Item sources use hyphens, component IDs use colons.
target.filter in enhancement recipes
enhancement_recipes/*.yml (a separate recipe set from the recipes/*.yml covered on this page) also accepts a general item matcher in target.filter: when filter contains a type key it is parsed as a matcher, otherwise it keeps the existing provider-specific key/value behaviour.
target:
provider: equipment
# Has a type key -> parsed as a general item matcher
filter:
type: component
component: enchantments
operator: existstarget:
provider: equipment
# No type key -> still interpreted as free-form provider keys (existing behaviour)
filter:
item_type: SWORDIts materials[] entries follow the standard shape: item_sources for the allowed item sources and a sibling matcher for non-item-source conditions, ANDed. Item source conditions that used to sit inside matcher belong in item_sources now.
NOTE
The remaining fields of the enhancement_recipes/ set are not yet documented on this site; this section covers only where it accepts a matcher.
:::
Star stage materials
| Field | Type | Default | Description |
|---|---|---|---|
item_sources | list | none | Allowed material item sources; selects the material. |
matcher | object | none | Non-item-source conditions re-verifying the actual item, ANDed with item_sources. See Item Matcher. |
amount | integer | 1 | Required amount. Use -1 to require possession without consuming. |
optional | boolean | false | Whether the material is optional. |
protection | boolean | false | Prevents a star drop on failure. |
temper_boost | integer | 0 | Extra temper levels supplied for this attempt. |
materials:
- item_sources:
- "minecraft-copper_ingot"
amount: 3
# Protection material: not consumed, only checked
- item_sources:
- "minecraft-gold_nugget"
amount: -1
optional: true
protection: trueSuccess rates
success_rates:
1: 100.0
2: 95.0
3: 90.0
4: 80.0
5: 70.0Keys represent the target star, and values are percentages. Temper bonuses are applied after the base rate and are capped by limits.success_chance_cap.
Star example
stars:
1:
effects:
- type: "variables"
variables:
physical_attack: 4
- type: "lore_action"
lore_actions:
- action: "append"
content:
- "<gray>Physical Damage: <gold>+4</gold></gray>"
materials:
- item_sources:
- "minecraft-copper_ingot"
amount: 1
- item_sources:
- "minecraft-gunpowder"
amount: 2
2:
effects:
- type: "variables"
variables:
physical_attack: 4
- type: "lore_action"
lore_actions:
- action: "replace_line"
anchor: "Physical Damage:"
content:
- "<gray>Physical Damage: <gold>+8</gold></gray>"
materials:
- item_sources:
- "minecraft-copper_ingot"
amount: 1Effect types
| Type | Description |
|---|---|
variables | Expression variables used by lore, name/lore templates, and placeholder context. They do not automatically become Attribute PDC attributes. |
ea_attribute | Explicit EmakiAttribute PDC attribute payload. |
es_skill | EmakiSkills skill attachment; payload uses the es_skills list. |
lore_action | Lore operation. |
name_action | Item name operation. |
Current effect boundaries:
variablesonly provide text, placeholder, and operation-template context.- Real attribute output must be configured explicitly with
type: "ea_attribute"andea_attributes. - Skill attachments use
type: "es_skill", while concrete skill ids are stored in thees_skillslist.
Notes
- Use high success rates for early stars and gradually increase material cost.
- Use protection materials for high-risk levels when item downgrade or destruction is enabled by recipe logic.
- Prefer
replace_linefor repeated stat lines to avoid duplicate lore. - Test old strengthened items after changing recipe ids or match rules.