an image of a forest and water

Lucky Framework Notes - Part2

These are notes - so they might be partly or fully incorrect. This is just me jotting down things to wrap my head around it... 

Models describe what your object is.


Operations are objects that provide an interface on how your applications interact with the model. This is a bit different than, say, Rails' Active Record (at least the last time I looked at it). If you need to create a custom validation, callback, restrictions on what fields can be updated, they go here.

For example:

I'm creating a model called Post (pluralized to Posts in the DB). Lucky automatically creates created_at and updated_at fields when you create a new model. It will also create a Save Operation called SavePost which inherits from Post::SaveOperation. The default will look like:

class SavePost < Post::SaveOperation
  permit_columns title, body

Notice the only permitted columns you can update are title and body (which were defined when I created the model). I can't touch created_at or updated_at - at least without specifying these columns (not that you'd really want to - but this is just an example).

Queries are objects that hold your custom queries you define for your models.

The View layer has three parts - Pages, Components, and Layouts

Pages are how you present the content to the user. The default method in lucky is that all of your views are written in Crystal like this: 

def render_posts 
  ul do 
    posts.each do |post| 
      li do 
        link post.title, Posts::Show.with(post) 

Notice - no HTML. You can swap this out for something else but it generally works pretty well, once you get the hang of writing crystal instead of HTML. It reminds me a lot of (IIRC) Smalltalk's Seaside framework.

Components are little chunks of shareable objects. Instead of having to add a header and footer into each page, you can create a component.

Layouts let you define a shared structure throughout your site. This is fairly obvious. But in the getting-started tutorial on the Lucky site, you'll do an example where you create a Home page which inherits from a layout. You then add a footer and navbar component to the layout and the content from the Page is then parsed into the final document: 

def render 
  html class: "h-100", lang: "en" do 
    mount Shared::LayoutHead, page_title: page_title 
    body class: "d-flex flex-column h-100" do 
      mount Shared::Navbar 
      mount Shared::FlashMessages, context.flash 
      main class: "flex-shrink-0" do 
    mount Shared::Footer 

Your controllers are called Actions - each action has a separate class in distinct file. Your Actions control how resources are called and how the response is presented to the user.  

This article was updated on 25 Oct 2021