Skip to content

Commit 25c7909

Browse files
Merge pull request #117 from JakeRoggenbuck/repopulate-page-dir
Full data save on disk
2 parents 3a4520a + c8e4323 commit 25c7909

File tree

2 files changed

+121
-2
lines changed

2 files changed

+121
-2
lines changed

src/record.rs

Lines changed: 75 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
use super::page::PhysicalPage;
22
use pyo3::prelude::*;
3+
use serde::{Deserialize, Serialize};
34
use std::sync::{Arc, Mutex};
45

56
#[derive(Debug, Clone)]
@@ -8,6 +9,61 @@ pub struct RecordAddress {
89
pub offset: i64,
910
}
1011

12+
impl RecordAddress {
13+
pub fn get_metadata(&self) -> RecordAddressMetadata {
14+
RecordAddressMetadata {
15+
// TODO: Get the index of each page
16+
page_index: -1,
17+
offset: self.offset,
18+
}
19+
}
20+
}
21+
22+
#[derive(Debug, Clone, Deserialize, Serialize)]
23+
pub struct RecordAddressMetadata {
24+
// What page (basically the column index)
25+
pub page_index: i64,
26+
27+
pub offset: i64,
28+
}
29+
30+
impl RecordAddressMetadata {
31+
pub fn load_state(&self) -> RecordAddress {
32+
// TODO: Get the actual physical page by reference
33+
let phys_page: PhysicalPage = PhysicalPage::new();
34+
35+
RecordAddress {
36+
page: Arc::new(Mutex::new(phys_page)),
37+
offset: self.offset,
38+
}
39+
}
40+
}
41+
42+
#[derive(Debug, Clone, Deserialize, Serialize)]
43+
pub struct RecordMetadata {
44+
pub rid: i64,
45+
46+
pub addresses: Vec<RecordAddressMetadata>,
47+
}
48+
49+
impl RecordMetadata {
50+
pub fn load_state(&self) -> Record {
51+
let mut rec_addrs = Vec::new();
52+
53+
// Create the RecordAddresses from the metadata
54+
// This eventually gets propagated through load_state
55+
// calls all the way to PageDirectory
56+
for rec_addr in &self.addresses {
57+
rec_addrs.push(rec_addr.load_state());
58+
}
59+
60+
Record {
61+
rid: self.rid,
62+
addresses: Arc::new(Mutex::new(rec_addrs)),
63+
}
64+
}
65+
}
66+
1167
#[derive(Debug, Clone)]
1268
#[pyclass]
1369
pub struct Record {
@@ -19,6 +75,25 @@ pub struct Record {
1975
pub addresses: Arc<Mutex<Vec<RecordAddress>>>,
2076
}
2177

78+
impl Record {
79+
pub fn get_metadata(&self) -> RecordMetadata {
80+
let mut rm = RecordMetadata {
81+
rid: self.rid,
82+
addresses: Vec::new(),
83+
};
84+
85+
let m = self.addresses.lock().unwrap();
86+
let addrs = m.iter();
87+
88+
for addr in addrs {
89+
// Get the metadata for each RecordAddress
90+
rm.addresses.push(addr.get_metadata());
91+
}
92+
93+
return rm;
94+
}
95+
}
96+
2297
#[pymethods]
2398
impl Record {
2499
fn __str__(&self) -> String {

src/table.rs

Lines changed: 46 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,18 @@
11
use super::index::RIndex;
22
use super::pagerange::{PageRange, PageRangeMetadata};
3-
use super::record::Record;
3+
use super::record::{Record, RecordMetadata};
44
use bincode;
55
use pyo3::prelude::*;
66
use serde::{Deserialize, Serialize};
77
use std::collections::HashMap;
88
use std::fs::File;
99
use std::io::{BufReader, BufWriter, Write};
1010

11+
#[derive(Default, Clone, Serialize, Deserialize)]
12+
pub struct PageDirectoryMetadata {
13+
pub directory: HashMap<i64, RecordMetadata>,
14+
}
15+
1116
#[derive(Default, Clone)]
1217
pub struct PageDirectory {
1318
pub directory: HashMap<i64, Record>,
@@ -21,10 +26,47 @@ impl PageDirectory {
2126
}
2227

2328
fn load_state() -> PageDirectory {
24-
PageDirectory::default()
29+
let hardcoded_filename = "./redoxdata/page_directory.data";
30+
31+
let file = BufReader::new(File::open(hardcoded_filename).expect("Should open file."));
32+
let page_meta: PageDirectoryMetadata =
33+
bincode::deserialize_from(file).expect("Should deserialize.");
34+
35+
let mut pd: PageDirectory = PageDirectory {
36+
directory: HashMap::new(),
37+
};
38+
39+
// TODO: We need to somehow load all of the physical pages, wrap them
40+
// in an Arc Mutex, and assign those references to the record addresses
41+
// that need them
42+
//
43+
// We could store the id for where the the physical page it stored on disk
44+
// in the physical, and then we can load all of them up here, assuming we
45+
// have something storing the max page index
46+
47+
for (rid, record_meta) in page_meta.directory {
48+
pd.directory.insert(rid, record_meta.load_state());
49+
}
50+
51+
return pd;
2552
}
2653

2754
fn save_state(&self) {
55+
let hardcoded_filename = "./redoxdata/page_directory.data";
56+
57+
let mut pd_meta = PageDirectoryMetadata {
58+
directory: HashMap::new(),
59+
};
60+
61+
for (rid, record) in &self.directory {
62+
let r: RecordMetadata = record.get_metadata();
63+
pd_meta.directory.insert(*rid, r);
64+
}
65+
66+
let table_bytes: Vec<u8> = bincode::serialize(&pd_meta).expect("Should serialize.");
67+
68+
let mut file = BufWriter::new(File::create(hardcoded_filename).expect("Should open file."));
69+
file.write_all(&table_bytes).expect("Should serialize.");
2870
}
2971
}
3072

@@ -236,6 +278,8 @@ impl RTable {
236278
// Save the state of the page range
237279
self.page_range.save_state();
238280

281+
self.page_directory.save_state();
282+
239283
let table_meta = self.get_metadata();
240284

241285
let table_bytes: Vec<u8> = bincode::serialize(&table_meta).expect("Should serialize.");

0 commit comments

Comments
 (0)