Repository: ultrabug/py3status

Issue:
Formatting returns empty when closing with a False or None placeholder
Formatting returns empty when closing with a `False` or `None` placeholder.
```diff
diff --git a/py3status/modules/static_string.py b/py3status/modules/static_string.py
index dbcec8c6..593b3740 100644
--- a/py3status/modules/static_string.py
+++ b/py3status/modules/static_string.py
@@ -18,10 +18,17 @@ class Py3status:
     # available configuration parameters
     format = 'Hello, world!'
 
+    # format = 'A, B, C // {true}'    # IS OK     | A, B, C // True
+    # format = 'A, B, C // {false}'   # IS NOT OK |
+    # format = 'A, B, C // {none}'    # IS NOT OK |
+    # format = 'A, B, C // {false} '  # IS OK     | A, B, C // False
+    # format = 'A, B, C // {none} '   # IS OK     | A, B, C // None
+
     def static_string(self):
+        new_dict = {'true': True, 'false': False, 'none': None}
         return {
             'cached_until': self.py3.CACHE_FOREVER,
-            'full_text': self.py3.safe_format(self.format),
+            'full_text': self.py3.safe_format(self.format, new_dict),
         }
```

Discussion:
tobes: IMHO this breaks the formatter, because the original tests fail.

With #1095 I do not actually understand what the issue is that you are describing.  Maybe if I understood that then this would make more sense.

Now maybe the current behaviour of the formatter is incorrect.  Then we should have a clear discussion about  that and how to improve it.
lasers: Brief explanation. Apply the git patch. I included some examples. Test each as you go.
```
+    # format = 'A, B, C // {true}'    # IS OK     | A, B, C // True
+    # format = 'A, B, C // {false}'   # IS NOT OK |
+    # format = 'A, B, C // {none}'    # IS NOT OK |
+    # format = 'A, B, C // {false} '  # IS OK     | A, B, C // False
+    # format = 'A, B, C // {none} '   # IS OK     | A, B, C // None
```

Different examples.
* `'Repeat: {repeat}'` -- Expected -- `'Repeat: False'` -- Got `''`.
* `'Hi. Long string. {none}'` -- Expected -- `Hi. Long string. None` -- Got `''`.

First, I never knew about this `{false}` --> `''` and `{none}` --> `''` until I made a pull request... and failed the tests here. Color me surprised. I think few tests may be wrong (fixed now) because it prints `True` on `{true}` and just disappear on `{false}`, `{none}`.
tobes: > First, I never knew about this {false} --> '' and {none} --> '' until I made a pull request

That is intentional.  Now whether it is a good idea is a different issue. 

The main issue is that the formatter still lacks documentation.
lasers: >That is intentional. Now whether it is a good idea is a different issue.

I amended two tests in this commit. Check them out and decide.

And we can have many `{False}`, `{None}` as we want... and still get nothing.
```
diff --git a/py3status/modules/static_string.py b/py3status/modules/static_string.py
index dbcec8c6..e15b30a4 100644
--- a/py3status/modules/static_string.py
+++ b/py3status/modules/static_string.py
@@ -16,12 +16,15 @@ class Py3status:
     """
     """
     # available configuration parameters
-    format = 'Hello, world!'
+    format = ' '.join(['{false} {none}' for x in range(5)])
+    # format += ' '
+    # format += ' {true}'
 
     def static_string(self):
         return {
             'cached_until': self.py3.CACHE_FOREVER,
-            'full_text': self.py3.safe_format(self.format),
+            'full_text': self.py3.safe_format(
+                self.format, {'true': True, 'false': False, 'none': None}),
         }
```
```
$ python3 static_string.py
[]
```
```
$ python3 static_string.py    # add space
{'full_text': 'False None False None False None False None False None ', 'cached_until': -1}
```
```
$ python3 static_string.py    # add {true}
{'cached_until': -1, 'full_text': 'False None False None False None False None False None True'}
```
It's been said many times that the truth will set you free. I guess it was really true.
ultrabug: @tobes bump plz?

Patch:
diff --git a/py3status/formatter.py b/py3status/formatter.py
index e265819e..db2875de 100644
--- a/py3status/formatter.py
+++ b/py3status/formatter.py
@@ -268,7 +268,9 @@ class Placeholder:
                 output = u'{%s%s}' % (self.key, self.format)
                 value = value_ = output.format(**{self.key: value})
 
-            if block.commands.not_zero:
+            if block.parent is None:
+                valid = True
+            elif block.commands.not_zero:
                 valid = value_ not in ['', 'None', None, False, '0', '0.0', 0, 0.0]
             else:
                 # '', None, and False are ignored


Test patch:
diff --git a/tests/test_formatter.py b/tests/test_formatter.py
index 0d1bf9b5..76febab4 100644
--- a/tests/test_formatter.py
+++ b/tests/test_formatter.py
@@ -296,10 +296,18 @@ def test_26():
 
 
 def test_27():
-    run_formatter({'format': '{None}', 'expected': '', })
+    run_formatter({'format': '{None}', 'expected': 'None', })
 
 
 def test_27a():
+    run_formatter({'format': '{None} {no}', 'expected': 'None False', })
+
+
+def test_27b():
+    run_formatter({'format': '[Hello {None}] {no}', 'expected': ' False', })
+
+
+def test_27c():
     run_formatter({'format': '[Hi, my name is {None_str}]', 'expected': '', })
 
 
@@ -312,7 +320,7 @@ def test_29():
 
 
 def test_30():
-    run_formatter({'format': '{no}', 'expected': '', })
+    run_formatter({'format': '{no}', 'expected': 'False', })
 
 
 def test_31():
@@ -1134,7 +1142,7 @@ def test_module_true_value():
 
 
 def test_module_false_value():
-    run_formatter({'format': '{module_false}', 'expected': ''})
+    run_formatter({'format': '{module_false}', 'expected': 'False'})
 
 
 def test_zero_format_1():