V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
Mark24
V2EX  ›  Ruby

Sinatra 的 app 模板,提供一些胶水代码支持类似 Rails 的体验

  •  
  •   Mark24 · 2021-09-14 23:02:45 +08:00 · 1590 次点击
    这是一个创建于 926 天前的主题,其中的信息可能已经有所发展或是发生改变。

    Sinatra 的 app 模板,提供一些胶水代码支持类似 Rails 的体验

    如果你想灵活的开展工作,又觉得 Rails 过于庞大(比如 Rails6+ 携带一个 Node )、文档要读很久,正在犹豫当中。

    你恰巧知道 Sinatra 的存在,15 分钟读完的 Sinatra/README 又觉得自己行了,可是 Sinatra 似乎太简单了,你想要是 Sinatra 有 MVC 和开箱即用的 ORM 就好了。

    这是最近做一个简单后端项目的沉淀,可以作为一个简单的起点。

    一切基于 Sinatra+Rack,用一些胶水代码 把 Rack/Sinatra + 配置 + 文件目录 联系在一起开始工作。容易更改,简单明了。

    分享一下,可能不够成熟,欢迎碰撞,让我可以学习更多~

    github: https://github.com/Mark24Code/sinatra-app-template

    geeknote: https://geeknote.net/mark24/posts/283

    RubyChina: https://ruby-china.org/topics/41685

    Sinatra App Template

    Lightweight web framework codebase. Just clone and develop on it.

    Tech component: Rack+Sinatra+Sequel and default use Postgresql database.

    Add rails-like migration command line helpers.

    Openbox Features

    Apps

    • <input checked="" disabled="" type="checkbox"> Multi Env Configuration
    • <input checked="" disabled="" type="checkbox"> Multi router DSL base on Rack
    • <input checked="" disabled="" type="checkbox"> CORS support
    • <input checked="" disabled="" type="checkbox"> Hot reload
    • <input checked="" disabled="" type="checkbox"> Custom logger
    • <input checked="" disabled="" type="checkbox"> ORM base on Sequel'

    Tasks

    • <input checked="" disabled="" type="checkbox"> Rails-like migration helpers
    • <input checked="" disabled="" type="checkbox"> Test
    • <input checked="" disabled="" type="checkbox"> Seed

    CI&CD

    • <input checked="" disabled="" type="checkbox"> Dockerfile

    Find helpful rake tasks

    rake or rake -T

    Run server & develop

    rake server:run

    Production Server & deploy

    APP_ENV=production bundle exec rake server:run

    you can also use docker

    docker built -t <what your docker image label> .

    Custom server & database

    You can use DSL to config Key:Value , then you application just use.

    Config::Default.configure do
      set :app_env, ENV.fetch('APP_ENV'){ 'development' }
      set :bind, ENV.fetch('HOST') { '0.0.0.0' }
      set :port, ENV.fetch('PORT') { 3000 }
      set :secrets, ENV.fetch('SECRETS') { 'YOU CANNOT GUESS ME' }
      set :max_threads, ENV.fetch('MAX_THREADS') { 5 }
    
      set :database_url, ENV['DATABASE_URL']
    end
    
    Config::Development.configure do 
      set :database_url, 'ENV['DATABASE_URL']'
    end
    
    Config::Test.configure do 
      set :database_url, ENV['DATABASE_URL']
    end
    
    Config::Production.configure do 
      # set :database_url, ENV['DATABASE_URL']
    end
    

    They have an inheritance relationship

    Development < Default
    Test < Default
    Production < Default
    

    In your code, just use Config directly. core/bootstrap do a work that loaded all necessery mods before your code.

    Config.current  # current env configuration
    
    Config::Development.database_url
    
    Config::Development
    
    Config::Development.database_url
    

    You can also create your own Config for your single Application:

    class MyConfig < Config::Base
    
    end
    
    MyConfig.configure do 
      # set :database_url, ENV['DATABASE_URL']
    end
    
    

    Mount different Sinatra web application

    Edit config.ru

    Lark also is Rack application. We can use Rack middlewares.

    require_relative './cores/bootstrap'
    Bootstrap.rack 
    
    # you can load Rack middleware here
    
    # mount applications
    require 'controllers/root_controller'
    # routers(handy config)
    map '/' do
      run RootController 
    end
    

    Base

    bases directory are use for Application Base Class.

    You can make different Configured Sinatra Application class here, then your application/controller just inherit the Base Class to create Application.

    It will share Config, and make less code.

    # Sinatra Doc http://sinatrarb.com/intro.html
    require 'sinatra/base'
    require 'json'
    
    class BaseController < Sinatra::Base
      # Inject config
    
      # Config & register Sinatra Extensions
    
      # Rewrite Views dir
      settings.views = File.expand_path(File.join($PROJECT_DIR, 'views'))
    
      configure :development do
        require 'sinatra/reloader'
        register Sinatra::Reloader
      end
    
      # mount Sinatra Helpers
    
      # mount Sinatra middlewares
    
    end
    
    
    # Share Configuration
    
    class MyPageServer < BaseController
    end
    
    class MyApiServer < BaseController
    end
    
    

    ORM & Tools

    Provide rails-like rake task help you build app quickly.

    rake db:check                   # Checking for current migrations
    rake db:connect                 # Connect database
    rake db:console                 # Database Console
    rake db:create[database_name]   # Create database
    rake db:create_migration[name]  # Create a migration
    rake db:drop[database_name]     # Drop database
    rake db:ls                      # List database tables
    rake db:migrate[version]        # Run migrations
    rake db:rollback[version]       # Rollback to migration
    rake db:version                 # Prints current schema version
    rake list                       # List all tasks
    rake seed:all                   # Seed: run all seeds
    rake seed:run[seed_name]        # Seed: run seed
    rake server:run                 # Run server
    rake test                       # Run tests
    

    Project Structure

    .
    ├── Dockerfile # Common Dockerfile
    ├── Gemfile
    ├── Gemfile.lock
    ├── README.md
    ├── Rakefile # Rake Task Index File.
    ├── bases # Base configured class. You can make different BaseClasses then reuse them.
    │   └── base_controller.rb # You contoller can inherit it or write yourself.
    ├── config.ru # Application index. You can mount controllers and routes here.
    ├── configs # You can make different configs for applications
    │   └── config.rb # Base config
    ├── controllers 
    │   └── root_controller.rb
    ├── cores # Inject ENVS and autoloads files, make MVC works
    │   ├── 01_config.rb # Names can controller mount order
    │   └── bootstrap.rb
    ├── dbs # You can make multi database here
    │   ├── default_db.rb # default database connect instance
    │   └── migrations # save database migrations
    ├── docs
    │   └── good.feature
    ├── log # Directory for save logs by default
    │   └── development.log
    ├── loggers # Loggers for application
    │   └── default_logger.rb
    ├── public # Public resources
    │   └── favicon.svg
    ├── seeds # Seeds
    ├── tasks # Rake helpful tasks 
    │   ├── db_task.rb
    │   ├── seed_task.rb
    │   ├── server_task.rb
    │   └── test_task.rb
    ├── tests # Test cases
    │   └── test_demo.rb
    └── views # views template
        ├── base.erb
        └── root.erb
    
    

    Bootstrap & Load orders

    For Rake

    require_relative './cores/bootstrap'
    Bootstrap.rake
    

    It will auto load files make sure rake task can work.

    In rake we can use Config.current to read configuration.

    DB also available.

    For Rack/Applications

    In the same way

    require_relative './cores/bootstrap'
    Bootstrap.rack
    # OR
    # Bootstrap.apps
    

    It will autoload all dep mods. Share with a context.

    Change load orders

    cores/bootstrap.rb defines different load orders, you can change.

    In anther way, you can change filename to e.g 00_before_all.rb01_first_load.rb to control mods load order.

    目前尚无回复
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   我们的愿景   ·   实用小工具   ·   1041 人在线   最高记录 6543   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 29ms · UTC 19:18 · PVG 03:18 · LAX 12:18 · JFK 15:18
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.