1 use std
::process
::{Command, Stdio}
;
4 use serde_json
::{json, Value}
;
6 use proxmox
::api
::{api, ApiMethod, Router, RpcEnvironment, Permission}
;
8 use crate::api2
::types
::*;
9 use crate::config
::acl
::PRIV_SYS_AUDIT
;
16 service
: Option
<&str>,
17 ) -> Result
<(u64, Vec
<Value
>), Error
> {
19 let mut args
= vec
!["-o", "short", "--no-pager"];
21 if let Some(service
) = service { args.extend(&["--unit", service]); }
22 if let Some(since
) = since { args.extend(&["--since", since]); }
23 if let Some(until
) = until { args.extend(&["--until", until]); }
25 let mut lines
: Vec
<Value
> = vec
![];
26 let mut limit
= limit
.unwrap_or(50);
27 let start
= start
.unwrap_or(0);
28 let mut count
: u64 = 0;
30 let mut child
= Command
::new("journalctl")
32 .stdout(Stdio
::piped())
35 use std
::io
::{BufRead,BufReader}
;
37 if let Some(ref mut stdout
) = child
.stdout
{
38 for line
in BufReader
::new(stdout
).lines() {
42 if count
< start { continue }
;
43 if limit
== 0 { continue }
;
45 lines
.push(json
!({ "n": count, "t": line }
));
50 log
::error
!("reading journal failed: {}", err
);
58 let status
= child
.wait().unwrap();
59 if !status
.success() {
60 log
::error
!("journalctl failed with {}", status
);
63 // HACK: ExtJS store.guaranteeRange() does not like empty array
67 lines
.push(json
!({ "n": count, "t": "no content"}
));
82 description
: "Start line number.",
88 description
: "Max. number of lines.",
95 description
: "Display all log since this date-time string.",
96 format
: &SYSTEMD_DATETIME_FORMAT
,
101 description
: "Display all log until this date-time string.",
102 format
: &SYSTEMD_DATETIME_FORMAT
,
107 description
: "Service ID.",
114 description
: "Returns a list of syslog entries.",
118 description
: "Line number.",
122 description
: "Line text.",
127 permission
: &Permission
::Privilege(&["system", "log"], PRIV_SYS_AUDIT
, false),
130 /// Read syslog entries.
134 mut rpcenv
: &mut dyn RpcEnvironment
,
135 ) -> Result
<Value
, Error
> {
137 let (count
, lines
) = dump_journal(
138 param
["start"].as_u64(),
139 param
["limit"].as_u64(),
140 param
["since"].as_str(),
141 param
["until"].as_str(),
142 param
["service"].as_str())?
;
144 rpcenv
["total"] = Value
::from(count
);
149 pub const ROUTER
: Router
= Router
::new()
150 .get(&API_METHOD_GET_SYSLOG
);