Skip to content

Commit

Permalink
refactor(writer/xlsx): simplify make_buffer function and improve work…
Browse files Browse the repository at this point in the history
…sheet processing

- Reorganized the `make_buffer` function for better readability and maintainability.
- Replaced manual iteration with `try_for_each` for processing worksheets.
- Consolidated worksheet processing logic to handle both deserialized and raw data more cleanly.
- Improved comments for clarity on each processing step.
- Streamlined the addition of various worksheet components (charts, drawings, comments, etc.).
- Ensured proper handling of printer settings and other worksheet relationships.
  • Loading branch information
mxsrm committed Dec 22, 2024
1 parent 4dcea0e commit 72faf4f
Show file tree
Hide file tree
Showing 2 changed files with 89 additions and 106 deletions.
1 change: 0 additions & 1 deletion src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -138,7 +138,6 @@
variant_size_differences
)]
#![allow(dead_code)]

#![deny(clippy::correctness)]
#![warn(
clippy::style,
Expand Down
194 changes: 89 additions & 105 deletions src/writer/xlsx.rs
Original file line number Diff line number Diff line change
Expand Up @@ -35,139 +35,123 @@ mod worksheet;
mod worksheet_rels;

fn make_buffer(spreadsheet: &Spreadsheet, is_light: bool) -> Result<Vec<u8>, XlsxError> {
let mut arv = zip::ZipWriter::new(io::Cursor::new(Vec::new()));
let cursor = io::Cursor::new(Vec::new());
let mut arv = zip::ZipWriter::new(cursor);
let mut writer_manager = WriterManager::new(&mut arv);
writer_manager.set_is_light(is_light);

// Add docProps App
// Add docProps
doc_props_app::write(spreadsheet, &mut writer_manager)?;

// Add docProps Core
doc_props_core::write(spreadsheet, &mut writer_manager)?;

// Add docProps Custom
doc_props_custom::write(spreadsheet, &mut writer_manager)?;

// Add vbaProject.bin
vba_project_bin::write(spreadsheet, &mut writer_manager)?;

// Add relationships
rels::write(spreadsheet, &mut writer_manager)?;

// Add theme
theme::write(spreadsheet.get_theme(), &mut writer_manager)?;

// worksheet
let shared_string_table = spreadsheet.get_shared_string_table();
let mut stylesheet = spreadsheet.get_stylesheet().clone();
let mut worksheet_no = 1;
for worksheet in spreadsheet.get_sheet_collection_no_check() {
if worksheet.is_deserialized() {
// from deserialized.
worksheet::write(
worksheet_no,

// Process each worksheet
spreadsheet.get_sheet_collection_no_check().iter().enumerate().try_for_each(
|(index, worksheet)| {
let worksheet_no = index + 1;
if worksheet.is_deserialized() {
worksheet::write(
worksheet_no as i32,
worksheet,
shared_string_table.clone(),
&mut stylesheet,
spreadsheet.get_has_macros(),
&mut writer_manager,
)
} else {
worksheet
.get_raw_data_of_worksheet()
.write(worksheet_no as i32, &mut writer_manager)
}
},
)?;

// Process objects associated with worksheets
spreadsheet.get_sheet_collection_no_check().iter().enumerate().try_for_each(
|(index, worksheet)| {
let worksheet_no = index + 1;
if !worksheet.is_deserialized() {
return Ok(());
}

// Add charts
let chart_no_list: Result<Vec<String>, XlsxError> = worksheet
.get_worksheet_drawing()
.get_chart_collection()
.iter()
.map(|chart| {
chart::write(chart.get_chart_space(), spreadsheet, &mut writer_manager)
})
.collect();

let chart_no_list = chart_no_list?;

// Add drawing and its relationships
let (drawing_no, rel_list) = drawing::write(worksheet, &mut writer_manager)?;
drawing_rels::write(
worksheet,
shared_string_table.clone(),
&mut stylesheet,
spreadsheet.get_has_macros(),
&drawing_no,
&chart_no_list,
&rel_list,
&mut writer_manager,
)?;
} else {
// from no deserialized.
worksheet.get_raw_data_of_worksheet().write(worksheet_no, &mut writer_manager)?;
}
worksheet_no += 1;
}

// Objects associated with worksheets
let mut worksheet_no = 0;
for worksheet in spreadsheet.get_sheet_collection_no_check() {
worksheet_no += 1;
if !worksheet.is_deserialized() {
continue;
}
// Add vml drawing and its relationships
let (vml_drawing_no, rel_list) = vml_drawing::write(worksheet, &mut writer_manager)?;
vml_drawing_rels::write(worksheet, &vml_drawing_no, &rel_list, &mut writer_manager)?;

// from deserialized.
// Add charts
let mut chart_no_list: Vec<String> = Vec::new();
for chart in worksheet.get_worksheet_drawing().get_chart_collection() {
let chart_space = chart.get_chart_space();
let chart_no = chart::write(chart_space, spreadsheet, &mut writer_manager)?;
chart_no_list.push(chart_no);
}
// Add comments
let comment_no = comment::write(worksheet, &mut writer_manager)?;

// Add drawing
let (drawing_no, rel_list) = drawing::write(worksheet, &mut writer_manager)?;

// Add drawing rels
drawing_rels::write(
worksheet,
&drawing_no,
&chart_no_list,
&rel_list,
&mut writer_manager,
)?;

// Add vml drawing
let (vml_drawing_no, rel_list) = vml_drawing::write(worksheet, &mut writer_manager)?;

// Add vml drawing rels
vml_drawing_rels::write(worksheet, &vml_drawing_no, &rel_list, &mut writer_manager)?;

// Add comment
let comment_no = comment::write(worksheet, &mut writer_manager)?;

// Add ole_object and excel
let (ole_object_no_list, excel_no_list) =
embeddings::write(worksheet, &mut writer_manager)?;

// Add Media
media::write(worksheet, &mut writer_manager)?;

// Add printer_settings
let printer_settings_no = match worksheet.get_page_setup().get_object_data() {
Some(_) => printer_settings::write(worksheet, &mut writer_manager)?,
None => String::new(),
};

// Add tables
let table_no_list = table::write(worksheet, &mut writer_manager)?;

// Add worksheet rels
worksheet_rels::write(
worksheet,
&worksheet_no.to_string(),
&drawing_no,
&vml_drawing_no,
&comment_no,
&ole_object_no_list,
&excel_no_list,
&printer_settings_no,
&table_no_list,
&mut writer_manager,
)?;
}
// Add ole_object and excel
let (ole_object_no_list, excel_no_list) =
embeddings::write(worksheet, &mut writer_manager)?;

// file list sort
writer_manager.file_list_sort();
// Add Media
media::write(worksheet, &mut writer_manager)?;

// Add SharedStrings
shared_strings::write(shared_string_table.clone(), &mut writer_manager)?;
// Add printer settings
let printer_settings_no =
worksheet.get_page_setup().get_object_data().map_or_else(String::new, |_| {
printer_settings::write(worksheet, &mut writer_manager).unwrap_or_default()
});

// Add Styles
styles::write(&stylesheet, &mut writer_manager)?;
// Add tables
let table_no_list = table::write(worksheet, &mut writer_manager)?;

// Add worksheet relationships
worksheet_rels::write(
worksheet,
&worksheet_no.to_string(),
&drawing_no,
&vml_drawing_no,
&comment_no,
&ole_object_no_list,
&excel_no_list,
&printer_settings_no,
&table_no_list,
&mut writer_manager,
)
},
)?;

// Add workbook
// Finalize file list and add remaining components
writer_manager.file_list_sort();
shared_strings::write(shared_string_table.clone(), &mut writer_manager)?;
styles::write(&stylesheet, &mut writer_manager)?;
workbook::write(spreadsheet, &mut writer_manager)?;

// Add workbook relationships
let has_shared_string_table = shared_string_table.read().unwrap().has_value();
workbook_rels::write(spreadsheet, has_shared_string_table, &mut writer_manager)?;

// Add Content_Types
content_types::write(spreadsheet, &mut writer_manager)?;

Ok(arv.finish()?.into_inner())
arv.finish().map(|cursor| cursor.into_inner()).map_err(Into::into)
}

/// write spreadsheet file to arbitrary writer.
Expand Down

0 comments on commit 72faf4f

Please sign in to comment.