Browse Source

Add a `draft` field to Post

TODO: handle drafts differently on the frontend
master
Dylan Baker 3 years ago
parent
commit
25daa48d08
4 changed files with 43 additions and 9 deletions
  1. 10
    2
      oslo-lib/src/post.rs
  2. 25
    0
      oslo-lib/src/util.rs
  3. 7
    6
      templates/components.html
  4. 1
    1
      templates/edit.html

+ 10
- 2
oslo-lib/src/post.rs View File

@@ -4,6 +4,10 @@ use std::io::{Error, ErrorKind};
4 4
 
5 5
 use crate::{fs, util};
6 6
 
7
+fn f() -> bool {
8
+    false
9
+}
10
+
7 11
 #[derive(Debug, Serialize, Deserialize)]
8 12
 pub struct Post {
9 13
     pub title: String,
@@ -11,6 +15,10 @@ pub struct Post {
11 15
     pub body: String,
12 16
     pub html: String,
13 17
     pub date: String,
18
+    #[serde(serialize_with = "util::int_from_bool")]
19
+    #[serde(deserialize_with = "util::bool_from_int")]
20
+    #[serde(default = "f")]
21
+    pub draft: bool,
14 22
 }
15 23
 
16 24
 impl Post {
@@ -25,9 +33,9 @@ impl Post {
25 33
     pub fn from_str(blob: &str) -> Result<Post, Error> {
26 34
         let post: Post = match serde_json::from_str(blob) {
27 35
             Ok(p) => Ok(p),
28
-            Err(_) => Err(Error::new(
36
+            Err(e) => Err(Error::new(
29 37
                 ErrorKind::Other,
30
-                format!("Error deserializing post"),
38
+                format!("Error deserializing post: {}", e.to_string()),
31 39
             )),
32 40
         }?;
33 41
         Ok(post)

+ 25
- 0
oslo-lib/src/util.rs View File

@@ -1,4 +1,9 @@
1 1
 use pulldown_cmark::{html, Options, Parser};
2
+use serde::Serializer;
3
+use serde::{
4
+    de::{Deserialize, Deserializer},
5
+    Serialize,
6
+};
2 7
 
3 8
 pub fn generate_html(s: &str) -> String {
4 9
     let options = Options::all();
@@ -7,3 +12,23 @@ pub fn generate_html(s: &str) -> String {
7 12
     html::push_html(&mut html_output, parser);
8 13
     html_output
9 14
 }
15
+
16
+pub fn bool_from_int<'de, D>(deserializer: D) -> Result<bool, D::Error>
17
+where
18
+    D: Deserializer<'de>,
19
+{
20
+    match u8::deserialize(deserializer)? {
21
+        1 => Ok(true),
22
+        _ => Ok(false),
23
+    }
24
+}
25
+
26
+pub fn int_from_bool<S>(value: &bool, s: S) -> Result<S::Ok, S::Error>
27
+where
28
+    S: Serializer,
29
+{
30
+    match value {
31
+        true => 1.serialize(s),
32
+        false => 0.serialize(s),
33
+    }
34
+}

+ 7
- 6
templates/components.html View File

@@ -26,11 +26,6 @@
26 26
 
27 27
 {% macro form(post=false, action) %}
28 28
   <form class="form" method="POST" action="{{ action }}" id="post-form">
29
-    <input
30
-      type="hidden"
31
-      name="id"
32
-      value="{% if post %}{{ post.slug }}{% endif %}"
33
-    />
34 29
     <input
35 30
       type="hidden"
36 31
       name="date"
@@ -71,9 +66,15 @@
71 66
         required
72 67
       >{% if post %}{{ post.body }}{% endif %}</textarea>
73 68
     </div>
69
+    <div class="form__field">
70
+       <label for="draft">
71
+        Save as Draft?
72
+        <input type="checkbox" name="draft" value="1" {% if post.draft %}checked{% endif %}>
73
+       </label>
74
+    </div>
74 75
     <div class="form__field">
75 76
       <a class="btn" href="#" data-preview>Preview</a>
76
-      <input class="btn btn--green" type="submit" value="Post" />
77
+      <input class="btn btn--green" type="submit" value="Post">
77 78
     </div>
78 79
   </form>
79 80
 {% endmacro %}

+ 1
- 1
templates/edit.html View File

@@ -2,7 +2,7 @@
2 2
 {% block content %}
3 3
 
4 4
   <div class="posts">
5
-    {{ components::form(post=post, action="/posts/{{ post.slug }}") }}
5
+    {{ components::form(post=post, action="/posts/" ~ post.slug) }}
6 6
   </div>
7 7
 
8 8
 {% endblock %}

Loading…
Cancel
Save