filepress 0.3.0 → 0.3.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: cd4430ee794157675a4edeeb36bf4d09ca137300f1ca4b6dc3f1f1b1dd23c387
4
- data.tar.gz: 6a164c8673b1cd8d1be639f6ff03955bee8f3306a6e25ad8bc4f0274c6fd93ed
3
+ metadata.gz: 745a5e3486f737ba398c1d8418299aafe2aafdee92593ab4ddc97ee5860db0d7
4
+ data.tar.gz: f6cf79cf496608719ff2cd65531d9240645f6953b65ecf72c494e41261e84810
5
5
  SHA512:
6
- metadata.gz: b707d65fb21ec3d1621705e63c7d7bd1707fb4804982f4029e93946ddc15ada6b155c2bc434aae8e60a16f2d13990815743b6c6d2ab413d1395949a0287d6a10
7
- data.tar.gz: 1577478c2cbcbfb39931ef4cd00ad920802646da96ba0cdd2d40548bc8d883519b80abd7a3d5fefaf1fbdaa2b02313a07e51deb400ca3a675d7e1ba9101d62a9
6
+ metadata.gz: 4c0e44caf392542ea428f53d2db17366028ad5944f6436a87c8cdc728fe09052159c176d7638a7804a8230573392985d7540ab4ca6c91b11e1348fe240e98b6f
7
+ data.tar.gz: 04f98d47ed32028b8b233abeaf1597d81d6a03959fb1bc235b9face53334627036aa846b5c52551330025c57fc4b4ea5b00fda169be87691cce12b05b8ee8b9b
data/README.md CHANGED
@@ -1,32 +1,25 @@
1
1
  # Filepress
2
2
 
3
- Filepress is a minimal Rails plugin that offers the best of both worlds for content management:
4
- - Write and version control your content in Markdown (or a similar format)
5
- - Sync it seamlessly to ActiveRecord models so you can harness the full power of a Rails backend.
3
+ Filepress is a minimal Rails plugin that syncs content from flat files to ActiveRecord models. Write your posts in Markdown, version control them with git, and query them with ActiveRecord.
6
4
 
7
- Ideal for blogs, documentation, or any content-driven Rails app where you want the flexibility of flat files and the structure of a database.
5
+ ## Build a blog with Filepress
8
6
 
9
- ## Getting Started
10
-
11
- 1. Install the gem
12
-
13
- Add it to your Gemfile:
7
+ ### 1. Install the gem
14
8
 
15
9
  ```ruby
16
10
  gem "filepress"
17
11
  ```
18
12
 
19
- 2. Create a model to represent your content
13
+ ### 2. Generate a Post model
20
14
 
21
- Be sure to include a field that can serve as a unique identifier (e.g. `slug`):
15
+ Include a `slug` field to serve as the unique identifier (derived from the filename) and a `body` field for the content:
22
16
 
23
17
  ```bash
24
- rails g model Post title:string slug:string body:text
18
+ bin/rails generate model Post title:string slug:string:uniq body:text published:boolean
19
+ bin/rails db:migrate
25
20
  ```
26
21
 
27
- 3. Enable Filepress for your model
28
-
29
- Use the `filepress` method in your model class:
22
+ ### 3. Enable Filepress
30
23
 
31
24
  ```ruby
32
25
  class Post < ApplicationRecord
@@ -34,26 +27,100 @@ class Post < ApplicationRecord
34
27
  end
35
28
  ```
36
29
 
37
- 4. Add some content
30
+ ### 4. Write a post
38
31
 
39
- Create Markdown files in `app/content/posts`. The filename becomes the slug, and YAML frontmatter maps to your model's attributes:
32
+ Create a Markdown file at `app/content/posts/hello-world.md`. The filename becomes the slug, and YAML frontmatter maps to model attributes:
40
33
 
