ECS is a solution direction if inheritance or interfaces fail. From your post I gathered you don't use those much yet, so ECS is a possible solution 2 steps away from your problem for you. I'd suggest you get a good understanding about inheritance and interfaces first (in particular when not to use them) before you venture into ECS.
I think my Behavior object is at least in the direction of ECS, but I am not sure. I am more of a pragmatic programmer picking the ideas that fix the problem, rather than knowing exactly what is "proper ECS" or "proper OOP" or "proper Foo-Pattern" or "proper <whatever>".
Nice to see you already moved into reading data from file. As to how to write behavior in a file, whatever you do, it must be text, since that's the only thing you can write in a text file. Other adventure authoring systems tend to allow writing source code in some form which they load and interpret, but that's likely too complicated for you at this time (in the general case you end up in scanner and parser code generators like yacc or bison (both are C-based, no idea what exists in C# but likely it's similar). A much simpler form is to give each behavior a name, and then loading behavior into an Item is just a list of such names.
A switch statement is one option for converting a name to an object in the program. An other option is to use a Dictionary, which is quite simple if none of the the behavior objects has state. (That is, they don't have any variables inside that are different between behavior objects in different Items.) In that case, you can make a "Dictionary<string, Behavior> behaviors;" dictionary, where Behavior is the base class (or interface) of all behaviors. Getting the behavior is then a simple dictionary lookup, something like "behaviors.get(loaded_name)" or "behaviors[loaded_name]". (Not being a C# programmer, I don't know exactly how to do that, but https://stackoverflow.com/questions/12169443/get-dictionary-value-by-key seems to point to a solution.)
If the behavior objects do have state (and I can imagine that being useful), you need to construct a new Behavior object for each Item. The usual solution for that is the Factory pattern. Instead of a dictionary from name to behavior, you have a dictionary of name to behavior-builder. Getting a behavior is then a 2-step process, first get the builder (the factory) from the dictionary, then ask the builder for a fresh behavior object. I can imagine that this is too complicated for now, and a switch is the better solution to you at this point.
How to find and perform a behavior at runtime is indeed another puzzle. I would try to avoid splitting the actions as much as possible. The advantage of that is less cases to deal with, and (probably more for the future), simpler expansion of the set of actions. If you want to add "boinc" as new action (no idea what it would do, just an example), you don't want to have to write a new derived BoincAction, extend all existing behavior code for this new Boinc action, etc.
So instead, why not let the command processor ask the Item for a Behavior object matching the given action string (or action ID). The Item then asks all its behaviors whether they understand that action, and if one does, it is returned. The command processor thus gets (or doesn't get) a behavior object, which it then executes ("behavior, please do your stuff"). Nothing in this setup knows what action is performed exactly, except the behavior object itself, but the latter is supposed to know eh? The command processor and the Item don't know if you typed "eat", "open", "rub", or (in the future) "boinc".