pakx_core/lockfile/
parse.rs1use std::path::Path;
4
5use crate::errors::LockfileError;
6
7use super::schema::{is_valid_entry_key, Lockfile, LOCKFILE_VERSION};
8
9pub fn parse_lockfile(source: &str, path: Option<&Path>) -> Result<Lockfile, LockfileError> {
12 let lockfile: Lockfile =
13 serde_json::from_str(source).map_err(|source| LockfileError::ParseJson {
14 source,
15 path: path.map(Path::to_path_buf),
16 })?;
17
18 if lockfile.lockfile_version != LOCKFILE_VERSION {
19 return Err(LockfileError::Schema {
20 message: format!(
21 "unsupported lockfileVersion {} (this build understands {LOCKFILE_VERSION})",
22 lockfile.lockfile_version
23 ),
24 path: path.map(Path::to_path_buf),
25 });
26 }
27
28 for key in lockfile.entries.keys() {
29 if !is_valid_entry_key(key) {
30 return Err(LockfileError::Schema {
31 message: format!("invalid entry key {key:?}: must match `<type>/<id>@<version>`"),
32 path: path.map(Path::to_path_buf),
33 });
34 }
35 }
36
37 for dep_key in lockfile.entries.values().flat_map(|e| &e.dependencies) {
38 if !is_valid_entry_key(dep_key) {
39 return Err(LockfileError::Schema {
40 message: format!(
41 "invalid transitive dependency key {dep_key:?}: must match `<type>/<id>@<version>`"
42 ),
43 path: path.map(Path::to_path_buf),
44 });
45 }
46 }
47
48 Ok(lockfile)
49}