annotate sat_frontends/jp/common.py @ 3704:c143e7f35074

cli (base): better background detection: - ANSI escape code detection is only used on terminals known to be compatible (currently xterm, konsole, and all VTE based ones) - `COLORFGBG` environment variable is used as fallback - if both methods fail, `dark` is used This should avoid problems with incompatible terminals (e.g. on QTerminal, users had to press `[ENTER]` each time). fix 406
author Goffi <goffi@goffi.org>
date Sat, 06 Nov 2021 17:08:50 +0100
parents fc24e611c9aa
children 742e466fa000
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
3137
559a625a236b fixed shebangs
Goffi <goffi@goffi.org>
parents: 3136
diff changeset
1 #!/usr/bin/env python3
559a625a236b fixed shebangs
Goffi <goffi@goffi.org>
parents: 3136
diff changeset
2
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
3
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
4 # jp: a SàT command line tool
3479
be6d91572633 date update
Goffi <goffi@goffi.org>
parents: 3137
diff changeset
5 # Copyright (C) 2009-2021 Jérôme Poisson (goffi@goffi.org)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
6
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
7 # This program is free software: you can redistribute it and/or modify
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
8 # it under the terms of the GNU Affero General Public License as published by
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
9 # the Free Software Foundation, either version 3 of the License, or
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
10 # (at your option) any later version.
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
11
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
12 # This program is distributed in the hope that it will be useful,
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
13 # but WITHOUT ANY WARRANTY; without even the implied warranty of
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
14 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
15 # GNU Affero General Public License for more details.
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
16
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
17 # You should have received a copy of the GNU Affero General Public License
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
18 # along with this program. If not, see <http://www.gnu.org/licenses/>.
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
19
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
20 import json
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
21 import os
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
22 import os.path
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
23 import time
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
24 import tempfile
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
25 import asyncio
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
26 import shlex
3121
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
27 import re
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
28 from pathlib import Path
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
29 from sat_frontends.jp.constants import Const as C
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
30 from sat.core.i18n import _
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
31 from sat.core import exceptions
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
32 from sat.tools.common import regex
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
33 from sat.tools.common.ansi import ANSI as A
2551
b27165bf160c jp (merge-request/set): if service and node are not specified, URIFinder is now used + ask confirmation before publishing
Goffi <goffi@goffi.org>
parents: 2532
diff changeset
34 from sat.tools.common import uri as xmpp_uri
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
35 from sat.tools import config
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
36 from configparser import NoSectionError, NoOptionError
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
37 from collections import namedtuple
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
38
3676
fc24e611c9aa jp (common): add neovim (`nvim`) default arguments
Goffi <goffi@goffi.org>
parents: 3626
diff changeset
39 # default arguments used for some known editors (editing with metadata)
2523
21d43eab3fb9 jp (common): assure nosplitright in default commands for edition with vim
Goffi <goffi@goffi.org>
parents: 2493
diff changeset
40 VIM_SPLIT_ARGS = "-c 'set nospr|vsplit|wincmd w|next|wincmd w'"
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
41 EMACS_SPLIT_ARGS = '--eval "(split-window-horizontally)"'
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
42 EDITOR_ARGS_MAGIC = {
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
43 "vim": VIM_SPLIT_ARGS + " {content_file} {metadata_file}",
3676
fc24e611c9aa jp (common): add neovim (`nvim`) default arguments
Goffi <goffi@goffi.org>
parents: 3626
diff changeset
44 "nvim": VIM_SPLIT_ARGS + " {content_file} {metadata_file}",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
45 "gvim": VIM_SPLIT_ARGS + " --nofork {content_file} {metadata_file}",
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
46 "emacs": EMACS_SPLIT_ARGS + " {content_file} {metadata_file}",
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
47 "xemacs": EMACS_SPLIT_ARGS + " {content_file} {metadata_file}",
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
48 "nano": " -F {content_file} {metadata_file}",
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
49 }
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
50
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
51 SECURE_UNLINK_MAX = 10
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
52 SECURE_UNLINK_DIR = ".backup"
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
53 METADATA_SUFF = "_metadata.json"
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
54
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
55
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
56 def ansi_ljust(s, width):
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
57 """ljust method handling ANSI escape codes"""
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
58 cleaned = regex.ansiRemove(s)
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
59 return s + " " * (width - len(cleaned))
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
60
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
61
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
62 def ansi_center(s, width):
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
63 """ljust method handling ANSI escape codes"""
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
64 cleaned = regex.ansiRemove(s)
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
65 diff = width - len(cleaned)
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
66 half = diff / 2
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
67 return half * " " + s + (half + diff % 2) * " "
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
68
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
69
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
70 def ansi_rjust(s, width):
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
71 """ljust method handling ANSI escape codes"""
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
72 cleaned = regex.ansiRemove(s)
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
73 return " " * (width - len(cleaned)) + s
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
74
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
75
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
76 def getTmpDir(sat_conf, cat_dir, sub_dir=None):
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
77 """Return directory used to store temporary files
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
78
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
79 @param sat_conf(ConfigParser.ConfigParser): instance opened on sat configuration
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
80 @param cat_dir(str): directory of the category (e.g. "blog")
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
81 @param sub_dir(str): sub directory where data need to be put
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
82 profile can be used here, or special directory name
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
83 sub_dir will be escaped to be usable in path (use regex.pathUnescape to find
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
84 initial str)
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
85 @return (Path): path to the dir
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
86 """
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
87 local_dir = config.getConfig(sat_conf, "", "local_dir", Exception)
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
88 path_elts = [local_dir, cat_dir]
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
89 if sub_dir is not None:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
90 path_elts.append(regex.pathEscape(sub_dir))
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
91 return Path(*path_elts)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
92
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
93
2273
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
94 def parse_args(host, cmd_line, **format_kw):
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
95 """Parse command arguments
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
96
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
97 @param cmd_line(unicode): command line as found in sat.conf
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
98 @param format_kw: keywords used for formating
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
99 @return (list(unicode)): list of arguments to pass to subprocess function
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
100 """
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
101 try:
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
102 # we split the arguments and add the known fields
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
103 # we split arguments first to avoid escaping issues in file names
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
104 return [a.format(**format_kw) for a in shlex.split(cmd_line)]
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
105 except ValueError as e:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
106 host.disp(
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
107 "Couldn't parse editor cmd [{cmd}]: {reason}".format(cmd=cmd_line, reason=e)
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
108 )
2273
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
109 return []
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
110
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
111
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
112 class BaseEdit(object):
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
113 """base class for editing commands
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
114
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
115 This class allows to edit file for PubSub or something else.
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
116 It works with temporary files in SàT local_dir, in a "cat_dir" subdir
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
117 """
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
118
2273
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
119 def __init__(self, host, cat_dir, use_metadata=False):
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
120 """
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
121 @param sat_conf(ConfigParser.ConfigParser): instance opened on sat configuration
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
122 @param cat_dir(unicode): directory to use for drafts
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
123 this will be a sub-directory of SàT's local_dir
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
124 @param use_metadata(bool): True is edition need a second file for metadata
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
125 most of signature change with use_metadata with an additional metadata
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
126 argument.
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
127 This is done to raise error if a command needs metadata but forget the flag,
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
128 and vice versa
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
129 """
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
130 self.host = host
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
131 self.cat_dir = cat_dir
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
132 self.use_metadata = use_metadata
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
133
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
134 def secureUnlink(self, path):
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
135 """Unlink given path after keeping it for a while
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
136
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
137 This method is used to prevent accidental deletion of a draft
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
138 If there are more file in SECURE_UNLINK_DIR than SECURE_UNLINK_MAX,
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
139 older file are deleted
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
140 @param path(Path, str): file to unlink
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
141 """
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
142 path = Path(path).resolve()
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
143 if not path.is_file:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
144 raise OSError("path must link to a regular file")
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
145 if path.parent != getTmpDir(self.sat_conf, self.cat_dir):
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
146 self.disp(
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
147 f"File {path} is not in SàT temporary hierarchy, we do not remove " f"it",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
148 2,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
149 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
150 return
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
151 # we have 2 files per draft with use_metadata, so we double max
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
152 unlink_max = SECURE_UNLINK_MAX * 2 if self.use_metadata else SECURE_UNLINK_MAX
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
153 backup_dir = getTmpDir(self.sat_conf, self.cat_dir, SECURE_UNLINK_DIR)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
154 if not os.path.exists(backup_dir):
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
155 os.makedirs(backup_dir)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
156 filename = os.path.basename(path)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
157 backup_path = os.path.join(backup_dir, filename)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
158 # we move file to backup dir
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
159 self.host.disp(
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
160 "Backuping file {src} to {dst}".format(src=path, dst=backup_path),
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
161 1,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
162 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
163 os.rename(path, backup_path)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
164 # and if we exceeded the limit, we remove older file
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
165 backup_files = [os.path.join(backup_dir, f) for f in os.listdir(backup_dir)]
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
166 if len(backup_files) > unlink_max:
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
167 backup_files.sort(key=lambda path: os.stat(path).st_mtime)
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
168 for path in backup_files[: len(backup_files) - unlink_max]:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
169 self.host.disp("Purging backup file {}".format(path), 2)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
170 os.unlink(path)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
171
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
172 async def runEditor(
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
173 self,
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
174 editor_args_opt,
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
175 content_file_path,
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
176 content_file_obj,
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
177 meta_file_path=None,
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
178 meta_ori=None,
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
179 ):
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
180 """Run editor to edit content and metadata
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
181
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
182 @param editor_args_opt(unicode): option in [jp] section in configuration for
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
183 specific args
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
184 @param content_file_path(str): path to the content file
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
185 @param content_file_obj(file): opened file instance
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
186 @param meta_file_path(str, Path, None): metadata file path
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
187 if None metadata will not be used
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
188 @param meta_ori(dict, None): original cotent of metadata
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
189 can't be used if use_metadata is False
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
190 """
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
191 if not self.use_metadata:
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
192 assert meta_file_path is None
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
193 assert meta_ori is None
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
194
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
195 # we calculate hashes to check for modifications
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
196 import hashlib
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
197
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
198 content_file_obj.seek(0)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
199 tmp_ori_hash = hashlib.sha1(content_file_obj.read()).digest()
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
200 content_file_obj.close()
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
201
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
202 # we prepare arguments
3626
82e616b70a2a CLI: fix section used for config following name change
Goffi <goffi@goffi.org>
parents: 3568
diff changeset
203 editor = config.getConfig(self.sat_conf, C.CONFIG_SECTION, "editor") or os.getenv(
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
204 "EDITOR", "vi"
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
205 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
206 try:
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
207 # is there custom arguments in sat.conf ?
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
208 editor_args = config.getConfig(
3626
82e616b70a2a CLI: fix section used for config following name change
Goffi <goffi@goffi.org>
parents: 3568
diff changeset
209 self.sat_conf, C.CONFIG_SECTION, editor_args_opt, Exception
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
210 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
211 except (NoOptionError, NoSectionError):
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
212 # no, we check if we know the editor and have special arguments
2273
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
213 if self.use_metadata:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
214 editor_args = EDITOR_ARGS_MAGIC.get(os.path.basename(editor), "")
2273
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
215 else:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
216 editor_args = ""
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
217 parse_kwargs = {"content_file": content_file_path}
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
218 if self.use_metadata:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
219 parse_kwargs["metadata_file"] = meta_file_path
2273
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
220 args = parse_args(self.host, editor_args, **parse_kwargs)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
221 if not args:
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
222 args = [content_file_path]
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
223
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
224 # actual editing
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
225 editor_process = await asyncio.create_subprocess_exec(
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
226 editor, *[str(a) for a in args]
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
227 )
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
228 editor_exit = await editor_process.wait()
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
229
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
230 # edition will now be checked, and data will be sent if it was a success
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
231 if editor_exit != 0:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
232 self.disp(
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
233 f"Editor exited with an error code, so temporary file has not be "
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
234 f"deleted, and item is not published.\nYou can find temporary file "
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
235 f"at {content_file_path}",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
236 error=True,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
237 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
238 else:
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
239 # main content
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
240 try:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
241 with content_file_path.open("rb") as f:
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
242 content = f.read()
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
243 except (OSError, IOError):
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
244 self.disp(
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
245 f"Can read file at {content_file_path}, have it been deleted?\n"
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
246 f"Cancelling edition",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
247 error=True,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
248 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
249 self.host.quit(C.EXIT_NOT_FOUND)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
250
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
251 # metadata
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
252 if self.use_metadata:
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
253 try:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
254 with meta_file_path.open("rb") as f:
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
255 metadata = json.load(f)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
256 except (OSError, IOError):
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
257 self.disp(
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
258 f"Can read file at {meta_file_path}, have it been deleted?\n"
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
259 f"Cancelling edition",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
260 error=True,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
261 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
262 self.host.quit(C.EXIT_NOT_FOUND)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
263 except ValueError:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
264 self.disp(
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
265 f"Can't parse metadata, please check it is correct JSON format. "
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
266 f"Cancelling edition.\nYou can find tmp file at "
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
267 f"{content_file_path} and temporary meta file at "
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
268 f"{meta_file_path}.",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
269 error=True,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
270 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
271 self.host.quit(C.EXIT_DATA_ERROR)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
272
2905
d9491cb81726 jp (common): `publish` is now a boolean
Goffi <goffi@goffi.org>
parents: 2771
diff changeset
273 if self.use_metadata and not metadata.get("publish", True):
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
274 self.disp(
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
275 f'Publication blocked by "publish" key in metadata, cancelling '
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
276 f"edition.\n\ntemporary file path:\t{content_file_path}\nmetadata "
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
277 f"file path:\t{meta_file_path}",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
278 error=True,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
279 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
280 self.host.quit()
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
281
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
282 if len(content) == 0:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
283 self.disp("Content is empty, cancelling the edition")
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
284 if content_file_path.parent != getTmpDir(self.sat_conf, self.cat_dir):
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
285 self.disp(
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
286 "File are not in SàT temporary hierarchy, we do not remove them",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
287 2,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
288 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
289 self.host.quit()
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
290 self.disp(f"Deletion of {content_file_path}", 2)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
291 os.unlink(content_file_path)
2273
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
292 if self.use_metadata:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
293 self.disp(f"Deletion of {meta_file_path}".format(meta_file_path), 2)
2273
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
294 os.unlink(meta_file_path)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
295 self.host.quit()
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
296
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
297 # time to re-check the hash
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
298 elif tmp_ori_hash == hashlib.sha1(content).digest() and (
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
299 not self.use_metadata or meta_ori == metadata
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
300 ):
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
301 self.disp("The content has not been modified, cancelling the edition")
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
302 self.host.quit()
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
303
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
304 else:
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
305 # we can now send the item
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
306 content = content.decode("utf-8-sig") # we use utf-8-sig to avoid BOM
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
307 try:
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
308 if self.use_metadata:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
309 await self.publish(content, metadata)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
310 else:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
311 await self.publish(content)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
312 except Exception as e:
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
313 if self.use_metadata:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
314 self.disp(
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
315 f"Error while sending your item, the temporary files have "
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
316 f"been kept at {content_file_path} and {meta_file_path}: "
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
317 f"{e}",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
318 error=True,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
319 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
320 else:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
321 self.disp(
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
322 f"Error while sending your item, the temporary file has been "
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
323 f"kept at {content_file_path}: {e}",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
324 error=True,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
325 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
326 self.host.quit(1)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
327
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
328 self.secureUnlink(content_file_path)
2273
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
329 if self.use_metadata:
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
330 self.secureUnlink(meta_file_path)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
331
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
332 async def publish(self, content):
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
333 # if metadata is needed, publish will be called with it last argument
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
334 raise NotImplementedError
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
335
2351
3c0a3fae1862 jp (pubsub/node): added schema (set/edit/get) commands to manipulate PubSub node schema
Goffi <goffi@goffi.org>
parents: 2345
diff changeset
336 def getTmpFile(self):
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
337 """Create a temporary file
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
338
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
339 @return (tuple(file, Path)): opened (w+b) file object and file path
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
340 """
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
341 suff = "." + self.getTmpSuff()
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
342 cat_dir_str = self.cat_dir
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
343 tmp_dir = getTmpDir(self.sat_conf, self.cat_dir, self.profile)
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
344 if not tmp_dir.exists():
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
345 try:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
346 tmp_dir.mkdir(parents=True)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
347 except OSError as e:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
348 self.disp(
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
349 f"Can't create {tmp_dir} directory: {e}",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
350 error=True,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
351 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
352 self.host.quit(1)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
353 try:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
354 fd, path = tempfile.mkstemp(
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
355 suffix=suff,
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
356 prefix=time.strftime(cat_dir_str + "_%Y-%m-%d_%H:%M:%S_"),
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
357 dir=tmp_dir,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
358 text=True,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
359 )
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
360 return os.fdopen(fd, "w+b"), Path(path)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
361 except OSError as e:
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
362 self.disp(f"Can't create temporary file: {e}", error=True)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
363 self.host.quit(1)
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
364
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
365 def getCurrentFile(self, profile):
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
366 """Get most recently edited file
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
367
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
368 @param profile(unicode): profile linked to the draft
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
369 @return(Path): full path of current file
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
370 """
2273
5f0dbf42aa9c jp (blog, common): various fixes in common and blog:
Goffi <goffi@goffi.org>
parents: 2270
diff changeset
371 # we guess the item currently edited by choosing
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
372 # the most recent file corresponding to temp file pattern
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
373 # in tmp_dir, excluding metadata files
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
374 tmp_dir = getTmpDir(self.sat_conf, self.cat_dir, profile)
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
375 available = [
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
376 p
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
377 for p in tmp_dir.glob(f"{self.cat_dir}_*")
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
378 if not p.match(f"*{METADATA_SUFF}")
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
379 ]
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
380 if not available:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
381 self.disp(
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
382 f"Could not find any content draft in {tmp_dir}",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
383 error=True,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
384 )
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
385 self.host.quit(1)
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
386 return max(available, key=lambda p: p.stat().st_mtime)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
387
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
388 async def getItemData(self, service, node, item):
2280
4bc9a2c2d6c9 jp (pubsub, common): fixed last item edition (keep item id instead of creating a new one)
Goffi <goffi@goffi.org>
parents: 2279
diff changeset
389 """return formatted content, metadata (or not if use_metadata is false), and item id"""
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
390 raise NotImplementedError
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
391
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
392 def getTmpSuff(self):
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
393 """return suffix used for content file"""
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
394 return "xml"
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
395
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
396 async def getItemPath(self):
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
397 """Retrieve item path (i.e. service and node) from item argument
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
398
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
399 This method is obviously only useful for edition of PubSub based features
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
400 """
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
401 service = self.args.service
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
402 node = self.args.node
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
403 item = self.args.item
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
404 last_item = self.args.last_item
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
405
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
406 if self.args.current:
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
407 # user wants to continue current draft
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
408 content_file_path = self.getCurrentFile(self.profile)
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
409 self.disp("Continuing edition of current draft", 2)
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
410 content_file_obj = content_file_path.open("r+b")
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
411 # we seek at the end of file in case of an item already exist
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
412 # this will write content of the existing item at the end of the draft.
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
413 # This way no data should be lost.
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
414 content_file_obj.seek(0, os.SEEK_END)
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
415 elif self.args.draft_path:
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
416 # there is an existing draft that we use
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
417 content_file_path = self.args.draft_path.expanduser()
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
418 content_file_obj = content_file_path.open("r+b")
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
419 # we seek at the end for the same reason as above
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
420 content_file_obj.seek(0, os.SEEK_END)
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
421 else:
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
422 # we need a temporary file
2351
3c0a3fae1862 jp (pubsub/node): added schema (set/edit/get) commands to manipulate PubSub node schema
Goffi <goffi@goffi.org>
parents: 2345
diff changeset
423 content_file_obj, content_file_path = self.getTmpFile()
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
424
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
425 if item or last_item:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
426 self.disp("Editing requested published item", 2)
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
427 try:
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
428 if self.use_metadata:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
429 content, metadata, item = await self.getItemData(service, node, item)
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
430 else:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
431 content, item = await self.getItemData(service, node, item)
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
432 except Exception as e:
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
433 # FIXME: ugly but we have not good may to check errors in bridge
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
434 if "item-not-found" in str(e):
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
435 #  item doesn't exist, we create a new one with requested id
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
436 metadata = None
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
437 if last_item:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
438 self.disp(_("no item found at all, we create a new one"), 2)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
439 else:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
440 self.disp(
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
441 _(
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
442 'item "{item}" not found, we create a new item with'
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
443 "this id"
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
444 ).format(item=item),
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
445 2,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
446 )
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
447 content_file_obj.seek(0)
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
448 else:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
449 self.disp(f"Error while retrieving item: {e}")
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
450 self.host.quit(C.EXIT_ERROR)
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
451 else:
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
452 # item exists, we write content
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
453 if content_file_obj.tell() != 0:
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
454 # we already have a draft,
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
455 # we copy item content after it and add an indicator
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
456 content_file_obj.write("\n*****\n")
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
457 content_file_obj.write(content.encode("utf-8"))
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
458 content_file_obj.seek(0)
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
459 self.disp(_('item "{item}" found, we edit it').format(item=item), 2)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
460 else:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
461 self.disp("Editing a new item", 2)
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
462 if self.use_metadata:
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
463 metadata = None
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
464
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
465 if self.use_metadata:
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
466 return service, node, item, content_file_path, content_file_obj, metadata
2269
606ff34d30f2 jp (blog, common): moved and improved edit code from blog:
Goffi <goffi@goffi.org>
parents:
diff changeset
467 else:
2532
772447ec070f jp: pubsub options refactoring:
Goffi <goffi@goffi.org>
parents: 2523
diff changeset
468 return service, node, item, content_file_path, content_file_obj
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
469
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
470
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
471 class Table(object):
2345
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
472 def __init__(self, host, data, headers=None, filters=None, use_buffer=False):
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
473 """
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
474 @param data(iterable[list]): table data
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
475 all lines must have the same number of columns
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
476 @param headers(iterable[unicode], None): names/titles of the columns
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
477 if not None, must have same number of columns as data
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
478 @param filters(iterable[(callable, unicode)], None): values filters
2610
c9dddf691d7b jp (common): allow tables filters callbacks to have only one argument
Goffi <goffi@goffi.org>
parents: 2562
diff changeset
479 the callable will get 2 arguments:
c9dddf691d7b jp (common): allow tables filters callbacks to have only one argument
Goffi <goffi@goffi.org>
parents: 2562
diff changeset
480 - current column value
c9dddf691d7b jp (common): allow tables filters callbacks to have only one argument
Goffi <goffi@goffi.org>
parents: 2562
diff changeset
481 - RowData with all columns values
c9dddf691d7b jp (common): allow tables filters callbacks to have only one argument
Goffi <goffi@goffi.org>
parents: 2562
diff changeset
482 if may also only use 1 argument, which will then be current col value.
c9dddf691d7b jp (common): allow tables filters callbacks to have only one argument
Goffi <goffi@goffi.org>
parents: 2562
diff changeset
483 the callable must return a string
3121
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
484 if it's unicode, it will be used with .format and must countain u'{}' which
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
485 will be replaced with the string.
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
486 if not None, must have same number of columns as data
2345
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
487 @param use_buffer(bool): if True, bufferise output instead of printing it directly
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
488 """
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
489 self.host = host
2345
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
490 self._buffer = [] if use_buffer else None
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
491 #  headers are columns names/titles, can be None
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
492 self.headers = headers
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
493 #  sizes fof columns without headers,
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
494 # headers may be larger
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
495 self.sizes = []
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
496 #  rows countains one list per row with columns values
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
497 self.rows = []
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
498
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
499 size = None
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
500 if headers:
3121
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
501 # we use a namedtuple to make the value easily accessible from filters
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
502 headers_safe = [re.sub(r"[^a-zA-Z_]", "_", h) for h in headers]
3121
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
503 row_cls = namedtuple("RowData", headers_safe)
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
504 else:
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
505 row_cls = tuple
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
506
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
507 for row_data in data:
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
508 new_row = []
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
509 row_data_list = list(row_data)
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
510 for idx, value in enumerate(row_data_list):
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
511 if filters is not None and filters[idx] is not None:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
512 filter_ = filters[idx]
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
513 if isinstance(filter_, str):
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
514 col_value = filter_.format(value)
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
515 else:
2610
c9dddf691d7b jp (common): allow tables filters callbacks to have only one argument
Goffi <goffi@goffi.org>
parents: 2562
diff changeset
516 try:
c9dddf691d7b jp (common): allow tables filters callbacks to have only one argument
Goffi <goffi@goffi.org>
parents: 2562
diff changeset
517 col_value = filter_(value, row_cls(*row_data_list))
c9dddf691d7b jp (common): allow tables filters callbacks to have only one argument
Goffi <goffi@goffi.org>
parents: 2562
diff changeset
518 except TypeError:
c9dddf691d7b jp (common): allow tables filters callbacks to have only one argument
Goffi <goffi@goffi.org>
parents: 2562
diff changeset
519 col_value = filter_(value)
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
520 # we count size without ANSI code as they will change length of the
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
521 # string when it's mostly style/color changes.
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
522 col_size = len(regex.ansiRemove(col_value))
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
523 else:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
524 col_value = str(value)
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
525 col_size = len(col_value)
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
526 new_row.append(col_value)
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
527 if size is None:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
528 self.sizes.append(col_size)
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
529 else:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
530 self.sizes[idx] = max(self.sizes[idx], col_size)
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
531 if size is None:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
532 size = len(new_row)
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
533 if headers is not None and len(headers) != size:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
534 raise exceptions.DataError("headers size is not coherent with rows")
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
535 else:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
536 if len(new_row) != size:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
537 raise exceptions.DataError("rows size is not coherent")
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
538 self.rows.append(new_row)
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
539
2344
78ffb9ce57a4 jp (common): fixed empty table display when headers are specified
Goffi <goffi@goffi.org>
parents: 2334
diff changeset
540 if not data and headers is not None:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
541 #  the table is empty, we print headers at their lenght
2344
78ffb9ce57a4 jp (common): fixed empty table display when headers are specified
Goffi <goffi@goffi.org>
parents: 2334
diff changeset
542 self.sizes = [len(h) for h in headers]
78ffb9ce57a4 jp (common): fixed empty table display when headers are specified
Goffi <goffi@goffi.org>
parents: 2334
diff changeset
543
2345
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
544 @property
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
545 def string(self):
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
546 if self._buffer is None:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
547 raise exceptions.InternalError("buffer must be used to get a string")
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
548 return "\n".join(self._buffer)
2345
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
549
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
550 @staticmethod
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
551 def readDictValues(data, keys, defaults=None):
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
552 if defaults is None:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
553 defaults = {}
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
554 for key in keys:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
555 try:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
556 yield data[key]
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
557 except KeyError as e:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
558 default = defaults.get(key)
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
559 if default is not None:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
560 yield default
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
561 else:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
562 raise e
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
563
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
564 @classmethod
3121
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
565 def fromListDict(
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
566 cls, host, data, keys=None, headers=None, filters=None, defaults=None
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
567 ):
3121
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
568 """Create a table from a list of dictionaries
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
569
3121
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
570 each dictionary is a row of the table, keys being columns names.
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
571 the whole data will be read and kept into memory, to be printed
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
572 @param data(list[dict[unicode, unicode]]): data to create the table from
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
573 @param keys(iterable[unicode], None): keys to get
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
574 if None, all keys will be used
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
575 @param headers(iterable[unicode], None): name of the columns
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
576 names must be in same order as keys
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
577 @param filters(dict[unicode, (callable,unicode)), None): filter to use on values
2610
c9dddf691d7b jp (common): allow tables filters callbacks to have only one argument
Goffi <goffi@goffi.org>
parents: 2562
diff changeset
578 keys correspond to keys to filter, and value is the same as for Table.__init__
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
579 @param defaults(dict[unicode, unicode]): default value to use
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
580 if None, an exception will be raised if not value is found
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
581 """
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
582 if keys is None and headers is not None:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
583 # FIXME: keys are not needed with OrderedDict,
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
584 raise exceptions.DataError("You must specify keys order to used headers")
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
585 if keys is None:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
586 keys = list(data[0].keys())
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
587 if headers is None:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
588 headers = keys
3121
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
589 if filters is None:
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
590 filters = {}
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
591 filters = [filters.get(k) for k in keys]
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
592 return cls(
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
593 host, (cls.readDictValues(d, keys, defaults) for d in data), headers, filters
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
594 )
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
595
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
596 def _headers(self, head_sep, headers, sizes, alignment="left", style=None):
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
597 """Render headers
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
598
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
599 @param head_sep(unicode): sequence to use as separator
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
600 @param alignment(unicode): how to align, can be left, center or right
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
601 @param style(unicode, iterable[unicode], None): ANSI escape sequences to apply
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
602 @param headers(list[unicode]): headers to show
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
603 @param sizes(list[int]): sizes of columns
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
604 """
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
605 rendered_headers = []
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
606 if isinstance(style, str):
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
607 style = [style]
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
608 for idx, header in enumerate(headers):
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
609 size = sizes[idx]
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
610 if alignment == "left":
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
611 rendered = header[:size].ljust(size)
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
612 elif alignment == "center":
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
613 rendered = header[:size].center(size)
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
614 elif alignment == "right":
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
615 rendered = header[:size].rjust(size)
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
616 else:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
617 raise exceptions.InternalError("bad alignment argument")
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
618 if style:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
619 args = style + [rendered]
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
620 rendered = A.color(*args)
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
621 rendered_headers.append(rendered)
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
622 return head_sep.join(rendered_headers)
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
623
2345
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
624 def _disp(self, data):
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
625 """output data (can be either bufferised or printed)"""
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
626 if self._buffer is not None:
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
627 self._buffer.append(data)
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
628 else:
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
629 self.host.disp(data)
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
630
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
631 def display(
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
632 self,
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
633 head_alignment="left",
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
634 columns_alignment="left",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
635 head_style=None,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
636 show_header=True,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
637 show_borders=True,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
638 hide_cols=None,
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
639 col_sep=" │ ",
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
640 top_left="┌",
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
641 top="─",
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
642 top_sep="─┬─",
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
643 top_right="┐",
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
644 left="│",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
645 right=None,
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
646 head_sep=None,
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
647 head_line="┄",
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
648 head_line_left="├",
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
649 head_line_sep="┄┼┄",
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
650 head_line_right="┤",
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
651 bottom_left="└",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
652 bottom=None,
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
653 bottom_sep="─┴─",
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
654 bottom_right="┘",
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
655 ):
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
656 """Print the table
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
657
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
658 @param show_header(bool): True if header need no be shown
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
659 @param show_borders(bool): True if borders need no be shown
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
660 @param hide_cols(None, iterable(unicode)): columns which should not be displayed
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
661 @param head_alignment(unicode): how to align headers, can be left, center or right
3121
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
662 @param columns_alignment(unicode): how to align columns, can be left, center or
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
663 right
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
664 @param col_sep(unicode): separator betweens columns
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
665 @param head_line(unicode): character to use to make line under head
2345
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
666 @param disp(callable, None): method to use to display the table
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
667 None to use self.host.disp
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
668 """
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
669 if not self.sizes:
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
670 # the table is empty
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
671 return
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
672 col_sep_size = len(regex.ansiRemove(col_sep))
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
673
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
674 # if we have columns to hide, we remove them from headers and size
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
675 if not hide_cols:
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
676 headers = self.headers
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
677 sizes = self.sizes
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
678 else:
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
679 headers = list(self.headers)
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
680 sizes = self.sizes[:]
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
681 ignore_idx = [headers.index(to_hide) for to_hide in hide_cols]
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
682 for to_hide in hide_cols:
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
683 hide_idx = headers.index(to_hide)
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
684 del headers[hide_idx]
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
685 del sizes[hide_idx]
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
686
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
687 if right is None:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
688 right = left
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
689 if top_sep is None:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
690 top_sep = col_sep_size * top
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
691 if head_sep is None:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
692 head_sep = col_sep
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
693 if bottom is None:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
694 bottom = top
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
695 if bottom_sep is None:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
696 bottom_sep = col_sep_size * bottom
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
697 if not show_borders:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
698 left = right = head_line_left = head_line_right = ""
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
699 # top border
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
700 if show_borders:
2345
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
701 self._disp(
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
702 top_left + top_sep.join([top * size for size in sizes]) + top_right
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
703 )
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
704
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
705 # headers
3121
040ca99e25fe jp (common): various Table fixes:
Goffi <goffi@goffi.org>
parents: 3046
diff changeset
706 if show_header and self.headers is not None:
2345
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
707 self._disp(
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
708 left
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
709 + self._headers(head_sep, headers, sizes, head_alignment, head_style)
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
710 + right
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
711 )
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
712 # header line
2345
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
713 self._disp(
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
714 head_line_left
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
715 + head_line_sep.join([head_line * size for size in sizes])
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
716 + head_line_right
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
717 )
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
718
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
719 # content
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
720 if columns_alignment == "left":
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
721 alignment = lambda idx, s: ansi_ljust(s, sizes[idx])
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
722 elif columns_alignment == "center":
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
723 alignment = lambda idx, s: ansi_center(s, sizes[idx])
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
724 elif columns_alignment == "right":
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
725 alignment = lambda idx, s: ansi_rjust(s, sizes[idx])
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
726 else:
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
727 raise exceptions.InternalError("bad columns alignment argument")
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
728
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
729 for row in self.rows:
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
730 if hide_cols:
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
731 row = [v for idx, v in enumerate(row) if idx not in ignore_idx]
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
732 self._disp(
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
733 left
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
734 + col_sep.join([alignment(idx, c) for idx, c in enumerate(row)])
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
735 + right
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
736 )
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
737
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
738 if show_borders:
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
739 # bottom border
2345
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
740 self._disp(
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
741 bottom_left
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
742 + bottom_sep.join([bottom * size for size in sizes])
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
743 + bottom_right
2624
56f94936df1e code style reformatting using black
Goffi <goffi@goffi.org>
parents: 2610
diff changeset
744 )
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
745 #  we return self so string can be used after display (table.display().string)
2345
c57bc0fe17d9 jp (common): added use_buffer argument in Table:
Goffi <goffi@goffi.org>
parents: 2344
diff changeset
746 return self
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
747
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
748 def display_blank(self, **kwargs):
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
749 """Display table without visible borders"""
3028
ab2696e34d29 Python 3 port:
Goffi <goffi@goffi.org>
parents: 2905
diff changeset
750 kwargs_ = {"col_sep": " ", "head_line_sep": " ", "show_borders": False}
2298
276e546b7619 jp (common): new ansi_ljust, ansi_rjust and ansi_center command + table:
Goffi <goffi@goffi.org>
parents: 2280
diff changeset
751 kwargs_.update(kwargs)
2493
984792a451bc jp (common/table): a column can be hidden + fix for empty tables
Goffi <goffi@goffi.org>
parents: 2483
diff changeset
752 return self.display(**kwargs_)
2551
b27165bf160c jp (merge-request/set): if service and node are not specified, URIFinder is now used + ask confirmation before publishing
Goffi <goffi@goffi.org>
parents: 2532
diff changeset
753
b27165bf160c jp (merge-request/set): if service and node are not specified, URIFinder is now used + ask confirmation before publishing
Goffi <goffi@goffi.org>
parents: 2532
diff changeset
754
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
755 async def fill_well_known_uri(command, path, key, meta_map=None):
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
756 """Look for URIs in well-known location and fill appropriate args if suitable
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
757
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
758 @param command(CommandBase): command instance
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
759 args of this instance will be updated with found values
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
760 @param path(unicode): absolute path to use as a starting point to look for URIs
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
761 @param key(unicode): key to look for
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
762 @param meta_map(dict, None): if not None, map metadata to arg name
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
763 key is metadata used attribute name
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
764 value is name to actually use, or None to ignore
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
765 use empty dict to only retrieve URI
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
766 possible keys are currently:
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
767 - labels
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
768 """
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
769 args = command.args
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
770 if args.service or args.node:
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
771 # we only look for URIs if a service and a node are not already specified
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
772 return
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
773
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
774 host = command.host
2551
b27165bf160c jp (merge-request/set): if service and node are not specified, URIFinder is now used + ask confirmation before publishing
Goffi <goffi@goffi.org>
parents: 2532
diff changeset
775
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
776 try:
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
777 uris_data = await host.bridge.URIFind(path, [key])
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
778 except Exception as e:
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
779 host.disp(f"can't find {key} URI: {e}", error=True)
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
780 host.quit(C.EXIT_BRIDGE_ERRBACK)
2551
b27165bf160c jp (merge-request/set): if service and node are not specified, URIFinder is now used + ask confirmation before publishing
Goffi <goffi@goffi.org>
parents: 2532
diff changeset
781
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
782 try:
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
783 uri_data = uris_data[key]
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
784 except KeyError:
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
785 host.disp(
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
786 _(
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
787 "No {key} URI specified for this project, please specify service and "
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
788 "node"
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
789 ).format(key=key),
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
790 error=True,
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
791 )
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
792 host.quit(C.EXIT_NOT_FOUND)
2558
501b0f827f63 jp (merge-request,common): fixed URIFinder when metadata are not needed:
Goffi <goffi@goffi.org>
parents: 2554
diff changeset
793
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
794 uri = uri_data["uri"]
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
795
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
796 # set extra metadata if they are specified
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
797 for data_key in ["labels"]:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
798 new_values_json = uri_data.get(data_key)
2558
501b0f827f63 jp (merge-request,common): fixed URIFinder when metadata are not needed:
Goffi <goffi@goffi.org>
parents: 2554
diff changeset
799 if uri_data is not None:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
800 if meta_map is None:
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
801 dest = data_key
2558
501b0f827f63 jp (merge-request,common): fixed URIFinder when metadata are not needed:
Goffi <goffi@goffi.org>
parents: 2554
diff changeset
802 else:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
803 dest = meta_map.get(data_key)
2558
501b0f827f63 jp (merge-request,common): fixed URIFinder when metadata are not needed:
Goffi <goffi@goffi.org>
parents: 2554
diff changeset
804 if dest is None:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
805 continue
2558
501b0f827f63 jp (merge-request,common): fixed URIFinder when metadata are not needed:
Goffi <goffi@goffi.org>
parents: 2554
diff changeset
806
501b0f827f63 jp (merge-request,common): fixed URIFinder when metadata are not needed:
Goffi <goffi@goffi.org>
parents: 2554
diff changeset
807 try:
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
808 values = getattr(args, data_key)
2558
501b0f827f63 jp (merge-request,common): fixed URIFinder when metadata are not needed:
Goffi <goffi@goffi.org>
parents: 2554
diff changeset
809 except AttributeError:
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
810 raise exceptions.InternalError(f"there is no {data_key!r} arguments")
2558
501b0f827f63 jp (merge-request,common): fixed URIFinder when metadata are not needed:
Goffi <goffi@goffi.org>
parents: 2554
diff changeset
811 else:
501b0f827f63 jp (merge-request,common): fixed URIFinder when metadata are not needed:
Goffi <goffi@goffi.org>
parents: 2554
diff changeset
812 if values is None:
501b0f827f63 jp (merge-request,common): fixed URIFinder when metadata are not needed:
Goffi <goffi@goffi.org>
parents: 2554
diff changeset
813 values = []
501b0f827f63 jp (merge-request,common): fixed URIFinder when metadata are not needed:
Goffi <goffi@goffi.org>
parents: 2554
diff changeset
814 values.extend(json.loads(new_values_json))
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
815 setattr(args, dest, values)
2558
501b0f827f63 jp (merge-request,common): fixed URIFinder when metadata are not needed:
Goffi <goffi@goffi.org>
parents: 2554
diff changeset
816
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
817 parsed_uri = xmpp_uri.parseXMPPUri(uri)
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
818 try:
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
819 args.service = parsed_uri["path"]
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
820 args.node = parsed_uri["node"]
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
821 except KeyError:
3568
04283582966f core, frontends: fix invalid translatable strings.
Goffi <goffi@goffi.org>
parents: 3479
diff changeset
822 host.disp(_("Invalid URI found: {uri}").format(uri=uri), error=True)
3040
fee60f17ebac jp: jp asyncio port:
Goffi <goffi@goffi.org>
parents: 3037
diff changeset
823 host.quit(C.EXIT_DATA_ERROR)