require 'rack' require 'maglove/middleware/live_reload' module MagLove class Server attr_reader :app, :options def self.start(port, theme, templates) app = Rack::Builder.new do use MagLove::Middleware::LiveReload, mount: "/maglove", theme: theme, templates: templates use Rack::Static, urls: ["/fonts", "/themes"], root: "dist" use Rack::Static, urls: ["/images"], root: "dist/themes/#{theme}" run MagLove::Server.new(theme: theme, templates: templates, port: port) end Rack::Server.start(app: app, Port: port, server: :puma) end def initialize(options) @options = options Maglove::Engine.configure do |config| config.asset_uri = "." config.block_path = "src/themes/#{options[:theme]}/blocks" end end def call(env) template = env["PATH_INFO"].sub("/", "") if env["PATH_INFO"] == "/maglove.js" [200, { 'Content-Type' => 'text/javascript' }, [Maglove.assets_dir.file("maglove.js").read]] elsif env["PATH_INFO"] == "/maglove-widgets.js" widgets_file = Workspace.dir(Dir.pwd).file("node_modules/maglove-widgets/dist/widgets.js") if widgets_file.exists? [200, { 'Content-Type' => 'text/javascript' }, [widgets_file.read]] else [200, { 'Content-Type' => 'text/javascript' }, ["export default { ready: function() { alert('Module \\\"maglove-widgets\\\" not installed. Run \\\"npm install maglove-widgets\\\" to install.'); return this; }, then: function() {} }"]] end elsif env["PATH_INFO"] == "/maglove.css" [200, { 'Content-Type' => 'text/css' }, [Maglove.assets_dir.file("maglove.css").read]] elsif @options[:templates].include?(template) [200, { 'Content-Type' => 'text/html' }, [process(template)]] else [200, { 'Content-Type' => 'text/html' }, [Maglove::Engine.render(Maglove.assets_dir.file("index.haml").read, @options)]] end end def process(template) css_contents = Workspace::Dir.new(Dir.pwd, "dist/themes/#{options[:theme]}").file("theme.css").read js_contents = Workspace::Dir.new(Dir.pwd, "dist/themes/#{options[:theme]}").file("theme.js").read template_asset = MagLove::Asset::Theme.new("templates/#{template}.haml", { base: false }) Maglove::Engine.render(Maglove.assets_dir.file("maglove.haml").read, { theme: @options[:theme], contents: template_asset.contents, css_contents: css_contents, js_contents: js_contents, template: template, port: @options[:port] || 3000 }) end def setup(theme) @widget_stamps = {} Dir["widgets/*.rb"].each { |file| @widget_stamps[file] = File.mtime(file).to_i } @options[:templates].each do |template| mount("/#{template}") do |req, res| Dir["widgets/*.rb"].each do |file| stamp = File.mtime(file).to_i next unless @widget_stamps[file] and @widget_stamps[file] < stamp @widget_stamps[file] = stamp debug("▸ reloading widget: #{file}") load(file) end end end end end end