Clone wiki

Cinch Web / 02 Backend

#Backend Controllers#

The Cinch website uses Ruby on Rails for it's application layer and postgres as it's database. In addition, a key/value store used by redis is utilized for both caching of webpages and api data, as well as processing queues of asynchronous data from rails via jobs sent to Sidekiq, the results of which are saved back to Postgres.

Ruby on Rails utilizes an MVC architecture (model - view - controllers), where there is a separation of concerns:

mvc architecture

  • The model directly manages the data.
  • A view can be any output representation of information, a webpage, chart, or diagram.
  • The controller manages the logic and interaction between the model and the view.

In the case of Ruby on Rails, there's also a routing component if there's deviation from the built in resource url linking (ie /users/32/edit).

In the Cinch application logic there's an API controller that data is routed to via outside POST requests, and JSON is returned (look for more details regarding the API or serialized JSON). There's also the short term key/value store saved to redis as either cached data, or queues of asynchronous data to be processed before being saved to the postgres database -- for example, sensor data needs to be processed into dailysummaries.

The best way to visualize all the components working together is by three tiers:

cinch dataflow

  1. The first tier is the data tier which uses postgres for long-term data, redis for short-term or transient data.

  2. The core of the logic is done in the controller code within the rails application, processing the flow between the 1st and 3rd layers.

  3. The user interacts at the third tier - whether via the website views or a mobile application utilizing the API interaction.

Explaining the specifics of the controller code is probably outside of the scope of this document - and honestly, the logic is so intrinsic to the nature of Ruby on Rails, one would be able to pick it up easily if one were familiar with RoR. However the basics of the controller code is tied into the business logic of the application:

A doctor can have many patients.

A patient can have many doctors.

A patient can have many parents.

A parent can have many children (patients).

A parent can have many *doctors through their children (patients).

A doctor can have many parents through their patients.

The above explains the relationships of the user-types to each other very simply. The inter-relationships and how they are inherited are built into Ruby on Rails.

At the core of everything is a product; in the case of Cinch a product is really a brace. The product has one patient, and can have many doctors.

A product has many sensors and each of these sensors has a location. A product has a treatment, this treatment can have many prescriptions, each of which will have prescribed tensions for every sensor that exists in the product it's treating. Each of these prescribed tensions will have a force and position for that sensor.

Each of the emboldened words above are really single datapoints whose variables are described as models in the Cinch application, and whose controller logic basically assembles the interaction as a whole.

The application also controlls the authentication of the user and the data allowed; for example a patient will never be able to see other patient information, or a product that belongs to another patient. A doctor will only be able to see products that belong to patients under their care, but not patient or product information under a different physician's care.

In the Ruby on Rails structure, an object -- say a doctor -- will have a model, a controller and a view (or multiple views, say one view for showing a doctor, another view for editing* a doctor, etc).

API Controllers

The API controllers exist within the controller structure, but they don't have an API model, nor an API view -- instead they are routed POST queries via Ruby on Rails routes -- and respond in kind based upon the urls and data being POSTed. Ruby on Rails etc could respond via it's own RESTful structure based upon the data type being requested, but we opted for urls for API requests only, based upon previous interation of the site / application when it wasn't RESTful (ie a .Net backend).