Most large games I've worked on do it like this:
1. The data is entered into a spreadsheet or SQL database using whatever app you want (Excel, OO, Google Spreadsheet, SQL). You can lay this out however you want (simple row/column grid all the way up to a fully normalized database).
2. The spreadsheet or database is scanned for the data, and stored however you feel is most appropriate for your game (custom binary form, protobuf, XML, JSON, etc). This step typically takes database-style table-based data (i.e. if an inventory item has a variable length list of crafting ingredients, the crafting ingredients would be normalized as a separate sheet/table in the input spreadsheet/database) and turns it into more typical hierarchical data structures (i.e. "Item.CraftingIngredients").
3. The game loads the data into the data structure you feel is most appropriate for your game (a simple list, an associative array with unique IDs, a full-on SQLite database, etc). Excessively large data sets may be hosted on a web service that can be fetched from 100 items (or so) at a time.
The large games I've worked on have all used Excel spreadsheets for data entry and associative arrays (Dictionary<string,InventoryItem>) for runtime storage.