6

In my web application that uses an MVC framework which has different modules for models, views and controllers I talk to several databases and APIs. Those are implemented as individual models.

A lot of data gets entered by the user accross several different screens. That data goes into the session. Some of that data is meta information that validates the success of the process, and some of it is stuff that I want to keep. That data is supposed to be written to a file in the file system, and the path of that file with some meta-information is stored in a database. After that, a confirmation page will be displayed to the user.

I am now struggling with where to put the writing of the subset of the data that has accumulated in the session to the file in my specific format.

There are several thoughts I have on the matter. I am not sure which one is the most right.

  1. It should be a View because it takes data that is already there in the user's session and presents it in a specific way – the file format (which is XML, but that is not relevant). Formatting and writing the file is implemented there.

    Reasoning: The default HTML view that renders data as a website to the user's browser has the webserver's interface set as its STDOUT channel. Likewise would a JSON view that presents stuff in case an API call is made. If we write to a file, the STDOUT of the view that formats the file is set to a local file handle and we write there.

  2. There should be a View to bring the data into my XML format, but a Model to write the data into the file.

    Reasoning: Because after writing the file, another website will be displayed. Only one view can be at the end of the chain of things that do stuff in the lifetime of one request handling. But because data is being formatted, a view is appropriate. It just returns the formatted data rather than writing it to a sink (STDOUT).

  3. It should be a Model, because it deals with data.

    Reasoning: Models are data sources and data sinks. Although the source-part is absent here there is still a data sink. The fact that it needs to be formatted also is neglegible because if we'd talk to e.g. a RESTful API of some sort we would also first format the data to be either part of a GET request (which is very simple) or maybe a JSON representation as the body of a POST/PUT request.

The code that formats the data into XML is already built as a stand-alone class that is not tied to the webapp yet.

My question is this: Where in the application should I use that class and write the file to disk so I do not break the MVC pattern?


Example cases where this specific process would happen include:

  • a user feedback/survey form with multiple pages, like the Stack Overflow anual user survey,
  • an e-commerce order funnel,
  • back-office data entry that talks to a third party through a file-based API where the "sending" happens asynchronously at a later, unrelated time
5

None of the above, actually. It is the responsibility of your controller to write the data to file, although I'd recommend writing a specific class for that and just having the controller use that class.

It is not a view because views in MVC are strictly about rendering data in the UI. The data itself should probably be put into a model and that model persisted via the controller.

Think about this in a storage-independent way. If this was data you store in the database, would you do anything besides put the data onto a model and use a repository (or some sort of DAL) to write that model to a database? Probably not. In this case you would gather your data into a model, hand the model off to a repository and then use your XML-formatting class to write the model into a file.

  • Please clarify: you are saying it's my point 3, but the writing is done by the controller? – simbabque Aug 11 '15 at 9:57
  • Well, your question was where you should use the class to write the file to disk. You wouldn't use that class IN the model, but you would use that class in the controller to write the model. So in that sense, yes. – JDT Aug 11 '15 at 10:03
  • I like your answer, but I would like to give it some time to allow other people to answer as well. :) – simbabque Aug 11 '15 at 13:52
0

I had the same problem but my situation was a little bit different, let me explain.

In my project I had to use files for two purposes:

  1. Store data (database)
  2. Track errors (log file)

So my model was dedicated to the interaction with files used as database and i created some helpers (I was using Codeigniter) to write log files. In this way i could invoke helper functions everywhere and this was really helpful because I had to track errors in models and controllers.

In your case i suggest you to write your own helper class to be invoked where you need to write data.

I hope it helps

  • I'm not talking about logs that are written in several places. This is a once-per user action that not all users reach. So I think this approach will not help me. I already have a logging mechanism out of the box from my framework. – simbabque Aug 11 '15 at 10:09
  • Sorry, can you give us a concrete example? I think could help – Ema.jar Aug 11 '15 at 10:10
  • 1
    Please see my edit to the question – simbabque Aug 11 '15 at 12:19
0

In a slight variation of JDT's answer...if I'm understanding all of it correctly, this is how I view it (pardon the pun):

View/Controller: Both part of the presentation concern. The controller acts as the intermediary between the view and the model, affecting changes to the model (unless you have binding to the model from the view) and reflecting model state in the view.

Models: Implement the business rules/behavior or, at least, make use of objects that do. The business rules are used when applying commands and queries to the application/session state and define the heart of the application's behavior.

Data: The application state needs to be persisted to be of any use, generally, so the models use a data layer to achieve that.

In this way, any mutation of the application state goes through the same layer of business rules to achieve consistency; the presentation wouldn't directly interact with the data.

I wouldn't have the controller directly being responsible for the persistence because if you were to switch out the presentation layer with another (where you don't have the controller, such as if it became a headless service), you've lost the piece that was doing the persistence for you. By pushing it down to the business tier (in the models), you're free to change your presentation layer and still maintain your behavior.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.