release 0.1.0

Signed-off-by: Jia Chao <jiac13@chinaunicom.cn>
This commit is contained in:
Jia Chao 2024-06-14 10:58:15 +08:00
parent 38053414fb
commit 39ee661dc7
2 changed files with 180 additions and 1 deletions

View File

@ -1,11 +1,48 @@
use std::fs::File;
use std::io;
use cvrf_xmlparser::{Severity, XmlReader};
use serde::{Serialize, Deserialize};
use serde::{Deserialize, Serialize};
use tracing::{debug, error, instrument, trace};
use xml::reader::XmlEvent;
#[cfg(test)]
mod test;
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct UpdateInfoDb {
db: Vec<UpdateInfo>,
}
impl UpdateInfoDb {
pub fn new() -> Self {
UpdateInfoDb { db: Vec::new() }
}
#[instrument(skip(self))]
pub fn load_xml(&mut self, xmlfile: &str) -> io::Result<()> {
let file = File::open(xmlfile)?;
let mut source = XmlReader::new(file);
let xmlreader = &mut source;
loop {
let event = xmlreader.next();
if xmlreader.depth() != 2 {
if event == Ok(XmlEvent::EndDocument) {
trace!("End of the xml, break...");
break;
}
continue;
}
let mut updateinfo = UpdateInfo::new();
updateinfo.load_from_xml(xmlreader);
self.db.push(updateinfo);
}
Ok(())
}
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct UpdateInfo {
// sa id
@ -33,6 +70,111 @@ pub struct UpdateInfo {
pkglist: Vec<RpmInfo>,
}
impl UpdateInfo {
pub fn new() -> Self {
UpdateInfo {
id: String::new(),
title: String::new(),
severity: Severity::new(),
release: String::new(),
//date: String::new(),
cves: Vec::new(),
description: String::new(),
pkglist: Vec::new(),
}
}
#[instrument(skip(self, xmlreader))]
fn load_from_xml(&mut self, xmlreader: &mut XmlReader) {
loop {
let key = if let Some(key) = xmlreader.next_start_name_under_depth(1) {
key
} else {
break;
};
debug!("Parser {key} content");
match key.as_str() {
"id" => self.id = xmlreader.next_characters(),
"title" => self.title = xmlreader.next_characters(),
"severity" => {
self.severity = xmlreader.next_characters().parse::<Severity>().unwrap()
}
"release" => self.release = xmlreader.next_characters(),
"description" => self.description = xmlreader.next_characters(),
"references" => self.handle_references(xmlreader),
"pkglist" => self.handle_pkglist(xmlreader),
_ => {}
}
}
}
#[instrument(skip(self, xmlreader))]
fn handle_references(&mut self, xmlreader: &mut XmlReader) {
loop {
if xmlreader.depth() < 3 {
break;
}
match xmlreader.next() {
Ok(XmlEvent::StartElement { attributes, .. }) => {
for attr in attributes {
match attr.name.local_name.as_str() {
"id" => self.cves.push(attr.value.clone()),
_ => {}
}
}
}
Err(e) => {
error!("XmlReader Error: {e}");
break;
}
_ => {}
}
}
}
#[instrument(skip(self, xmlreader))]
fn handle_pkglist(&mut self, xmlreader: &mut XmlReader) {
loop {
if xmlreader.depth() < 3 {
break;
}
match xmlreader.next() {
Ok(XmlEvent::StartElement {
name, attributes, ..
}) => {
if name.local_name.as_str() != "package" {
continue;
}
let mut rpminfo = RpmInfo::new();
for attr in attributes {
rpminfo.set(attr.name.local_name.as_str(), attr.value.clone());
/*
match attr.name.local_name.as_str() {
"name" => rpminfo.name = attr.value.clone(),
"epoch" => rpminfo.epoch = attr.value.clone(),
"version" => rpminfo.version = attr.value.clone(),
"release" => rpminfo.release = attr.value.clone(),
"arch" => rpminfo.arch = attr.value.clone(),
_ => {}
}
*/
}
rpminfo.set("file", xmlreader.next_characters());
self.pkglist.push(rpminfo);
}
Err(e) => {
error!("XmlReader Error: {e}");
break;
}
_ => {}
}
}
}
}
#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct RpmInfo {
// 包名
@ -61,6 +203,19 @@ impl RpmInfo {
}
}
#[instrument(skip(self))]
pub fn set(&mut self, key: &str, value: String) {
match key {
"name" => self.name = value,
"epoch" => self.epoch = value,
"version" => self.version = value,
"release" => self.release = value,
"arch" => self.arch = value,
"file" => self.file = value,
_ => error!("Unknow field: {key}"),
}
}
pub fn name(&self) -> &str {
&self.name
}

24
src/test.rs Normal file
View File

@ -0,0 +1,24 @@
use crate::*;
#[test]
fn it_works() {
let updatexml = "test/updateinfo.xml";
let mut db = UpdateInfoDb::new();
db.load_xml(&updatexml).unwrap();
let id = "openEuler-SA-2022-1587";
let title = "An update for mariadb is now available for openEuler-22.03-LTS";
let severity = cvrf_xmlparser::Severity::Important;
let release = "openEuler";
let cves = 10;
let updateinfo = &db.db[0];
assert_eq!(updateinfo.id, id);
assert_eq!(updateinfo.title, title);
assert_eq!(updateinfo.severity, severity);
assert_eq!(updateinfo.release, release);
assert_eq!(updateinfo.cves.len(), cves);
assert!(true);
}