Is it feasible to reuse WPF ViewModels in MVC?

2019-06-24 05:47发布

问题:

we have a rich client application written in WPF/WCF and are intending to create a companion website in ASP.net (using MVC if possible).

I've been asked to figure out how much of our current codebase, we can reuse (by a separate team) - and I have little to no experience with ASP.net.

We will reuse our domain model, but is there any point in separating out the WPF-specific parts of our ViewModels and reuse the WPF-agnostic parts in MVC? Does it even follow the same paradigms? We use RelayCommands exclusively for commanding, so it would be easy to wrap the contained methods in something ASP.net specific... But how about UI-specific things - e.g. does ASP.net use INotifyPropertyChanged - or how does it handle UI-updates?

回答1:

For me it wouldn't make any sense. Your models should contain all of your important business logic code and should be the point of greatest reuseability. Your view models should contain presentation logic only, and as this is so different for a desktop and web app, it doesn't make sense to reuse these.

MVC does not use any binding mechanism for UI updates, as web apps are stateless by nature. You will actually most likely end up using view models for your MVC app, but in MVC these act as simple data transfer objects (DTOs) for providing data to the views for rendering for each HTTP request. Once the view is rendered, you would need to go back to the server to update the view model and rerender the view.

Alternatively, you can of course update the UI client side with scripting. Knockout.js is a nice JS library for client side view model/view binding.



回答2:

I can't directly answer your specific question because it depends highly on your application and the way your existing view-model is written but the question you raise is an interesting one.

On the one hand, the logic that the view-model contains very little view-specific code is a tantalizing argument for reuse. On the other hand, the view-model very clearly serves the needs of the view and expecting it to serve the needs of a different view could be problematic.

In the end all we can give are guidelines. You certainly don't want a monolithic view-model with ifdefs or ifs all over the place. You could refactor common functionality into base classes -- that's the object-oriented way -- but without good unit tests it's sure to break something in your already working code. But not doing that means having distasteful cut-and-paste code that is almost the same and likely to diverge creating a maintenance nightmare.

Perhaps a practical approach is to assume you'll need a whole new view-model but to review your existing view-model for code you can push down into the model before your start, thereby making the view-model as small as possible. Then at some point, maybe after you get a prototype working, you could attempt a merge to see if it is practical and what issues arise. If it can work, take those issues into account as you continue implementation and then plan the two tasks according to your needs.