Personally, I'm not a big fan of the way you programmed it. You're implementing IRecipeType on a class (which makes no sense), not creating a serializer, and just not registering it anywhere.
So, let's break it down.
All recipes that hook into IRecipe have three things:
- A class that implements IRecipe<T> (most likely T will be RecipeWrapper if you are using IItemHandler over IInventory which YOU SHOULD BE)
- A class that extends ForgeRegistryEntry<IRecipeSerializer<V>> and implements IRecipeSerialier<V> (V is your class that extends IRecipe<T>)
- A variable holding your IRecipeType<V> (statically initialized through IRecipeType#register should be fine).
Let's start with IRecipeType. This just basically holds a string that will create a new map entry within RecipeManager for any recipe with that specific type. The string held within the registry should be your mod id appended with whatever you are going to call it.
Next, let's go into IRecipe. All IRecipes should have a constructor that takes in a ResourceLocation, a String group (if you are going to use the RecipeBook), an Ingredient (NBTIngredient if you want to use NBT data), and ItemStack output. Note, it doesn't have to be an ingredient or itemstack, that's just the case most people use it for. Then we have the methods:
- matches: checks to see if your recipe matches with the ones stored (will use Ingredient#test)
- getRecipeOutput: the output of your recipe with no information provided beforehand (will be your result)
- getCraftingResult: the output of your recipe with context (will be your result followed by ItemStack#copy)
- canFit: checks to see if your recipe can fit in the required space
- getId: the ResourceLocation of your recipe
- getType: the IRecipeType your recipe should be stored in
- getSerializer: the IRecipeSerializer used to read and write your recipe.
Then we have the IRecipeSerializer. This will be registered within your code via RegistryEvent or DeferredRegister. This has three main methods:
- read: reads the data from a JsonObject and returns an instance of your recipe (json file stored in datapack)
- read: reads the data from a PacketBuffer and returns an instance of your recipe (server/client packet sending)
- write: reads the data from your instance to a packet buffer (server/client packet sending)
These methods can be observed in all recipe classes (e.g. ShapedRecipe, AbstractCookingRecipe, SingleItemRecipe)
Once you start to create your json files (same place as all the other recipes), the type is handled by what the IRecipeSerializer is registered under (modid:object_name).
And that's basically it. Hope this helps. If you want an example, I wrote a basic recipe and serializer for blenders a while back.