Merge branch 'develop' into auto-linewrap

This commit is contained in:
Jonathan van der Steege 2022-07-17 14:27:31 +02:00
commit 488890d165
53 changed files with 539 additions and 448 deletions

View file

@ -39,12 +39,7 @@ runs:
echo 'DEPS_INSTALLED=true' >> $GITHUB_ENV
shell: bash
- name: Linting
- name: Linting & Testing
if: ${{ env.DEPS_INSTALLED == 'true' }}
run: poetry run poe ci-lint
shell: bash
- name: Testing
if: ${{ env.DEPS_INSTALLED == 'true' }}
run: poetry run poe ci-test
run: poetry run poe test
shell: bash

View file

@ -2,28 +2,18 @@
## [Unreleased](https://github.com/jrnl-org/jrnl/)
[Full Changelog](https://github.com/jrnl-org/jrnl/compare/v3.0-beta...HEAD)
**Fixed bugs:**
- Adding new entry with date only works with format m.d.Y [\#1509](https://github.com/jrnl-org/jrnl/issues/1509)
**Build:**
- Use tox [\#1361](https://github.com/jrnl-org/jrnl/issues/1361)
- Stop hardcoding bot info in changelog pipeline [\#1506](https://github.com/jrnl-org/jrnl/pull/1506) ([wren](https://github.com/wren))
- Fix Poetry caching for accessibility tests [\#1505](https://github.com/jrnl-org/jrnl/pull/1505) ([wren](https://github.com/wren))
- Implement Tox for testing [\#1504](https://github.com/jrnl-org/jrnl/pull/1504) ([wren](https://github.com/wren))
- Replace `make` with python alternative \(`poe`\) [\#1503](https://github.com/jrnl-org/jrnl/pull/1503) ([wren](https://github.com/wren))
- Update copyright year [\#1502](https://github.com/jrnl-org/jrnl/pull/1502) ([wren](https://github.com/wren))
## [v3.0-beta](https://pypi.org/project/jrnl/v3.0-beta/) (2022-06-11)
[Full Changelog](https://github.com/jrnl-org/jrnl/compare/v2.8.4...v3.0-beta)
[Full Changelog](https://github.com/jrnl-org/jrnl/compare/v3.0...HEAD)
**Implemented enhancements:**
- Warn user when there are duplicate keys in the config file [\#1415](https://github.com/jrnl-org/jrnl/issues/1415)
## [v3.0](https://pypi.org/project/jrnl/v3.0/) (2022-07-09)
[Full Changelog](https://github.com/jrnl-org/jrnl/compare/v3.0-beta2...v3.0)
**Implemented enhancements:**
- Add --change-time command to change the timestamp of an entry [\#1429](https://github.com/jrnl-org/jrnl/issues/1429)
- Show name of journal when creating a password/encrypting [\#1478](https://github.com/jrnl-org/jrnl/pull/1478) ([jonakeys](https://github.com/jonakeys))
- Rework how all output and messaging works in jrnl [\#1475](https://github.com/jrnl-org/jrnl/pull/1475) ([wren](https://github.com/wren))
- Implement --change-time flag [\#1452](https://github.com/jrnl-org/jrnl/pull/1452) ([richardjs](https://github.com/richardjs))
@ -32,14 +22,7 @@
**Fixed bugs:**
- --debug leads to logging error after composing new entry [\#1496](https://github.com/jrnl-org/jrnl/issues/1496)
- Using -not argument by itself leads to new entry creation [\#1472](https://github.com/jrnl-org/jrnl/issues/1472)
- Empty config file leads to confusing error message [\#1420](https://github.com/jrnl-org/jrnl/issues/1420)
- "Entry not saved" text doesn't appear in default stdin editor [\#1419](https://github.com/jrnl-org/jrnl/issues/1419)
- jrnl --encrypt doesn't prompt me for password change [\#1358](https://github.com/jrnl-org/jrnl/issues/1358)
- '-not -contains x' raises an AttributeError exception [\#1350](https://github.com/jrnl-org/jrnl/issues/1350)
- Exception when providing folder name of folder that does not exist as journal path [\#1293](https://github.com/jrnl-org/jrnl/issues/1293)
- display\_format: pretty and display\_format: short lead to crash [\#1263](https://github.com/jrnl-org/jrnl/issues/1263)
- Display message when no edits take place [\#1510](https://github.com/jrnl-org/jrnl/pull/1510) ([apainintheneck](https://github.com/apainintheneck))
- Fixed error related to display\_format in config file for some values [\#1495](https://github.com/jrnl-org/jrnl/pull/1495) ([apainintheneck](https://github.com/apainintheneck))
- Create folder if config ends with \(back\)slash [\#1492](https://github.com/jrnl-org/jrnl/pull/1492) ([jonakeys](https://github.com/jonakeys))
- `-not` search parameter no longer opens editor [\#1490](https://github.com/jrnl-org/jrnl/pull/1490) ([apainintheneck](https://github.com/apainintheneck))
@ -53,12 +36,18 @@
**Deprecated:**
- Remove "sample" format and its asteval dependency [\#1435](https://github.com/jrnl-org/jrnl/issues/1435)
- Drop support for Python 3.7 and 3.8 [\#1412](https://github.com/jrnl-org/jrnl/pull/1412) ([micahellison](https://github.com/micahellison))
**Build:**
- Clean up .gitignore [\#1286](https://github.com/jrnl-org/jrnl/issues/1286)
- Pin `pytest-bdd` to \<6.0 to temporarily avoid breaking changes [\#1536](https://github.com/jrnl-org/jrnl/pull/1536) ([wren](https://github.com/wren))
- Reduce difference between local and CI environments [\#1518](https://github.com/jrnl-org/jrnl/pull/1518) ([wren](https://github.com/wren))
- Add bdd tests for jrnl installation [\#1513](https://github.com/jrnl-org/jrnl/pull/1513) ([apainintheneck](https://github.com/apainintheneck))
- Stop hardcoding bot info in changelog pipeline [\#1506](https://github.com/jrnl-org/jrnl/pull/1506) ([wren](https://github.com/wren))
- Fix Poetry caching for accessibility tests [\#1505](https://github.com/jrnl-org/jrnl/pull/1505) ([wren](https://github.com/wren))
- Implement Tox for testing [\#1504](https://github.com/jrnl-org/jrnl/pull/1504) ([wren](https://github.com/wren))
- Replace `make` with python alternative \(`poe`\) [\#1503](https://github.com/jrnl-org/jrnl/pull/1503) ([wren](https://github.com/wren))
- Update copyright year [\#1502](https://github.com/jrnl-org/jrnl/pull/1502) ([wren](https://github.com/wren))
- Add Python 3.11 to PR tests [\#1500](https://github.com/jrnl-org/jrnl/pull/1500) ([micahellison](https://github.com/micahellison))
- Pin jinja2 in docs requirements to keep readthedocs builds from failing [\#1439](https://github.com/jrnl-org/jrnl/pull/1439) ([micahellison](https://github.com/micahellison))
- Tidy up git ignore [\#1414](https://github.com/jrnl-org/jrnl/pull/1414) ([nelnog](https://github.com/nelnog))
@ -69,7 +58,8 @@
**Packaging:**
- Sync jrnl's Python version support more closely to Python release cycle [\#1406](https://github.com/jrnl-org/jrnl/issues/1406)
- Bump cryptography from 37.0.2 to 37.0.3 [\#1516](https://github.com/jrnl-org/jrnl/pull/1516) ([dependabot[bot]](https://github.com/apps/dependabot))
- Bump poethepoet from 0.13.1 to 0.14.0 [\#1514](https://github.com/jrnl-org/jrnl/pull/1514) ([dependabot[bot]](https://github.com/apps/dependabot))
- Bump keyring from 23.5.1 to 23.6.0 [\#1499](https://github.com/jrnl-org/jrnl/pull/1499) ([dependabot[bot]](https://github.com/apps/dependabot))
- Bump pyxdg from 0.27 to 0.28 [\#1497](https://github.com/jrnl-org/jrnl/pull/1497) ([dependabot[bot]](https://github.com/apps/dependabot))
- Bump keyring from 23.5.0 to 23.5.1 [\#1487](https://github.com/jrnl-org/jrnl/pull/1487) ([dependabot[bot]](https://github.com/apps/dependabot))

View file

@ -59,7 +59,7 @@ representative at an online or offline event.
## Enforcement
Instances of abusive, harassing, or otherwise unacceptable behavior may be
reported by [emailing the maintainers](mailto:jrnl-sh@googlegroups.com).
reported by [emailing the maintainers](mailto:maintainers@jrnl.sh).
All complaints will be reviewed and investigated promptly and fairly.
All community leaders are obligated to respect the privacy and security of the

View file

@ -1,6 +1,6 @@
# Security
If you've discovered a potential security issue in jrnl, please contact the maintainers at [jrnl-sh@googlegroups.com](mailto:jrnl-sh@googlegroups.com).
If you've discovered a potential security issue in jrnl, please contact the maintainers at [maintainers@jrnl.sh](mailto:maintainers@jrnl.sh).
You can also feel free to [open an issue](https://github.com/jrnl-org/jrnl/issues/new/choose) (but please don't disclose the vulnerability) in case the email goes to spam.

View file

@ -4,22 +4,22 @@
import datetime
import fnmatch
import os
from pathlib import Path
import platform
import plistlib
import re
import socket
import time
import uuid
from pathlib import Path
from xml.parsers.expat import ExpatError
import pytz
import tzlocal
from . import Entry
from . import Journal
from . import __title__
from . import __version__
from jrnl import Entry
from jrnl import Journal
from jrnl import __title__
from jrnl import __version__
class DayOne(Journal.Journal):

View file

@ -18,15 +18,14 @@ from cryptography.hazmat.primitives.ciphers import algorithms
from cryptography.hazmat.primitives.ciphers import modes
from cryptography.hazmat.primitives.kdf.pbkdf2 import PBKDF2HMAC
from .Journal import Journal
from .Journal import LegacyJournal
from .prompt import create_password
from jrnl.exception import JrnlException
from jrnl.Journal import Journal
from jrnl.Journal import LegacyJournal
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.output import print_msg
from jrnl.prompt import create_password
def make_key(password):

View file

@ -5,8 +5,8 @@ import codecs
import fnmatch
import os
from . import Journal
from . import time
from jrnl import Journal
from jrnl import time
def get_files(journal_config):

View file

@ -6,15 +6,14 @@ import logging
import os
import re
from . import Entry
from . import time
from .prompt import yesno
from .path import expand_path
from jrnl.output import print_msg
from jrnl import Entry
from jrnl import time
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.output import print_msg
from jrnl.path import expand_path
from jrnl.prompt import yesno
class Tag:
@ -449,11 +448,11 @@ def open_journal(journal_name, config, legacy=False):
if config["journal"].strip("/").endswith(".dayone") or "entries" in os.listdir(
config["journal"]
):
from . import DayOneJournal
from jrnl import DayOneJournal
return DayOneJournal.DayOne(**config).open()
else:
from . import FolderJournal
from jrnl import FolderJournal
return FolderJournal.Folder(journal_name, **config).open()
@ -461,12 +460,12 @@ def open_journal(journal_name, config, legacy=False):
if legacy:
return LegacyJournal(journal_name, **config).open()
if config["journal"].endswith(os.sep):
from . import FolderJournal
from jrnl import FolderJournal
return FolderJournal.Folder(journal_name, **config).open()
return PlainJournal(journal_name, **config).open()
from . import EncryptedJournal
from jrnl import EncryptedJournal
if legacy:
return EncryptedJournal.LegacyEncryptedJournal(journal_name, **config).open()

View file

@ -2,7 +2,7 @@
# License: https://www.gnu.org/licenses/gpl-3.0.html
try:
from .__version__ import __version__
from jrnl.__version__ import __version__
except ImportError:
__version__ = "source"
__title__ = "jrnl"

View file

@ -3,7 +3,7 @@
import sys
from .cli import cli
from jrnl.cli import cli
if __name__ == "__main__":
sys.exit(cli())

View file

@ -1 +1 @@
__version__ = "v3.0-beta"
__version__ = "v3.0"

View file

@ -5,16 +5,16 @@ import argparse
import re
import textwrap
from .commands import postconfig_decrypt
from .commands import postconfig_encrypt
from .commands import postconfig_import
from .commands import postconfig_list
from .commands import preconfig_diagnostic
from .commands import preconfig_version
from .output import deprecated_cmd
from .plugins import EXPORT_FORMATS
from .plugins import IMPORT_FORMATS
from .plugins import util
from jrnl.commands import postconfig_decrypt
from jrnl.commands import postconfig_encrypt
from jrnl.commands import postconfig_import
from jrnl.commands import postconfig_list
from jrnl.commands import preconfig_diagnostic
from jrnl.commands import preconfig_version
from jrnl.output import deprecated_cmd
from jrnl.plugins import EXPORT_FORMATS
from jrnl.plugins import IMPORT_FORMATS
from jrnl.plugins import util
class WrappingFormatter(argparse.RawTextHelpFormatter):

View file

@ -5,14 +5,13 @@ import logging
import sys
import traceback
from .jrnl import run
from .args import parse_args
from jrnl.output import print_msg
from jrnl.args import parse_args
from jrnl.exception import JrnlException
from jrnl.jrnl import run
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.output import print_msg
def configure_logger(debug=False):

View file

@ -7,7 +7,7 @@ from string import whitespace
import colorama
from .os_compat import on_windows
from jrnl.os_compat import on_windows
if on_windows():
colorama.init()

View file

@ -17,11 +17,11 @@ avoid any possible overhead for these standalone commands.
import platform
import sys
from jrnl.output import print_msg
from jrnl.exception import JrnlException
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.output import print_msg
from jrnl.prompt import create_password
@ -50,14 +50,14 @@ conditions; for details, see: https://www.gnu.org/licenses/gpl-3.0.html"""
def postconfig_list(config, **kwargs):
from .output import list_journals
from jrnl.output import list_journals
print(list_journals(config))
def postconfig_import(args, config, **kwargs):
from .Journal import open_journal
from .plugins import get_importer
from jrnl.Journal import open_journal
from jrnl.plugins import get_importer
# Requires opening the journal
journal = open_journal(args.journal_name, config)
@ -70,10 +70,10 @@ def postconfig_encrypt(args, config, original_config, **kwargs):
"""
Encrypt a journal in place, or optionally to a new file
"""
from .EncryptedJournal import EncryptedJournal
from .Journal import open_journal
from .config import update_config
from .install import save_config
from jrnl.config import update_config
from jrnl.EncryptedJournal import EncryptedJournal
from jrnl.install import save_config
from jrnl.Journal import open_journal
# Open the journal
journal = open_journal(args.journal_name, config)
@ -118,10 +118,10 @@ def postconfig_encrypt(args, config, original_config, **kwargs):
def postconfig_decrypt(args, config, original_config, **kwargs):
"""Decrypts into new file. If filename is not set, we encrypt the journal file itself."""
from .Journal import PlainJournal
from .Journal import open_journal
from .config import update_config
from .install import save_config
from jrnl.config import update_config
from jrnl.install import save_config
from jrnl.Journal import PlainJournal
from jrnl.Journal import open_journal
journal = open_journal(args.journal_name, config)
journal.config["encrypt"] = False

View file

@ -5,18 +5,18 @@ import logging
import os
import colorama
from ruamel.yaml import YAML
import xdg.BaseDirectory
from ruamel.yaml import YAML
from ruamel.yaml import constructor
from . import __version__
from jrnl.output import list_journals
from jrnl.output import print_msg
from jrnl import __version__
from jrnl.exception import JrnlException
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from .path import home_dir
from jrnl.messages import MsgText
from jrnl.output import list_journals
from jrnl.output import print_msg
from jrnl.path import home_dir
# Constants
DEFAULT_CONFIG_NAME = "jrnl.yaml"
@ -160,10 +160,25 @@ def verify_config_colors(config):
def load_config(config_path):
"""Tries to load a config file from YAML."""
with open(config_path, encoding=YAML_FILE_ENCODING) as f:
yaml = YAML(typ="safe")
yaml.allow_duplicate_keys = True
return yaml.load(f)
try:
with open(config_path, encoding=YAML_FILE_ENCODING) as f:
yaml = YAML(typ="safe")
yaml.allow_duplicate_keys = False
return yaml.load(f)
except constructor.DuplicateKeyError as e:
print_msg(
Message(
MsgText.ConfigDoubleKeys,
MsgStyle.WARNING,
{
"error_message": e,
},
)
)
with open(config_path, encoding=YAML_FILE_ENCODING) as f:
yaml = YAML(typ="safe")
yaml.allow_duplicate_keys = True
return yaml.load(f)
def is_config_json(config_path):

View file

@ -8,15 +8,14 @@ import sys
import tempfile
from pathlib import Path
from jrnl.exception import JrnlException
from jrnl.messages import Message
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.os_compat import on_windows
from jrnl.os_compat import split_args
from jrnl.output import print_msg
from jrnl.exception import JrnlException
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
def get_text_from_editor(config, template=""):
suffix = ".jrnl"
@ -46,7 +45,7 @@ def get_text_from_editor(config, template=""):
os.remove(tmpfile)
if not raw:
raise JrnlException(Message(MsgText.NoTextReceived, MsgStyle.ERROR))
raise JrnlException(Message(MsgText.NoTextReceived, MsgStyle.NORMAL))
return raw

View file

@ -6,24 +6,23 @@ import logging
import os
import sys
from .path import home_dir
from .path import absolute_path
from .path import expand_path
from .config import DEFAULT_JOURNAL_KEY
from .config import get_config_path
from .config import get_default_config
from .config import get_default_journal_path
from .config import load_config
from .config import save_config
from .config import verify_config_colors
from .prompt import yesno
from .upgrade import is_old_version
from jrnl.output import print_msg
from jrnl.config import DEFAULT_JOURNAL_KEY
from jrnl.config import get_config_path
from jrnl.config import get_default_config
from jrnl.config import get_default_journal_path
from jrnl.config import load_config
from jrnl.config import save_config
from jrnl.config import verify_config_colors
from jrnl.exception import JrnlException
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.output import print_msg
from jrnl.path import absolute_path
from jrnl.path import expand_path
from jrnl.path import home_dir
from jrnl.prompt import yesno
from jrnl.upgrade import is_old_version
def upgrade_config(config_data, alt_config_path=None):

View file

@ -4,24 +4,23 @@
import logging
import sys
from . import install
from . import plugins
from .Journal import open_journal
from .config import get_journal_name
from .config import scope_config
from .config import get_config_path
from .editor import get_text_from_editor
from .editor import get_text_from_stdin
from . import time
from .override import apply_overrides
from jrnl import install
from jrnl import plugins
from jrnl import time
from jrnl.config import get_config_path
from jrnl.config import get_journal_name
from jrnl.config import scope_config
from jrnl.editor import get_text_from_editor
from jrnl.editor import get_text_from_stdin
from jrnl.exception import JrnlException
from jrnl.Journal import open_journal
from jrnl.messages import Message
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.output import print_msg
from jrnl.output import print_msgs
from .path import expand_path
from jrnl.exception import JrnlException
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from jrnl.override import apply_overrides
from jrnl.path import expand_path
def run(args):
@ -141,7 +140,7 @@ def write_mode(args, config, journal, **kwargs):
if not raw or raw.isspace():
logging.error("Write mode: couldn't get raw text or entry was empty")
raise JrnlException(Message(MsgText.NoTextReceived, MsgStyle.ERROR))
raise JrnlException(Message(MsgText.NoTextReceived, MsgStyle.NORMAL))
logging.debug(
'Write mode: appending raw text to journal "%s": %s', args.journal_name, raw
@ -342,6 +341,9 @@ def _print_edited_summary(journal, old_stats, **kwargs):
)
msgs.append(Message(my_msg, MsgStyle.NORMAL, {"num": stats["modified"]}))
if not msgs:
msgs.append(Message(MsgText.NoEditsReceived, MsgStyle.NORMAL))
print_msgs(msgs)

View file

@ -1,11 +1,11 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
from typing import NamedTuple
from typing import Mapping
from typing import NamedTuple
from .MsgText import MsgText
from .MsgStyle import MsgStyle
from jrnl.messages.MsgStyle import MsgStyle
from jrnl.messages.MsgText import MsgText
class Message(NamedTuple):

View file

@ -2,12 +2,13 @@
# License: https://www.gnu.org/licenses/gpl-3.0.html
from enum import Enum
from typing import NamedTuple
from typing import Callable
from rich.panel import Panel
from rich import box
from typing import NamedTuple
from .MsgText import MsgText
from rich import box
from rich.panel import Panel
from jrnl.messages.MsgText import MsgText
class MsgStyle(Enum):

View file

@ -149,6 +149,8 @@ class MsgText(Enum):
https://jrnl.sh/en/stable/external-editors/
"""
NoEditsReceived = "No edits to save, because nothing was changed"
NoTextReceived = """
No entry to save, because no text was received
"""
@ -196,6 +198,13 @@ class MsgText(Enum):
Configuration updated to newest version at {config_path}
"""
ConfigDoubleKeys = """
There is at least one duplicate key in your configuration file.
Details:
{error_message}
"""
# --- Password --- #
Password = "Password:"
PasswordFirstEntry = "Enter password for journal '{journal_name}': "

View file

@ -1,9 +1,9 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
from .Message import Message
from .MsgStyle import MsgStyle
from .MsgText import MsgText
from jrnl.messages.Message import Message
from jrnl.messages.MsgStyle import MsgStyle
from jrnl.messages.MsgText import MsgText
Message = Message
MsgStyle = MsgStyle

View file

@ -2,10 +2,10 @@
# License: https://www.gnu.org/licenses/gpl-3.0.html
import textwrap
from typing import Union
from rich.text import Text
from rich.console import Console
from rich.text import Text
from jrnl.messages import Message
from jrnl.messages import MsgStyle
@ -26,7 +26,7 @@ def deprecated_cmd(old_cmd, new_cmd, callback=None, **kwargs):
def list_journals(configuration):
from . import config
from jrnl import config
"""List the journals specified in the configuration file"""
result = f"Journals defined in config ({config.get_config_path()})\n"
@ -89,5 +89,9 @@ def _add_extra_style_args_if_needed(args, msg):
def format_msg_text(msg: Message) -> Text:
text = textwrap.dedent(msg.text.value.format(**msg.params)).strip()
text = textwrap.dedent(msg.text.value)
text = text.format(**msg.params)
# dedent again in case inserted text needs it
text = textwrap.dedent(text)
text = text.strip()
return Text(text)

View file

@ -1,9 +1,12 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
from .config import update_config, make_yaml_valid_dict
from argparse import Namespace
from jrnl.config import make_yaml_valid_dict
from jrnl.config import update_config
# import logging
def apply_overrides(args: Namespace, base_config: dict) -> dict:
"""Unpack CLI provided overrides into the configuration tree.

View file

@ -1,15 +1,15 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
from .fancy_exporter import FancyExporter
from .jrnl_importer import JRNLImporter
from .json_exporter import JSONExporter
from .markdown_exporter import MarkdownExporter
from .tag_exporter import TagExporter
from .dates_exporter import DatesExporter
from .text_exporter import TextExporter
from .xml_exporter import XMLExporter
from .yaml_exporter import YAMLExporter
from jrnl.plugins.dates_exporter import DatesExporter
from jrnl.plugins.fancy_exporter import FancyExporter
from jrnl.plugins.jrnl_importer import JRNLImporter
from jrnl.plugins.json_exporter import JSONExporter
from jrnl.plugins.markdown_exporter import MarkdownExporter
from jrnl.plugins.tag_exporter import TagExporter
from jrnl.plugins.text_exporter import TextExporter
from jrnl.plugins.xml_exporter import XMLExporter
from jrnl.plugins.yaml_exporter import YAMLExporter
__exporters = [
JSONExporter,

View file

@ -3,7 +3,7 @@
from collections import Counter
from .text_exporter import TextExporter
from jrnl.plugins.text_exporter import TextExporter
class DatesExporter(TextExporter):

View file

@ -1,13 +1,13 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
from jrnl.exception import JrnlException
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from textwrap import TextWrapper
from .text_exporter import TextExporter
from jrnl.exception import JrnlException
from jrnl.messages import Message
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.plugins.text_exporter import TextExporter
class FancyExporter(TextExporter):

View file

@ -5,8 +5,8 @@ import sys
from jrnl.exception import JrnlException
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.output import print_msg

View file

@ -3,8 +3,8 @@
import json
from .text_exporter import TextExporter
from .util import get_tags_count
from jrnl.plugins.text_exporter import TextExporter
from jrnl.plugins.util import get_tags_count
class JSONExporter(TextExporter):

View file

@ -4,12 +4,11 @@
import os
import re
from .text_exporter import TextExporter
from jrnl.output import print_msg
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.output import print_msg
from jrnl.plugins.text_exporter import TextExporter
class MarkdownExporter(TextExporter):

View file

@ -1,8 +1,8 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
from .text_exporter import TextExporter
from .util import get_tags_count
from jrnl.plugins.text_exporter import TextExporter
from jrnl.plugins.util import get_tags_count
class TagExporter(TextExporter):

View file

@ -5,10 +5,10 @@ import os
import re
import unicodedata
from jrnl.output import print_msg
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.output import print_msg
class TextExporter:

View file

@ -3,8 +3,8 @@
from xml.dom import minidom
from .json_exporter import JSONExporter
from .util import get_tags_count
from jrnl.plugins.json_exporter import JSONExporter
from jrnl.plugins.util import get_tags_count
class XMLExporter(JSONExporter):

View file

@ -4,13 +4,12 @@
import os
import re
from .text_exporter import TextExporter
from jrnl.exception import JrnlException
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.output import print_msg
from jrnl.plugins.text_exporter import TextExporter
class YAMLExporter(TextExporter):

View file

@ -2,8 +2,8 @@
# License: https://www.gnu.org/licenses/gpl-3.0.html
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.output import print_msg
from jrnl.output import print_msgs
@ -35,7 +35,7 @@ def create_password(journal_name: str) -> str:
print_msg(Message(MsgText.PasswordDidNotMatch, MsgStyle.ERROR))
if yesno(Message(MsgText.PasswordStoreInKeychain), default=True):
from .EncryptedJournal import set_keychain
from jrnl.EncryptedJournal import set_keychain
set_keychain(journal_name, pw)

View file

@ -3,21 +3,20 @@
import os
from . import Journal
from . import __version__
from .EncryptedJournal import EncryptedJournal
from .config import is_config_json
from .config import load_config
from .config import scope_config
from .prompt import yesno
from .path import expand_path
from jrnl.output import print_msg
from jrnl.output import print_msgs
from jrnl import Journal
from jrnl import __version__
from jrnl.config import is_config_json
from jrnl.config import load_config
from jrnl.config import scope_config
from jrnl.EncryptedJournal import EncryptedJournal
from jrnl.exception import JrnlException
from jrnl.messages import Message
from jrnl.messages import MsgText
from jrnl.messages import MsgStyle
from jrnl.messages import MsgText
from jrnl.output import print_msg
from jrnl.output import print_msgs
from jrnl.path import expand_path
from jrnl.prompt import yesno
def backup(filename, binary=False):

254
poetry.lock generated
View file

@ -44,7 +44,7 @@ test = ["astroid", "pytest"]
[[package]]
name = "atomicwrites"
version = "1.4.0"
version = "1.4.1"
description = "Atomic file writes."
category = "dev"
optional = false
@ -74,7 +74,7 @@ python-versions = "*"
[[package]]
name = "black"
version = "22.3.0"
version = "22.6.0"
description = "The uncompromising code formatter."
category = "dev"
optional = false
@ -85,7 +85,7 @@ click = ">=8.0.0"
mypy-extensions = ">=0.4.3"
pathspec = ">=0.9.0"
platformdirs = ">=2"
tomli = {version = ">=1.1.0", markers = "python_version < \"3.11\""}
tomli = {version = ">=1.1.0", markers = "python_full_version < \"3.11.0a7\""}
typing-extensions = {version = ">=3.10.0.0", markers = "python_version < \"3.10\""}
[package.extras]
@ -96,7 +96,7 @@ uvloop = ["uvloop (>=0.15.2)"]
[[package]]
name = "cffi"
version = "1.15.0"
version = "1.15.1"
description = "Foreign Function Interface for Python calling C code."
category = "main"
optional = false
@ -137,7 +137,7 @@ test = ["flake8 (==3.7.8)", "hypothesis (==3.55.3)"]
[[package]]
name = "cryptography"
version = "37.0.2"
version = "37.0.4"
description = "cryptography is a package which provides cryptographic recipes and primitives to Python developers."
category = "main"
optional = false
@ -170,6 +170,17 @@ category = "dev"
optional = false
python-versions = "*"
[[package]]
name = "execnet"
version = "1.9.0"
description = "execnet: rapid multi-Python deployment"
category = "dev"
optional = false
python-versions = ">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*, !=3.4.*"
[package.extras]
testing = ["pre-commit"]
[[package]]
name = "executing"
version = "0.8.3"
@ -227,7 +238,7 @@ python-versions = "*"
[[package]]
name = "importlib-metadata"
version = "4.11.4"
version = "4.12.0"
description = "Read metadata from Python packages"
category = "main"
optional = false
@ -239,7 +250,7 @@ zipp = ">=0.5"
[package.extras]
docs = ["sphinx", "jaraco.packaging (>=9)", "rst.linker (>=1.9)"]
perf = ["ipython"]
testing = ["pytest (>=6)", "pytest-checkdocs (>=2.4)", "pytest-flake8", "pytest-cov", "pytest-enabler (>=1.0.1)", "packaging", "pyfakefs", "flufl.flake8", "pytest-perf (>=0.9.2)", "pytest-black (>=0.3.7)", "pytest-mypy (>=0.9.1)", "importlib-resources (>=1.3)"]
testing = ["pytest (>=6)", "pytest-checkdocs (>=2.4)", "pytest-flake8", "pytest-cov", "pytest-enabler (>=1.3)", "packaging", "pyfakefs", "flufl.flake8", "pytest-perf (>=0.9.2)", "pytest-black (>=0.3.7)", "pytest-mypy (>=0.9.1)", "importlib-resources (>=1.3)"]
[[package]]
name = "iniconfig"
@ -297,6 +308,20 @@ qtconsole = ["qtconsole"]
test = ["pytest (<7.1)", "pytest-asyncio", "testpath"]
test_extra = ["pytest (<7.1)", "pytest-asyncio", "testpath", "curio", "matplotlib (!=3.2.0)", "nbformat", "numpy (>=1.19)", "pandas", "trio"]
[[package]]
name = "isort"
version = "5.10.1"
description = "A Python utility / library to sort Python imports."
category = "dev"
optional = false
python-versions = ">=3.6.1,<4.0"
[package.extras]
pipfile_deprecated_finder = ["pipreqs", "requirementslib"]
requirements_deprecated_finder = ["pipreqs", "pip-api"]
colors = ["colorama (>=0.4.3,<0.5.0)"]
plugins = ["setuptools"]
[[package]]
name = "jedi"
version = "0.18.1"
@ -358,7 +383,7 @@ testing = ["pytest (>=6)", "pytest-checkdocs (>=2.4)", "pytest-flake8", "pytest-
[[package]]
name = "mako"
version = "1.2.0"
version = "1.2.1"
description = "A super-fast templating language that borrows the best ideas from the existing templating languages."
category = "dev"
optional = false
@ -568,11 +593,11 @@ testing = ["pytest", "pytest-benchmark"]
[[package]]
name = "poethepoet"
version = "0.13.1"
version = "0.15.0"
description = "A task runner that works well with poetry."
category = "dev"
optional = false
python-versions = ">=3.6.2"
python-versions = ">=3.7"
[package.dependencies]
pastel = ">=0.2.1,<0.3.0"
@ -591,7 +616,7 @@ python-versions = "*"
[[package]]
name = "prompt-toolkit"
version = "3.0.29"
version = "3.0.30"
description = "Library for building powerful interactive command lines in Python"
category = "dev"
optional = false
@ -732,6 +757,36 @@ pprintpp = ">=0.4.0"
pytest = ">=3.5.0"
rich = ">=8.0.0"
[[package]]
name = "pytest-forked"
version = "1.4.0"
description = "run tests in isolated forked subprocesses"
category = "dev"
optional = false
python-versions = ">=3.6"
[package.dependencies]
py = "*"
pytest = ">=3.10"
[[package]]
name = "pytest-xdist"
version = "2.5.0"
description = "pytest xdist plugin for distributed testing and loop-on-failing modes"
category = "dev"
optional = false
python-versions = ">=3.6"
[package.dependencies]
execnet = ">=1.1"
pytest = ">=6.2.0"
pytest-forked = "*"
[package.extras]
psutil = ["psutil (>=3.0)"]
setproctitle = ["setproctitle"]
testing = ["filelock"]
[[package]]
name = "python-dateutil"
version = "2.8.2"
@ -886,7 +941,7 @@ python-versions = ">=3.7"
[[package]]
name = "tox"
version = "3.25.0"
version = "3.25.1"
description = "tox is a generic virtualenv management and test command line tool"
category = "dev"
optional = false
@ -919,7 +974,7 @@ test = ["pre-commit", "pytest"]
[[package]]
name = "typing-extensions"
version = "4.2.0"
version = "4.3.0"
description = "Backported and Experimental Type Hints for Python 3.7+"
category = "dev"
optional = false
@ -938,7 +993,7 @@ pytz = "*"
[[package]]
name = "virtualenv"
version = "20.14.1"
version = "20.15.1"
description = "Virtual Python Environment builder"
category = "dev"
optional = false
@ -983,7 +1038,7 @@ python-versions = ">=3.4"
[[package]]
name = "yq"
version = "2.14.0"
version = "3.0.2"
description = "Command-line YAML/XML processor - jq wrapper for YAML/XML documents"
category = "dev"
optional = false
@ -1010,13 +1065,10 @@ python-versions = ">=3.7"
docs = ["sphinx", "jaraco.packaging (>=9)", "rst.linker (>=1.9)"]
testing = ["pytest (>=6)", "pytest-checkdocs (>=2.4)", "pytest-flake8", "pytest-cov", "pytest-enabler (>=1.0.1)", "jaraco.itertools", "func-timeout", "pytest-black (>=0.3.7)", "pytest-mypy (>=0.9.1)"]
[extras]
testing = []
[metadata]
lock-version = "1.1"
python-versions = ">=3.9.0, <3.12"
content-hash = "ceca9186ac31a0b8ec81a6cc134469842080c786971bb8642d9e67d51bd73fca"
content-hash = "647a60d3f5c77ae365e4acef948b048a112eebd0315e026ffe31a0cc441c6601"
[metadata.files]
ansiwrap = [
@ -1035,10 +1087,7 @@ asttokens = [
{file = "asttokens-2.0.5-py2.py3-none-any.whl", hash = "sha256:0844691e88552595a6f4a4281a9f7f79b8dd45ca4ccea82e5e05b4bbdb76705c"},
{file = "asttokens-2.0.5.tar.gz", hash = "sha256:9a54c114f02c7a9480d56550932546a3f1fe71d8a02f1bc7ccd0ee3ee35cf4d5"},
]
atomicwrites = [
{file = "atomicwrites-1.4.0-py2.py3-none-any.whl", hash = "sha256:6d1784dea7c0c8d4a5172b6c620f40b6e4cbfdf96d783691f2e1302a7b88e197"},
{file = "atomicwrites-1.4.0.tar.gz", hash = "sha256:ae70396ad1a434f9c7046fd2dd196fc04b12f9e91ffb859164193be8b6168a7a"},
]
atomicwrites = []
attrs = [
{file = "attrs-21.4.0-py2.py3-none-any.whl", hash = "sha256:2d27e3784d7a565d36ab851fe94887c5eccd6a463168875832a1be79c82828b4"},
{file = "attrs-21.4.0.tar.gz", hash = "sha256:626ba8234211db98e869df76230a137c4c40a12d72445c45d5f5b716f076e2fd"},
@ -1047,83 +1096,8 @@ backcall = [
{file = "backcall-0.2.0-py2.py3-none-any.whl", hash = "sha256:fbbce6a29f263178a1f7915c1940bde0ec2b2a967566fe1c65c1dfb7422bd255"},
{file = "backcall-0.2.0.tar.gz", hash = "sha256:5cbdbf27be5e7cfadb448baf0aa95508f91f2bbc6c6437cd9cd06e2a4c215e1e"},
]
black = [
{file = "black-22.3.0-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:2497f9c2386572e28921fa8bec7be3e51de6801f7459dffd6e62492531c47e09"},
{file = "black-22.3.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:5795a0375eb87bfe902e80e0c8cfaedf8af4d49694d69161e5bd3206c18618bb"},
{file = "black-22.3.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:e3556168e2e5c49629f7b0f377070240bd5511e45e25a4497bb0073d9dda776a"},
{file = "black-22.3.0-cp310-cp310-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:67c8301ec94e3bcc8906740fe071391bce40a862b7be0b86fb5382beefecd968"},
{file = "black-22.3.0-cp310-cp310-win_amd64.whl", hash = "sha256:fd57160949179ec517d32ac2ac898b5f20d68ed1a9c977346efbac9c2f1e779d"},
{file = "black-22.3.0-cp36-cp36m-macosx_10_9_x86_64.whl", hash = "sha256:cc1e1de68c8e5444e8f94c3670bb48a2beef0e91dddfd4fcc29595ebd90bb9ce"},
{file = "black-22.3.0-cp36-cp36m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6d2fc92002d44746d3e7db7cf9313cf4452f43e9ea77a2c939defce3b10b5c82"},
{file = "black-22.3.0-cp36-cp36m-win_amd64.whl", hash = "sha256:a6342964b43a99dbc72f72812bf88cad8f0217ae9acb47c0d4f141a6416d2d7b"},
{file = "black-22.3.0-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:328efc0cc70ccb23429d6be184a15ce613f676bdfc85e5fe8ea2a9354b4e9015"},
{file = "black-22.3.0-cp37-cp37m-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:06f9d8846f2340dfac80ceb20200ea5d1b3f181dd0556b47af4e8e0b24fa0a6b"},
{file = "black-22.3.0-cp37-cp37m-win_amd64.whl", hash = "sha256:ad4efa5fad66b903b4a5f96d91461d90b9507a812b3c5de657d544215bb7877a"},
{file = "black-22.3.0-cp38-cp38-macosx_10_9_universal2.whl", hash = "sha256:e8477ec6bbfe0312c128e74644ac8a02ca06bcdb8982d4ee06f209be28cdf163"},
{file = "black-22.3.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:637a4014c63fbf42a692d22b55d8ad6968a946b4a6ebc385c5505d9625b6a464"},
{file = "black-22.3.0-cp38-cp38-macosx_11_0_arm64.whl", hash = "sha256:863714200ada56cbc366dc9ae5291ceb936573155f8bf8e9de92aef51f3ad0f0"},
{file = "black-22.3.0-cp38-cp38-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:10dbe6e6d2988049b4655b2b739f98785a884d4d6b85bc35133a8fb9a2233176"},
{file = "black-22.3.0-cp38-cp38-win_amd64.whl", hash = "sha256:cee3e11161dde1b2a33a904b850b0899e0424cc331b7295f2a9698e79f9a69a0"},
{file = "black-22.3.0-cp39-cp39-macosx_10_9_universal2.whl", hash = "sha256:5891ef8abc06576985de8fa88e95ab70641de6c1fca97e2a15820a9b69e51b20"},
{file = "black-22.3.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:30d78ba6bf080eeaf0b7b875d924b15cd46fec5fd044ddfbad38c8ea9171043a"},
{file = "black-22.3.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:ee8f1f7228cce7dffc2b464f07ce769f478968bfb3dd1254a4c2eeed84928aad"},
{file = "black-22.3.0-cp39-cp39-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:6ee227b696ca60dd1c507be80a6bc849a5a6ab57ac7352aad1ffec9e8b805f21"},
{file = "black-22.3.0-cp39-cp39-win_amd64.whl", hash = "sha256:9b542ced1ec0ceeff5b37d69838106a6348e60db7b8fdd245294dc1d26136265"},
{file = "black-22.3.0-py3-none-any.whl", hash = "sha256:bc58025940a896d7e5356952228b68f793cf5fcb342be703c3a2669a1488cb72"},
{file = "black-22.3.0.tar.gz", hash = "sha256:35020b8886c022ced9282b51b5a875b6d1ab0c387b31a065b84db7c33085ca79"},
]
cffi = [
{file = "cffi-1.15.0-cp27-cp27m-macosx_10_9_x86_64.whl", hash = "sha256:c2502a1a03b6312837279c8c1bd3ebedf6c12c4228ddbad40912d671ccc8a962"},
{file = "cffi-1.15.0-cp27-cp27m-manylinux1_i686.whl", hash = "sha256:23cfe892bd5dd8941608f93348c0737e369e51c100d03718f108bf1add7bd6d0"},
{file = "cffi-1.15.0-cp27-cp27m-manylinux1_x86_64.whl", hash = "sha256:41d45de54cd277a7878919867c0f08b0cf817605e4eb94093e7516505d3c8d14"},
{file = "cffi-1.15.0-cp27-cp27m-win32.whl", hash = "sha256:4a306fa632e8f0928956a41fa8e1d6243c71e7eb59ffbd165fc0b41e316b2474"},
{file = "cffi-1.15.0-cp27-cp27m-win_amd64.whl", hash = "sha256:e7022a66d9b55e93e1a845d8c9eba2a1bebd4966cd8bfc25d9cd07d515b33fa6"},
{file = "cffi-1.15.0-cp27-cp27mu-manylinux1_i686.whl", hash = "sha256:14cd121ea63ecdae71efa69c15c5543a4b5fbcd0bbe2aad864baca0063cecf27"},
{file = "cffi-1.15.0-cp27-cp27mu-manylinux1_x86_64.whl", hash = "sha256:d4d692a89c5cf08a8557fdeb329b82e7bf609aadfaed6c0d79f5a449a3c7c023"},
{file = "cffi-1.15.0-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:0104fb5ae2391d46a4cb082abdd5c69ea4eab79d8d44eaaf79f1b1fd806ee4c2"},
{file = "cffi-1.15.0-cp310-cp310-macosx_11_0_arm64.whl", hash = "sha256:91ec59c33514b7c7559a6acda53bbfe1b283949c34fe7440bcf917f96ac0723e"},
{file = "cffi-1.15.0-cp310-cp310-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:f5c7150ad32ba43a07c4479f40241756145a1f03b43480e058cfd862bf5041c7"},
{file = "cffi-1.15.0-cp310-cp310-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:00c878c90cb53ccfaae6b8bc18ad05d2036553e6d9d1d9dbcf323bbe83854ca3"},
{file = "cffi-1.15.0-cp310-cp310-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:abb9a20a72ac4e0fdb50dae135ba5e77880518e742077ced47eb1499e29a443c"},
{file = "cffi-1.15.0-cp310-cp310-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:a5263e363c27b653a90078143adb3d076c1a748ec9ecc78ea2fb916f9b861962"},
{file = "cffi-1.15.0-cp310-cp310-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:f54a64f8b0c8ff0b64d18aa76675262e1700f3995182267998c31ae974fbc382"},
{file = "cffi-1.15.0-cp310-cp310-win32.whl", hash = "sha256:c21c9e3896c23007803a875460fb786118f0cdd4434359577ea25eb556e34c55"},
{file = "cffi-1.15.0-cp310-cp310-win_amd64.whl", hash = "sha256:5e069f72d497312b24fcc02073d70cb989045d1c91cbd53979366077959933e0"},
{file = "cffi-1.15.0-cp36-cp36m-macosx_10_9_x86_64.whl", hash = "sha256:64d4ec9f448dfe041705426000cc13e34e6e5bb13736e9fd62e34a0b0c41566e"},
{file = "cffi-1.15.0-cp36-cp36m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:2756c88cbb94231c7a147402476be2c4df2f6078099a6f4a480d239a8817ae39"},
{file = "cffi-1.15.0-cp36-cp36m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3b96a311ac60a3f6be21d2572e46ce67f09abcf4d09344c49274eb9e0bf345fc"},
{file = "cffi-1.15.0-cp36-cp36m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:75e4024375654472cc27e91cbe9eaa08567f7fbdf822638be2814ce059f58032"},
{file = "cffi-1.15.0-cp36-cp36m-manylinux_2_5_i686.manylinux1_i686.whl", hash = "sha256:59888172256cac5629e60e72e86598027aca6bf01fa2465bdb676d37636573e8"},
{file = "cffi-1.15.0-cp36-cp36m-manylinux_2_5_x86_64.manylinux1_x86_64.whl", hash = "sha256:27c219baf94952ae9d50ec19651a687b826792055353d07648a5695413e0c605"},
{file = "cffi-1.15.0-cp36-cp36m-win32.whl", hash = "sha256:4958391dbd6249d7ad855b9ca88fae690783a6be9e86df65865058ed81fc860e"},
{file = "cffi-1.15.0-cp36-cp36m-win_amd64.whl", hash = "sha256:f6f824dc3bce0edab5f427efcfb1d63ee75b6fcb7282900ccaf925be84efb0fc"},
{file = "cffi-1.15.0-cp37-cp37m-macosx_10_9_x86_64.whl", hash = "sha256:06c48159c1abed75c2e721b1715c379fa3200c7784271b3c46df01383b593636"},
{file = "cffi-1.15.0-cp37-cp37m-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:c2051981a968d7de9dd2d7b87bcb9c939c74a34626a6e2f8181455dd49ed69e4"},
{file = "cffi-1.15.0-cp37-cp37m-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:fd8a250edc26254fe5b33be00402e6d287f562b6a5b2152dec302fa15bb3e997"},
{file = "cffi-1.15.0-cp37-cp37m-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:91d77d2a782be4274da750752bb1650a97bfd8f291022b379bb8e01c66b4e96b"},
{file = "cffi-1.15.0-cp37-cp37m-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:45db3a33139e9c8f7c09234b5784a5e33d31fd6907800b316decad50af323ff2"},
{file = "cffi-1.15.0-cp37-cp37m-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:263cc3d821c4ab2213cbe8cd8b355a7f72a8324577dc865ef98487c1aeee2bc7"},
{file = "cffi-1.15.0-cp37-cp37m-win32.whl", hash = "sha256:17771976e82e9f94976180f76468546834d22a7cc404b17c22df2a2c81db0c66"},
{file = "cffi-1.15.0-cp37-cp37m-win_amd64.whl", hash = "sha256:3415c89f9204ee60cd09b235810be700e993e343a408693e80ce7f6a40108029"},
{file = "cffi-1.15.0-cp38-cp38-macosx_10_9_x86_64.whl", hash = "sha256:4238e6dab5d6a8ba812de994bbb0a79bddbdf80994e4ce802b6f6f3142fcc880"},
{file = "cffi-1.15.0-cp38-cp38-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:0808014eb713677ec1292301ea4c81ad277b6cdf2fdd90fd540af98c0b101d20"},
{file = "cffi-1.15.0-cp38-cp38-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:57e9ac9ccc3101fac9d6014fba037473e4358ef4e89f8e181f8951a2c0162024"},
{file = "cffi-1.15.0-cp38-cp38-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:8b6c2ea03845c9f501ed1313e78de148cd3f6cad741a75d43a29b43da27f2e1e"},
{file = "cffi-1.15.0-cp38-cp38-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:10dffb601ccfb65262a27233ac273d552ddc4d8ae1bf93b21c94b8511bffe728"},
{file = "cffi-1.15.0-cp38-cp38-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:786902fb9ba7433aae840e0ed609f45c7bcd4e225ebb9c753aa39725bb3e6ad6"},
{file = "cffi-1.15.0-cp38-cp38-win32.whl", hash = "sha256:da5db4e883f1ce37f55c667e5c0de439df76ac4cb55964655906306918e7363c"},
{file = "cffi-1.15.0-cp38-cp38-win_amd64.whl", hash = "sha256:181dee03b1170ff1969489acf1c26533710231c58f95534e3edac87fff06c443"},
{file = "cffi-1.15.0-cp39-cp39-macosx_10_9_x86_64.whl", hash = "sha256:45e8636704eacc432a206ac7345a5d3d2c62d95a507ec70d62f23cd91770482a"},
{file = "cffi-1.15.0-cp39-cp39-macosx_11_0_arm64.whl", hash = "sha256:31fb708d9d7c3f49a60f04cf5b119aeefe5644daba1cd2a0fe389b674fd1de37"},
{file = "cffi-1.15.0-cp39-cp39-manylinux_2_12_i686.manylinux2010_i686.whl", hash = "sha256:6dc2737a3674b3e344847c8686cf29e500584ccad76204efea14f451d4cc669a"},
{file = "cffi-1.15.0-cp39-cp39-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:74fdfdbfdc48d3f47148976f49fab3251e550a8720bebc99bf1483f5bfb5db3e"},
{file = "cffi-1.15.0-cp39-cp39-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:ffaa5c925128e29efbde7301d8ecaf35c8c60ffbcd6a1ffd3a552177c8e5e796"},
{file = "cffi-1.15.0-cp39-cp39-manylinux_2_17_ppc64le.manylinux2014_ppc64le.whl", hash = "sha256:3f7d084648d77af029acb79a0ff49a0ad7e9d09057a9bf46596dac9514dc07df"},
{file = "cffi-1.15.0-cp39-cp39-manylinux_2_17_s390x.manylinux2014_s390x.whl", hash = "sha256:ef1f279350da2c586a69d32fc8733092fd32cc8ac95139a00377841f59a3f8d8"},
{file = "cffi-1.15.0-cp39-cp39-win32.whl", hash = "sha256:2a23af14f408d53d5e6cd4e3d9a24ff9e05906ad574822a10563efcef137979a"},
{file = "cffi-1.15.0-cp39-cp39-win_amd64.whl", hash = "sha256:3773c4d81e6e818df2efbc7dd77325ca0dcb688116050fb2b3011218eda36139"},
{file = "cffi-1.15.0.tar.gz", hash = "sha256:920f0d66a896c2d99f0adbb391f990a84091179542c205fa53ce5787aff87954"},
]
black = []
cffi = []
click = [
{file = "click-8.1.3-py3-none-any.whl", hash = "sha256:bb4d8133cb15a609f44e8213d9b391b0809795062913b383c62be0ee95b1db48"},
{file = "click-8.1.3.tar.gz", hash = "sha256:7682dc8afb30297001674575ea00d1814d808d6a36af415a82bd481d37ba7b8e"},
@ -1136,30 +1110,7 @@ commonmark = [
{file = "commonmark-0.9.1-py2.py3-none-any.whl", hash = "sha256:da2f38c92590f83de410ba1a3cbceafbc74fee9def35f9251ba9a971d6d66fd9"},
{file = "commonmark-0.9.1.tar.gz", hash = "sha256:452f9dc859be7f06631ddcb328b6919c67984aca654e5fefb3914d54691aed60"},
]
cryptography = [
{file = "cryptography-37.0.2-cp36-abi3-macosx_10_10_universal2.whl", hash = "sha256:ef15c2df7656763b4ff20a9bc4381d8352e6640cfeb95c2972c38ef508e75181"},
{file = "cryptography-37.0.2-cp36-abi3-macosx_10_10_x86_64.whl", hash = "sha256:3c81599befb4d4f3d7648ed3217e00d21a9341a9a688ecdd615ff72ffbed7336"},
{file = "cryptography-37.0.2-cp36-abi3-manylinux_2_12_x86_64.manylinux2010_x86_64.whl", hash = "sha256:2bd1096476aaac820426239ab534b636c77d71af66c547b9ddcd76eb9c79e004"},
{file = "cryptography-37.0.2-cp36-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.manylinux_2_24_aarch64.whl", hash = "sha256:31fe38d14d2e5f787e0aecef831457da6cec68e0bb09a35835b0b44ae8b988fe"},
{file = "cryptography-37.0.2-cp36-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl", hash = "sha256:093cb351031656d3ee2f4fa1be579a8c69c754cf874206be1d4cf3b542042804"},
{file = "cryptography-37.0.2-cp36-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:59b281eab51e1b6b6afa525af2bd93c16d49358404f814fe2c2410058623928c"},
{file = "cryptography-37.0.2-cp36-abi3-manylinux_2_24_x86_64.whl", hash = "sha256:0cc20f655157d4cfc7bada909dc5cc228211b075ba8407c46467f63597c78178"},
{file = "cryptography-37.0.2-cp36-abi3-musllinux_1_1_aarch64.whl", hash = "sha256:f8ec91983e638a9bcd75b39f1396e5c0dc2330cbd9ce4accefe68717e6779e0a"},
{file = "cryptography-37.0.2-cp36-abi3-musllinux_1_1_x86_64.whl", hash = "sha256:46f4c544f6557a2fefa7ac8ac7d1b17bf9b647bd20b16decc8fbcab7117fbc15"},
{file = "cryptography-37.0.2-cp36-abi3-win32.whl", hash = "sha256:731c8abd27693323b348518ed0e0705713a36d79fdbd969ad968fbef0979a7e0"},
{file = "cryptography-37.0.2-cp36-abi3-win_amd64.whl", hash = "sha256:471e0d70201c069f74c837983189949aa0d24bb2d751b57e26e3761f2f782b8d"},
{file = "cryptography-37.0.2-pp37-pypy37_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:a68254dd88021f24a68b613d8c51d5c5e74d735878b9e32cc0adf19d1f10aaf9"},
{file = "cryptography-37.0.2-pp37-pypy37_pp73-manylinux_2_24_x86_64.whl", hash = "sha256:a7d5137e556cc0ea418dca6186deabe9129cee318618eb1ffecbd35bee55ddc1"},
{file = "cryptography-37.0.2-pp38-pypy38_pp73-macosx_10_10_x86_64.whl", hash = "sha256:aeaba7b5e756ea52c8861c133c596afe93dd716cbcacae23b80bc238202dc023"},
{file = "cryptography-37.0.2-pp38-pypy38_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:95e590dd70642eb2079d280420a888190aa040ad20f19ec8c6e097e38aa29e06"},
{file = "cryptography-37.0.2-pp38-pypy38_pp73-manylinux_2_24_x86_64.whl", hash = "sha256:1b9362d34363f2c71b7853f6251219298124aa4cc2075ae2932e64c91a3e2717"},
{file = "cryptography-37.0.2-pp38-pypy38_pp73-win_amd64.whl", hash = "sha256:e53258e69874a306fcecb88b7534d61820db8a98655662a3dd2ec7f1afd9132f"},
{file = "cryptography-37.0.2-pp39-pypy39_pp73-macosx_10_10_x86_64.whl", hash = "sha256:1f3bfbd611db5cb58ca82f3deb35e83af34bb8cf06043fa61500157d50a70982"},
{file = "cryptography-37.0.2-pp39-pypy39_pp73-manylinux_2_17_x86_64.manylinux2014_x86_64.whl", hash = "sha256:419c57d7b63f5ec38b1199a9521d77d7d1754eb97827bbb773162073ccd8c8d4"},
{file = "cryptography-37.0.2-pp39-pypy39_pp73-manylinux_2_24_x86_64.whl", hash = "sha256:dc26bb134452081859aa21d4990474ddb7e863aa39e60d1592800a8865a702de"},
{file = "cryptography-37.0.2-pp39-pypy39_pp73-win_amd64.whl", hash = "sha256:3b8398b3d0efc420e777c40c16764d6870bcef2eb383df9c6dbb9ffe12c64452"},
{file = "cryptography-37.0.2.tar.gz", hash = "sha256:f224ad253cc9cea7568f49077007d2263efa57396a2f2f78114066fd54b5c68e"},
]
cryptography = []
decorator = [
{file = "decorator-5.1.1-py3-none-any.whl", hash = "sha256:b8c3f85900b9dc423225913c5aace94729fe1fa9763b38939a95226f02d37186"},
{file = "decorator-5.1.1.tar.gz", hash = "sha256:637996211036b6385ef91435e4fae22989472f9d571faba8927ba8253acbc330"},
@ -1168,6 +1119,10 @@ distlib = [
{file = "distlib-0.3.4-py2.py3-none-any.whl", hash = "sha256:6564fe0a8f51e734df6333d08b8b94d4ea8ee6b99b5ed50613f731fd4089f34b"},
{file = "distlib-0.3.4.zip", hash = "sha256:e4b58818180336dc9c529bfb9a0b58728ffc09ad92027a3f30b7cd91e3458579"},
]
execnet = [
{file = "execnet-1.9.0-py2.py3-none-any.whl", hash = "sha256:a295f7cc774947aac58dde7fdc85f4aa00c42adf5d8f5468fc630c1acf30a142"},
{file = "execnet-1.9.0.tar.gz", hash = "sha256:8f694f3ba9cc92cab508b152dcfe322153975c29bda272e2fd7f3f00f36e47c5"},
]
executing = [
{file = "executing-0.8.3-py2.py3-none-any.whl", hash = "sha256:d1eef132db1b83649a3905ca6dd8897f71ac6f8cac79a7e58a1a09cf137546c9"},
{file = "executing-0.8.3.tar.gz", hash = "sha256:c6554e21c6b060590a6d3be4b82fb78f8f0194d809de5ea7df1c093763311501"},
@ -1188,8 +1143,8 @@ glob2 = [
{file = "glob2-0.7.tar.gz", hash = "sha256:85c3dbd07c8aa26d63d7aacee34fa86e9a91a3873bc30bf62ec46e531f92ab8c"},
]
importlib-metadata = [
{file = "importlib_metadata-4.11.4-py3-none-any.whl", hash = "sha256:c58c8eb8a762858f49e18436ff552e83914778e50e9d2f1660535ffb364552ec"},
{file = "importlib_metadata-4.11.4.tar.gz", hash = "sha256:5d26852efe48c0a32b0509ffbc583fda1a2266545a78d104a6f4aff3db17d700"},
{file = "importlib_metadata-4.12.0-py3-none-any.whl", hash = "sha256:7401a975809ea1fdc658c3aa4f78cc2195a0e019c5cbc4c06122884e9ae80c23"},
{file = "importlib_metadata-4.12.0.tar.gz", hash = "sha256:637245b8bab2b6502fcbc752cc4b7a6f6243bb02b31c5c26156ad103d3d45670"},
]
iniconfig = [
{file = "iniconfig-1.1.1-py2.py3-none-any.whl", hash = "sha256:011e24c64b7f47f6ebd835bb12a743f2fbe9a26d4cecaa7f53bc4f35ee9da8b3"},
@ -1202,6 +1157,10 @@ ipython = [
{file = "ipython-8.4.0-py3-none-any.whl", hash = "sha256:7ca74052a38fa25fe9bedf52da0be7d3fdd2fb027c3b778ea78dfe8c212937d1"},
{file = "ipython-8.4.0.tar.gz", hash = "sha256:f2db3a10254241d9b447232cec8b424847f338d9d36f9a577a6192c332a46abd"},
]
isort = [
{file = "isort-5.10.1-py3-none-any.whl", hash = "sha256:6f62d78e2f89b4500b080fe3a81690850cd254227f27f75c3a0c491a1f351ba7"},
{file = "isort-5.10.1.tar.gz", hash = "sha256:e8443a5e7a020e9d7f97f1d7d9cd17c88bcb3bc7e218bf9cf5095fe550be2951"},
]
jedi = [
{file = "jedi-0.18.1-py2.py3-none-any.whl", hash = "sha256:637c9635fcf47945ceb91cd7f320234a7be540ded6f3e99a50cb6febdfd1ba8d"},
{file = "jedi-0.18.1.tar.gz", hash = "sha256:74137626a64a99c8eb6ae5832d99b3bdd7d29a3850fe2aa80a4126b2a7d949ab"},
@ -1218,10 +1177,7 @@ keyring = [
{file = "keyring-23.6.0-py3-none-any.whl", hash = "sha256:372ff2fc43ab779e3f87911c26e6c7acc8bb440cbd82683e383ca37594cb0617"},
{file = "keyring-23.6.0.tar.gz", hash = "sha256:3ac00c26e4c93739e19103091a9986a9f79665a78cf15a4df1dba7ea9ac8da2f"},
]
mako = [
{file = "Mako-1.2.0-py3-none-any.whl", hash = "sha256:23aab11fdbbb0f1051b93793a58323ff937e98e34aece1c4219675122e57e4ba"},
{file = "Mako-1.2.0.tar.gz", hash = "sha256:9a7c7e922b87db3686210cf49d5d767033a41d4010b284e747682c92bddd8b39"},
]
mako = []
markdown = [
{file = "Markdown-3.3.7-py3-none-any.whl", hash = "sha256:f5da449a6e1c989a4cea2631aa8ee67caa5a2ef855d551c88f9e309f4634c621"},
{file = "Markdown-3.3.7.tar.gz", hash = "sha256:cbb516f16218e643d8e0a95b309f77eb118cb138d39a4f27851e6a63581db874"},
@ -1331,18 +1287,12 @@ pluggy = [
{file = "pluggy-1.0.0-py2.py3-none-any.whl", hash = "sha256:74134bbf457f031a36d68416e1509f34bd5ccc019f0bcc952c7b909d06b37bd3"},
{file = "pluggy-1.0.0.tar.gz", hash = "sha256:4224373bacce55f955a878bf9cfa763c1e360858e330072059e10bad68531159"},
]
poethepoet = [
{file = "poethepoet-0.13.1-py3-none-any.whl", hash = "sha256:47e7b38c8b5412f840447f7612a9330697e8633e7500a7340b6734f50e26e380"},
{file = "poethepoet-0.13.1.tar.gz", hash = "sha256:4f6962f17f5d5a453fd7fa66e3e7897e9191d4289148433efe441c81f2451a46"},
]
poethepoet = []
pprintpp = [
{file = "pprintpp-0.4.0-py2.py3-none-any.whl", hash = "sha256:b6b4dcdd0c0c0d75e4d7b2f21a9e933e5b2ce62b26e1a54537f9651ae5a5c01d"},
{file = "pprintpp-0.4.0.tar.gz", hash = "sha256:ea826108e2c7f49dc6d66c752973c3fc9749142a798d6b254e1e301cfdbc6403"},
]
prompt-toolkit = [
{file = "prompt_toolkit-3.0.29-py3-none-any.whl", hash = "sha256:62291dad495e665fca0bda814e342c69952086afb0f4094d0893d357e5c78752"},
{file = "prompt_toolkit-3.0.29.tar.gz", hash = "sha256:bd640f60e8cecd74f0dc249713d433ace2ddc62b65ee07f96d358e0b152b6ea7"},
]
prompt-toolkit = []
ptyprocess = [
{file = "ptyprocess-0.7.0-py2.py3-none-any.whl", hash = "sha256:4b41f3967fce3af57cc7e94b888626c18bf37a083e3651ca8feeb66d492fef35"},
{file = "ptyprocess-0.7.0.tar.gz", hash = "sha256:5c5d0a3b48ceee0b48485e0c26037c0acd7d29765ca3fbb5cb3831d347423220"},
@ -1390,6 +1340,14 @@ pytest-bdd = [
pytest-clarity = [
{file = "pytest-clarity-1.0.1.tar.gz", hash = "sha256:505fe345fad4fe11c6a4187fe683f2c7c52c077caa1e135f3e483fe112db7772"},
]
pytest-forked = [
{file = "pytest-forked-1.4.0.tar.gz", hash = "sha256:8b67587c8f98cbbadfdd804539ed5455b6ed03802203485dd2f53c1422d7440e"},
{file = "pytest_forked-1.4.0-py3-none-any.whl", hash = "sha256:bbbb6717efc886b9d64537b41fb1497cfaf3c9601276be8da2cccfea5a3c8ad8"},
]
pytest-xdist = [
{file = "pytest-xdist-2.5.0.tar.gz", hash = "sha256:4580deca3ff04ddb2ac53eba39d76cb5dd5edeac050cb6fbc768b0dd712b4edf"},
{file = "pytest_xdist-2.5.0-py3-none-any.whl", hash = "sha256:6fe5c74fec98906deb8f2d2b616b5c782022744978e7bd4695d39c8f42d0ce65"},
]
python-dateutil = [
{file = "python-dateutil-2.8.2.tar.gz", hash = "sha256:0123cacc1627ae19ddf3c27a5de5bd67ee4586fbdd6440d9748f8abb483d3e86"},
{file = "python_dateutil-2.8.2-py2.py3-none-any.whl", hash = "sha256:961d03dc3453ebbc59dbdea9e4e11c5651520a876d0f4db161e8674aae935da9"},
@ -1504,26 +1462,17 @@ tomli = [
{file = "tomli-2.0.1-py3-none-any.whl", hash = "sha256:939de3e7a6161af0c887ef91b7d41a53e7c5a1ca976325f429cb46ea9bc30ecc"},
{file = "tomli-2.0.1.tar.gz", hash = "sha256:de526c12914f0c550d15924c62d72abc48d6fe7364aa87328337a31007fe8a4f"},
]
tox = [
{file = "tox-3.25.0-py2.py3-none-any.whl", hash = "sha256:0805727eb4d6b049de304977dfc9ce315a1938e6619c3ab9f38682bb04662a5a"},
{file = "tox-3.25.0.tar.gz", hash = "sha256:37888f3092aa4e9f835fc8cc6dadbaaa0782651c41ef359e3a5743fcb0308160"},
]
tox = []
traitlets = [
{file = "traitlets-5.3.0-py3-none-any.whl", hash = "sha256:65fa18961659635933100db8ca120ef6220555286949774b9cfc106f941d1c7a"},
{file = "traitlets-5.3.0.tar.gz", hash = "sha256:0bb9f1f9f017aa8ec187d8b1b2a7a6626a2a1d877116baba52a129bfa124f8e2"},
]
typing-extensions = [
{file = "typing_extensions-4.2.0-py3-none-any.whl", hash = "sha256:6657594ee297170d19f67d55c05852a874e7eb634f4f753dbd667855e07c1708"},
{file = "typing_extensions-4.2.0.tar.gz", hash = "sha256:f1c24655a0da0d1b67f07e17a5e6b2a105894e6824b92096378bb3668ef02376"},
]
typing-extensions = []
tzlocal = [
{file = "tzlocal-2.1-py2.py3-none-any.whl", hash = "sha256:e2cb6c6b5b604af38597403e9852872d7f534962ae2954c7f35efcb1ccacf4a4"},
{file = "tzlocal-2.1.tar.gz", hash = "sha256:643c97c5294aedc737780a49d9df30889321cbe1204eac2c2ec6134035a92e44"},
]
virtualenv = [
{file = "virtualenv-20.14.1-py2.py3-none-any.whl", hash = "sha256:e617f16e25b42eb4f6e74096b9c9e37713cf10bf30168fb4a739f3fa8f898a3a"},
{file = "virtualenv-20.14.1.tar.gz", hash = "sha256:ef589a79795589aada0c1c5b319486797c03b67ac3984c48c669c0e4f50df3a5"},
]
virtualenv = []
watchdog = [
{file = "watchdog-2.1.9-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:a735a990a1095f75ca4f36ea2ef2752c99e6ee997c46b0de507ba40a09bf7330"},
{file = "watchdog-2.1.9-cp310-cp310-macosx_10_9_x86_64.whl", hash = "sha256:6b17d302850c8d412784d9246cfe8d7e3af6bcd45f958abb2d08a6f8bedf695d"},
@ -1559,10 +1508,7 @@ xmltodict = [
{file = "xmltodict-0.13.0-py2.py3-none-any.whl", hash = "sha256:aa89e8fd76320154a40d19a0df04a4695fb9dc5ba977cbb68ab3e4eb225e7852"},
{file = "xmltodict-0.13.0.tar.gz", hash = "sha256:341595a488e3e01a85a9d8911d8912fd922ede5fecc4dce437eb4b6c8d037e56"},
]
yq = [
{file = "yq-2.14.0-py3-none-any.whl", hash = "sha256:b6321b29cb39c4e92a4a6f16d47d99a024650211e45e09a02d1906ec45fbaede"},
{file = "yq-2.14.0.tar.gz", hash = "sha256:f4bf2b299d1e5c7ebd74cfb25d1f5d9b6401063bac07a2d09a156144c1d644e1"},
]
yq = []
zipp = [
{file = "zipp-3.8.0-py3-none-any.whl", hash = "sha256:c4f6e5bbf48e74f7a38e7cc5b0480ff42b0ae5178957d564d18932525d5cf099"},
{file = "zipp-3.8.0.tar.gz", hash = "sha256:56bf8aadb83c24db6c4b577e13de374ccfb67da2078beba1d037c17980bf43ad"},

View file

@ -1,15 +1,15 @@
[tool.poetry]
name = "jrnl"
version = "v3.0-beta"
version = "v3.0"
description = "Collect your thoughts and notes without leaving the command line."
authors = [
"jrnl contributors <jrnl-sh@googlegroups.com>",
"jrnl contributors <maintainers@jrnl.sh>",
"Manuel Ebert <manuel@1450.me>",
"Jonathan Wren <jonathan@nowandwren.com>",
"Micah Ellison <micahellison@gmail.com>"
]
maintainers = [
"Jonathan Wren and Micah Ellison <jrnl-sh@googlegroups.com>",
"Jonathan Wren and Micah Ellison <maintainers@jrnl.sh>",
]
license = "GPL-3.0-only"
readme = "README.md"
@ -44,73 +44,75 @@ pytz = ">=2020" # https://pythonhosted.org/pytz/#issues-limitations
tzlocal = ">2.0, <3.0" # https://github.com/regebro/tzlocal/blob/master/CHANGES.txt
[tool.poetry.dev-dependencies]
mkdocs = ">=1.0,<1.3"
black = { version = ">=21.5b2", allow-prereleases = true }
toml = ">=0.10"
pytest = ">=6.2"
pytest-bdd = ">=4.0.1"
ipdb = "*"
isort = ">=5.10"
mkdocs = ">=1.0,<1.3"
poethepoet = "*"
pytest-clarity = "*"
pyproject-flake8 = "*"
yq = "*"
pytest = ">=6.2"
pytest-bdd = ">=4.0.1,<6.0"
pytest-clarity = "*"
pytest-xdist = ">=2.5.0"
toml = ">=0.10"
tox = "*"
[tool.poetry.extras]
testing = [ "pytest", "pytest-bdd", "toml" ]
yq = "*"
[tool.poetry.scripts]
jrnl = 'jrnl.cli:cli'
[tool.poe.tasks]
format = "black ."
format-check = "black --check --diff ."
format-version = "black --version"
format-run = [
{cmd = "black ."},
]
format-check = [
{cmd = "black --version"},
{cmd = "black --check --diff ."},
]
style-check = [
{cmd = "pflake8 --version"},
{cmd = "pflake8 jrnl tests"},
]
sort-run = [
{cmd = "isort ."},
]
sort-check = [
{cmd = "isort --version"},
{cmd = "isort --check ."},
]
# docs-check = ?
docs-run = [
{cmd = "mkdocs serve"},
]
test-run =[
{cmd = "tox -q -e py --"},
]
style-check = "pflake8 jrnl tests"
style-version = "pflake8 --version"
docs = "mkdocs serve"
test-unit = "tox -q -e unit --"
test-bdd = "tox -q -e bdd --"
test-all = "tox -e py --"
installer-check = "poetry check"
installer-version = "poetry --version"
installer-check = [
{cmd = "poetry --version"},
{cmd = "poetry check"},
]
# Groups of tasks
format = [
"format-run",
"sort-run",
]
lint = [
"installer-check",
"style-check",
"sort-check",
"format-check",
]
test = [
"lint",
"test-unit",
"test-bdd",
]
ci-lint = [
"installer-version",
"installer-check",
"style-version",
"style-check",
"format-version",
"format-check",
]
ci-test = [
"test-all",
"test-run",
]
[tool.isort]
multi_line_output = 7
profile = "black"
force_single_line = true
line_length = 88
known_first_party = ["jrnl"]
force_sort_within_sections = true
known_first_party = ["jrnl", "tests"]
[tool.pytest.ini_options]
minversion = "6.0"
@ -125,7 +127,9 @@ markers = [
"on_posix",
]
addopts = [
"--pdbcls=IPython.terminal.debugger:Pdb"
"--pdbcls=IPython.terminal.debugger:Pdb",
"--tb=native",
"-n=auto",
]
filterwarnings = [
@ -147,21 +151,16 @@ build-backend = "poetry.core.masonry.api"
# see: https://tox.wiki/en/latest/example/basic.html
legacy_tox_ini = """
[tox]
envlist = py-{unit,bdd}
envlist = py
isolated_build = True
[testenv]
deps =
pytest >= 6.2
pytest-bdd >=4.0.1
pytest-bdd >=4.0.1,<6.0
pytest-xdist >=2.5.0
toml >=0.10
commands = pytest --junitxml=reports/pytest/results.xml {posargs}
commands = pytest {posargs}
passenv = HOME
[testenv:unit]
commands = pytest tests/unit {posargs}
[testenv:bdd]
commands = pytest tests/bdd --gherkin-terminal-reporter --tb=native {posargs}
"""

View file

@ -110,4 +110,20 @@ Feature: Multiple journals
Scenario: Use a config file with linewrap set to 'auto'
Given we use the config "linewrap_auto.yaml"
When we run "jrnl -1"
Then the output should contain "Life is good."
Then the output should contain "Life is good."
Scenario: Show a warning message when the config file contains duplicate keys at the same level
Given the config "duplicate_keys.yaml" exists
And we use the config "duplicate_keys.yaml"
When we run "jrnl -1"
Then the output should contain "There is at least one duplicate key in your configuration file"
Scenario: Show a warning message when using --config-file with duplicate keys
Given the config "duplicate_keys.yaml" exists
And we use the config "multiple.yaml"
When we run "jrnl --cf duplicate_keys.yaml -1"
Then the output should contain "There is at least one duplicate key in your configuration file"
Scenario: Don't show a duplicate keys warning message when using --config-override on an existing value
Given we use the config "multiple.yaml"
When we run "jrnl --config-override highlight false"
Then the output should not contain "There is at least one duplicate key in your configuration file"

View file

@ -0,0 +1,45 @@
Feature: Installing jrnl
Scenario: Install jrnl with default options
Given we use no config
When we run "jrnl hello world" and enter
\n
\n
Then the output should contain "Journal 'default' created"
And the default journal "journal.txt" should be in the "." directory
And the config should contain "encrypt: false"
And the version in the config file should be up-to-date
Scenario: Install jrnl with custom relative default journal path
Given we use no config
When we run "jrnl hello world" and enter
default/custom.txt
n
Then the output should contain "Journal 'default' created"
And the default journal "custom.txt" should be in the "default" directory
And the config should contain "encrypt: false"
And the version in the config file should be up-to-date
Scenario: Install jrnl with custom expanded default journal path
Given we use no config
And the home directory is called "home"
When we run "jrnl hello world" and enter
~/custom.txt
n
Then the output should contain "Journal 'default' created"
And the default journal "custom.txt" should be in the "home" directory
And the config should contain "encrypt: false"
And the version in the config file should be up-to-date
Scenario: Install jrnl with encrypted default journal
Given we use no config
When we run "jrnl hello world" and enter
encrypted.txt
y
Then the output should contain "Journal will be encrypted"
And the default journal "encrypted.txt" should be in the "." directory
And the config should contain "encrypt: true"
And the version in the config file should be up-to-date
When we run "jrnl"
Then we should be prompted for a password

View file

@ -13,6 +13,7 @@ scenarios("features/encrypt.feature")
scenarios("features/file_storage.feature")
scenarios("features/format.feature")
scenarios("features/import.feature")
scenarios("features/install.feature")
scenarios("features/multiple_journals.feature")
scenarios("features/override.feature")
scenarios("features/password.feature")

View file

@ -4,9 +4,8 @@
from pytest import mark
from pytest import skip
from jrnl.os_compat import on_windows
from jrnl.os_compat import on_posix
from jrnl.os_compat import on_windows
pytest_plugins = [
"tests.lib.fixtures",

View file

@ -0,0 +1,27 @@
default_hour: 9
default_minute: 0
editor: ''
encrypt: false
highlight: true
template: false
template: false
journals:
default:
encrypt: false
journal: features/journals/simple.journal
journal: features/journals/simple.journal
ideas:
encrypt: false
journal: features/journals/does-not-exist.journal
simple:
encrypt: false
journal: features/journals/simple.journal
encrypt: false
work:
encrypt: false
journal: features/journals/work.journal
linewrap: 80
tagsymbols: '@'
editor: nano
timeformat: '%Y-%m-%d %H:%M'
indent_character: "|"

View file

@ -1,23 +1,23 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
from collections import defaultdict
import os
from pathlib import Path
import tempfile
from collections import defaultdict
from collections.abc import Iterable
from pathlib import Path
from unittest.mock import Mock
from unittest.mock import patch
import toml
from keyring import backend
from keyring import errors
from pytest import fixture
from unittest.mock import patch
from unittest.mock import Mock
from .helpers import get_fixture
import toml
from rich.console import Console
from jrnl.config import load_config
from jrnl.os_compat import split_args
from tests.lib.helpers import get_fixture
# --- Keyring --- #
@ -88,6 +88,7 @@ def cli_run(
mock_editor,
mock_user_input,
mock_overrides,
mock_default_journal_path,
):
# Check if we need more mocks
mock_factories.update(mock_args)
@ -96,6 +97,7 @@ def cli_run(
mock_factories.update(mock_editor)
mock_factories.update(mock_config_path)
mock_factories.update(mock_user_input)
mock_factories.update(mock_default_journal_path)
return {
"status": 0,
@ -164,6 +166,19 @@ def mock_config_path(request):
}
@fixture
def mock_default_journal_path(temp_dir):
journal_path = os.path.join(temp_dir.name, "journal.txt")
return {
"default_journal_path_install": lambda: patch(
"jrnl.install.get_default_journal_path", return_value=journal_path
),
"default_journal_path_config": lambda: patch(
"jrnl.config.get_default_journal_path", return_value=journal_path
),
}
@fixture
def temp_dir():
return tempfile.TemporaryDirectory()
@ -216,7 +231,9 @@ def mock_user_input(request, password_input, stdin_input):
return password_input
if isinstance(user_input, Iterable):
return next(user_input)
input_line = next(user_input)
# A raw newline is used to indicate deliberate empty input
return "" if input_line == r"\n" else input_line
# exceptions
return user_input if not kwargs["password"] else password_input

View file

@ -1,12 +1,12 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
from datetime import datetime
import json
import os
import random
import shutil
import string
from datetime import datetime
from unittest.mock import MagicMock
from unittest.mock import patch
from xml.etree import ElementTree
@ -16,10 +16,9 @@ from pytest_bdd.parsers import parse
from jrnl import __version__
from jrnl.time import __get_pdt_calendar
from .fixtures import FailedKeyring
from .fixtures import TestKeyring
from .helpers import get_fixture
from tests.lib.fixtures import FailedKeyring
from tests.lib.fixtures import TestKeyring
from tests.lib.helpers import get_fixture
@given(parse("we {editor_method} to the editor if opened\n{editor_input}"))
@ -147,3 +146,10 @@ def parse_output_as_language(cli_run, language_name):
assert False, f"Language name {language_name} not recognized"
return {"lang": language_name, "obj": parsed_output}
@given(parse('the home directory is called "{home_dir}"'))
def home_directory(temp_dir, home_dir, monkeypatch):
home_path = os.path.join(temp_dir.name, home_dir)
monkeypatch.setenv("USERPROFILE", home_path) # for windows
monkeypatch.setenv("HOME", home_path) # for *nix

View file

@ -11,11 +11,10 @@ from pytest_bdd.parsers import parse
from ruamel.yaml import YAML
from jrnl.config import scope_config
from .helpers import assert_equal_tags_ignoring_order
from .helpers import does_directory_contain_files
from .helpers import parse_should_or_should_not
from .helpers import get_nested_val
from tests.lib.helpers import assert_equal_tags_ignoring_order
from tests.lib.helpers import does_directory_contain_files
from tests.lib.helpers import get_nested_val
from tests.lib.helpers import parse_should_or_should_not
@then("we should get no error")
@ -97,6 +96,12 @@ def output_should_contain_version(cli_run, toml_version):
assert toml_version in out, toml_version
@then("the version in the config file should be up-to-date")
def config_file_version(config_on_disk, toml_version):
config_version = config_on_disk["version"]
assert config_version == toml_version
@then(parse("the output should be {width:d} columns wide"))
def output_should_be_columns_wide(cli_run, width):
out = cli_run["stdout"]
@ -105,6 +110,22 @@ def output_should_be_columns_wide(cli_run, width):
assert len(line) <= width
@then(
parse(
'the default journal "{journal_file}" should be in the "{journal_dir}" directory'
)
)
def default_journal_location(journal_file, journal_dir, config_on_disk, temp_dir):
default_journal_path = config_on_disk["journals"]["default"]
expected_journal_path = (
os.path.join(temp_dir.name, journal_file)
if journal_dir == "."
else os.path.join(temp_dir.name, journal_dir, journal_file)
)
# Use os.path.samefile here because both paths might not be fully expanded.
assert os.path.samefile(default_journal_path, expected_journal_path)
@then(
parse(
'the config for journal "{journal_name}" {should_or_should_not} contain "{some_yaml}"'

View file

@ -1,8 +1,8 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
from contextlib import ExitStack
import os
from contextlib import ExitStack
from pytest_bdd import when
from pytest_bdd.parsers import parse
@ -23,6 +23,8 @@ def when_we_change_directory(directory_name):
command = '(?P<command>[^"]*)'
input_method = "(?P<input_method>enter|pipe|type)"
all_input = '("(?P<all_input>[^"]*)")'
# Note: A line with only a raw newline r'\n' is treated as
# an empty line of input internally for testing purposes.
@when(parse('we run "jrnl {command}" and {input_method}\n{all_input}'))

View file

@ -1,9 +1,9 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
import pytest
from colorama import Fore
from colorama import Style
import pytest
from jrnl.color import colorize

View file

@ -1,11 +1,12 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
import pytest
import os
from jrnl.install import find_alt_config
import pytest
from jrnl.exception import JrnlException
from jrnl.install import find_alt_config
def test_find_alt_config(request):

View file

@ -1,15 +1,15 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
import random
import string
from unittest import mock
import pytest
import random
import string
import jrnl
from jrnl.jrnl import _display_search_results
from jrnl.args import parse_args
from jrnl.jrnl import _display_search_results
@pytest.fixture

View file

@ -1,6 +1,8 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
from argparse import Namespace
import pytest
from jrnl.override import _convert_dots_to_list
@ -9,8 +11,6 @@ from jrnl.override import _get_key_and_value_from_pair
from jrnl.override import _recursively_apply
from jrnl.override import apply_overrides
from argparse import Namespace
@pytest.fixture()
def minimal_config():

View file

@ -1,16 +1,16 @@
# Copyright (C) 2012-2022 jrnl contributors
# License: https://www.gnu.org/licenses/gpl-3.0.html
import pytest
import random
import string
from os import getenv
from unittest.mock import patch
from jrnl.path import home_dir
from jrnl.path import expand_path
import pytest
from jrnl.path import absolute_path
from jrnl.path import expand_path
from jrnl.path import home_dir
@pytest.fixture