test: add unique flatten test (#995)

This commit is contained in:
Matthias Seitz 2022-03-08 15:46:04 +01:00 committed by GitHub
parent 1641be7395
commit fab30887a2
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 60 additions and 10 deletions

View File

@ -10,6 +10,7 @@ use crate::{
use crate::artifacts::output_selection::ContractOutputSelection; use crate::artifacts::output_selection::ContractOutputSelection;
use serde::{Deserialize, Serialize}; use serde::{Deserialize, Serialize};
use std::{ use std::{
collections::HashSet,
fmt::{self, Formatter}, fmt::{self, Formatter},
fs, fs,
path::{Component, Path, PathBuf}, path::{Component, Path, PathBuf},
@ -229,7 +230,7 @@ impl ProjectPathsConfig {
pub fn flatten(&self, target: &Path) -> Result<String> { pub fn flatten(&self, target: &Path) -> Result<String> {
tracing::trace!("flattening file"); tracing::trace!("flattening file");
let graph = Graph::resolve(self)?; let graph = Graph::resolve(self)?;
self.flatten_node(target, &graph, &mut vec![], false, false) self.flatten_node(target, &graph, &mut Default::default(), false, false)
} }
/// Flattens a single node from the dependency graph /// Flattens a single node from the dependency graph
@ -237,7 +238,7 @@ impl ProjectPathsConfig {
&self, &self,
target: &Path, target: &Path,
graph: &Graph, graph: &Graph,
imported: &mut Vec<usize>, imported: &mut HashSet<usize>,
strip_version_pragma: bool, strip_version_pragma: bool,
strip_license: bool, strip_license: bool,
) -> Result<String> { ) -> Result<String> {
@ -248,9 +249,11 @@ impl ProjectPathsConfig {
SolcError::msg(format!("cannot resolve file at \"{:?}\"", target.display())) SolcError::msg(format!("cannot resolve file at \"{:?}\"", target.display()))
})?; })?;
if imported.iter().any(|&idx| idx == *target_index) { if imported.contains(target_index) {
// short circuit nodes that were already imported, if both A.sol and B.sol import C.sol
return Ok(String::new()) return Ok(String::new())
} }
imported.insert(*target_index);
let target_node = graph.node(*target_index); let target_node = graph.node(*target_index);
@ -278,21 +281,17 @@ impl ProjectPathsConfig {
for import in imports.iter() { for import in imports.iter() {
let import_path = self.resolve_import(target_dir, import.data())?; let import_path = self.resolve_import(target_dir, import.data())?;
let import_content = self let s = self.flatten_node(&import_path, graph, imported, true, true)?;
.flatten_node(&import_path, graph, imported, true, true)? let import_content = s.trim().as_bytes();
.trim()
.as_bytes()
.to_owned();
let import_content_len = import_content.len() as isize; let import_content_len = import_content.len() as isize;
let (start, end) = import.loc_by_offset(offset); let (start, end) = import.loc_by_offset(offset);
content.splice(start..end, import_content); content.splice(start..end, import_content.iter().copied());
offset += import_content_len - ((end - start) as isize); offset += import_content_len - ((end - start) as isize);
} }
let result = String::from_utf8(content).map_err(|err| { let result = String::from_utf8(content).map_err(|err| {
SolcError::msg(format!("failed to convert extended bytes to string: {}", err)) SolcError::msg(format!("failed to convert extended bytes to string: {}", err))
})?; })?;
imported.push(*target_index);
Ok(result) Ok(result)
} }

View File

@ -417,6 +417,57 @@ fn can_flatten_file_in_dapp_sample() {
assert!(result.contains("contract DappTest")); assert!(result.contains("contract DappTest"));
} }
#[test]
fn can_flatten_unique() {
let project = TempProject::dapptools().unwrap();
let f = project
.add_source(
"A",
r#"
pragma solidity ^0.8.10;
import "./C.sol";
import "./B.sol";
contract A { }
"#,
)
.unwrap();
project
.add_source(
"B",
r#"
pragma solidity ^0.8.10;
import "./C.sol";
contract B { }
"#,
)
.unwrap();
project
.add_source(
"C",
r#"
pragma solidity ^0.8.10;
import "./A.sol";
contract C { }
"#,
)
.unwrap();
let result = project.flatten(&f).unwrap();
assert_eq!(
result,
r#"
pragma solidity ^0.8.10;
contract C { }
contract B { }
contract A { }
"#
);
}
#[test] #[test]
fn can_flatten_file_with_duplicates() { fn can_flatten_file_with_duplicates() {
let root = PathBuf::from(env!("CARGO_MANIFEST_DIR")).join("test-data/test-flatten-duplicates"); let root = PathBuf::from(env!("CARGO_MANIFEST_DIR")).join("test-data/test-flatten-duplicates");