41
34
  ```markdown
42
35
  ---
43
- title: My First Post
36
+ title: Hello World
44
37
  published: true
45
38
  ---
46
39
 
47
- Hello, this is my first post!
40
+ This is my first post!
41
+ ```
42
+
43
+ Filepress syncs your content to the database automatically — on boot, on deploy, and whenever files change in development.
44
+
45
+ ### 5. Add a controller and routes
46
+
47
+ ```ruby
48
+ # config/routes.rb
49
+ resources :posts, only: [:index, :show]
50
+ ```
51
+
52
+ ```ruby
53
+ # app/controllers/posts_controller.rb
54
+ class PostsController < ApplicationController
55
+ def index
56
+ @posts = Post.all
57
+ end
58
+
59
+ def show
60
+ @post = Post.find_by!(slug: params[:id])
61
+ end
62
+ end
63
+ ```
64
+
65
+ Override `to_param` so Rails generates URLs using the slug:
66
+
67
+ ```ruby
68
+ class Post < ApplicationRecord
69
+ filepress
70
+
71
+ def to_param
72
+ slug
73
+ end
74
+ end
75
+ ```
76
+
77
+ ### 6. Add views
78
+
79
+ ```erb
80
+ <%# app/views/posts/index.html.erb %>
81
+ <% @posts.each do |post| %>
82
+ <h2><%= link_to post.title, post %></h2>
83
+ <% end %>
84
+ ```
85
+
86
+ ```erb
87
+ <%# app/views/posts/show.html.erb %>
88
+ <h1><%= @post.title %></h1>
89
+ <%= @post.body.html_safe %>
90
+ ```
91
+
92
+ ### 7. Render Markdown as HTML
93
+
94
+ Filepress stores the raw file content. To render Markdown to HTML at sync time, add a gem like [Kramdown](https://kramdown.gettalong.org) and a `before_save` callback:
95
+
96
+ ```ruby
97
+ gem "kramdown"
98
+ gem "kramdown-parser-gfm"
48
99
  ```
49
100
 
50
- That's it! Filepress syncs your content to the database automatically — on boot, on deploy, and whenever files change in development. No rake tasks, no deploy hooks.
101
+ ```ruby
102
+ class Post < ApplicationRecord
103
+ filepress
104
+
105
+ before_save :render_body, if: :body_changed?
106
+
107
+ def to_param
108
+ slug
109
+ end
110
+
111
+ private
112
+
113
+ def render_body
114
+ self.body = Kramdown::Document.new(body, input: "GFM").to_html
115
+ end
116
+ end
117
+ ```
51
118
 
52
- You're free to query your content via ActiveRecord like any other model. Filepress doesn't dictate how you render the body use a Markdown parser like Kramdown, Redcarpet, or similar.
119
+ The body is converted once on sync, not on every request. Any Markdown library worksRedcarpet, CommonMarker, etc.
53
120
 
54
121
  ## How it works
55
122
 
56
- Filepress reads your content files, extracts YAML frontmatter, and uses the values to populate or update model attributes. The rest of the file becomes the value of the body attribute (or another field, if configured).
123
+ Filepress reads your content files, extracts YAML frontmatter, and uses the values to populate or update model attributes. The rest of the file becomes the body.
57
124
 
58
125
  - Syncs are wrapped in a transaction — if any file fails, nothing changes
59
126
  - Unknown frontmatter keys (that don't match a column) are silently ignored
@@ -61,54 +128,36 @@ Filepress reads your content files, extracts YAML frontmatter, and uses the valu
61
128
 
62
129
  ## Configuration
63
130
 
64
- You can customize how Filepress behaves by passing options to `filepress`:
131
+ Customise Filepress by passing options to `filepress`:
65
132
 
66
- ### `from:` — Set a custom content directory
133
+ ### `from:` — Custom content directory
67
134
 
68
135
  ```ruby
69
- class Post < ApplicationRecord
70
- filepress from: "app/my_custom_content_folder"
71
- end
136
+ filepress from: "app/my_custom_content_folder"
72
137
  ```
73
138
 
74
- ### `extensions:` — Use filetypes besides Markdown
139
+ ### `extensions:` — File types besides Markdown
75
140
 
76
141
  ```ruby
77
- class Post < ApplicationRecord
78
- filepress extensions: ["html", "txt"]
79
- end
142
+ filepress extensions: ["html", "txt"]
80
143
  ```
81
144
 
82
- ### `key:` — Use a unique identifier other than `slug`
145
+ ### `key:` — Unique identifier other than `slug`
83
146
 
84
147
  ```ruby
85
- class Post < ApplicationRecord
86
- filepress key: :name
87
- end
148
+ filepress key: :name
88
149
  ```
89
150
 
90
- ### `body:` — Set which attribute stores the main content
151
+ ### `body:` — Attribute that stores the main content
91
152
 
92
153
  ```ruby
93
- class Post < ApplicationRecord
94
- filepress body: :content
95
- end
154
+ filepress body: :content
96
155
  ```
97
156
 
98
- ### `destroy_stale:` — Prevent deletion of records when files are removed
157
+ ### `destroy_stale:` — Keep records when files are removed
99
158
 
100
- By default, Filepress deletes records when the corresponding file is removed. Disable this behaviour with:
159
+ By default, Filepress deletes records when the corresponding file is removed. Disable this with:
101
160
 
102
161
  ```ruby
103
- class Post < ApplicationRecord
104
- filepress destroy_stale: false
105
- end
162
+ filepress destroy_stale: false
106
163
  ```
107
-
108
- ## Why Filepress?
109
-
110
- Filepress is for you if:
111
-
112
- - You prefer writing content in files
113
- - You want the convenience of version control for content
114
- - And you still want powerful querying, associations, validations and all the other Rails goodness
@@ -7,16 +7,7 @@ module Filepress
7
7
  end
8
8
 
9
9
  initializer "filepress.file_watcher" do |app|
10
- content_path = app.root.join("app", "content")
11
-
12
- app.config.after_initialize do
13
- if content_path.exist?
14
- extensions = Filepress.watched_extensions
15
- app.reloaders << app.config.file_watcher.new([], { content_path.to_s => extensions }) do
16
- Filepress.sync
17
- end
18
- end
19
- end
10
+ Filepress.app = app
20
11
  end
21
12
  end
22
13
  end
@@ -1,3 +1,3 @@
1
1
  module Filepress
2
- VERSION = "0.3.0"
2
+ VERSION = "0.3.2"
3
3
  end
data/lib/filepress.rb CHANGED
@@ -6,6 +6,8 @@ require "filepress/sync"
6
6
 
7
7
  module Filepress
8
8
  class << self
9
+ attr_accessor :app
10
+
9
11
  def registry
10
12
  @registry ||= {}
11
13
  end
@@ -13,12 +15,22 @@ module Filepress
13
15
  def register(model_class, options)
14
16
  config = options.merge(model_class: model_class)
15
17
  registry[model_class.name] = config
16
- Sync.new(config).perform
18
+
19
+ watch(config[:from], config[:extensions])
20
+
21
+ trace = TracePoint.new(:end) do |tp|
22
+ if tp.self == model_class
23
+ trace.disable
24
+ Sync.new(config).perform
25
+ end
26
+ end
27
+ trace.enable
17
28
  end
18
29
 
19
- def watched_extensions
20
- exts = registry.values.flat_map { |config| config[:extensions] }.uniq
21
- exts.empty? ? ["md"] : exts
30
+ def watch(dir, extensions)
31
+ return unless watched.add?(dir)
32
+
33
+ app.reloaders << app.config.file_watcher.new([], { dir => extensions }) { sync }
22
34
  end
23
35
 
24
36
  def sync
@@ -26,5 +38,11 @@ module Filepress
26
38
  Sync.new(config).perform
27
39
  end
28
40
  end
41
+
42
+ private
43
+
44
+ def watched
45
+ @watched ||= Set.new
46
+ end
29
47
  end
30
48
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: filepress
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.0
4
+ version: 0.3.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Carl Dawson