File Structure

Hyperstack adds the following files and directories to your Rails application:

/app/hyperstack
/app/operations
/app/policies
/config/initializers/hyperstack.rb
/app/javascript/packs/client_and_server.js
/app/javascript/packs/client_only.js

In addition there are configuration settings in existing Rails files that are explained in the next section. Below we cover the purpose of each these files, and their contents.

The /app/hyperstack/ Directory

Here lives all your Hyperstack code that will run on the client. Some of the subdirectories are isomorphic meaning the code is shared between the client and the server, other directories are client only.

Within the hyperstack directory there can be the following sub-directories:

  • components (client-only) is where your components live.

    Following Rails conventions a component with a class of Bar::None::FooManchu should be in a file named components/bar/none/foo_manchu.rb

  • models (isomorphic) is where ActiveRecord models are shared with the client. More on this below.

  • operations (isomorphic) is where Hyperstack Operations will live.

  • shared (isomorphic) is where you can put shared code that are not models or operations.

  • Any other subdirectory (such as libs and client-ops) will be considered client-only.

Sharing Models and Operations

Files in the hyperstack /models and /operations directories are loaded on the client and the server. So when you place a model's class definition in the hyperstack/models directory the class is available on the client.

Assuming:

Then

See the Policy section below for how access to the actual data is controlled. Remember a Model describes some data, but the actual data is stored in the database, and protected by Policies.

Likewise Operations placed in the /operations directory can be run on the client or the server, or in the case of a ServerOp the operation can be invoked on the client, but will run on the server.

Hyperstack sets things up so that Rails will first look in the hyperstack /models and /operations directories, and then in the server only app/models and app/operations directories. So if you don't want some model shared you can just leave it in the normal app directory.

Splitting Class Definitions

There are cases where you would like split a class definition into its shared and server-only aspects. For example there may be code in a model that cannot be sensibly run on the client. Hyperstack augments the Rails dependency lookup mechanism so that when a file is found in a hyperstack directory we will also load any matching file in the normal app directory.

This works because Ruby classes are open, so that you can define a class (or module) in multiple places.

Server Side Operations

Operations are Hyperstack's way of providing Service Objects: classes that perform some operation not strictly belonging to a single model, and often involving other services such as remote APIs. The idea of Operations comes from the Trailblazer Framework.

As such Operations can be useful strictly on the server side, and so can be added to the app/operations directory.

Server side operations can also be remotely run from the client. Such operations are defined as subclasses of Hyperstack::ServerOp.

The right way to define a ServerOp is to place its basic definition including its parameter signature in the hyperstack/operations directory, and then placing the rest of the operation's definition in the app/operations directory.

Policies

Hyperstack uses Policies to define access rights to your models. Policies are placed in the app/policies directory. For example the policies for the Todo model would defined by the TodoPolicy class located at app/policies/todo_policy.rb Details on policies can be found Policy section of this document..

Example Directory Structure

These directories are where most of your work will be done during Hyperstack development.

What about Controllers and Views?

Hyperstack works alongside Rails controllers and views. In a clean-sheet Hyperstack app you never need to create a controller or a view. On the other hand if you have existing code or aspects of your project that you feel would work better using a traditional MVC approach everything will work fine. You can also merge the two worlds: Hyperstack includes two helpers that allow you to mount components either from a controller or from within a view.

The Hyperstack Initializer

The Hyperstack configuration can be controlled via the config/initializers/hyperstack.rb initializer file. Using the installer will set up a reasonable set of of options, which you can tweak as needed.

Here is a summary of the various configuration settings:

Hyperstack Packs

Rails webpacker organizes javascript into packs. Hyperstack will look for and load one of two packs depending on if you are prerendering or not.

The default content of these packs are as follows:

Last updated

Was this helpful?