const { writeFile , readFile , unlink } = require ( "fs" ) ; const tmp = require ( "tmp" ) ; const { callback } = require ( "awaiting" ) ; const { spawn } = require ( "child_process" ) ; import { Options } from "./index" ; function close ( proc , cb ) { proc . on ( "close" , ( code ) => cb ( undefined , code ) ) ; } function run_clang_format ( input_path , indent ) { const style = `-style={BasedOnStyle: google, IndentWidth: ${ indent }}` ; const args = [ "--sort-includes=0" , "-i" , style , input_path ] ; return spawn ( "clang-format" , args ) ; } export async function clang_format ( input , ext , options , logger ) { const input_path = await callback ( tmp . file , { postfix : `.${ ext }` } ) ; try { await callback ( writeFile , input_path , input ) ; let formatter ; const indent = options . tabWidth || 2 ; switch ( options . parser ) { case "clang-format" : formatter = run_clang_format ( input_path , indent ) ; break ; default : throw Error ( `Unknown C/C++ code formatting utility '${ options . parser }'` ) ; } let stdout = "" ; let stderr = "" ; formatter . stdout . on ( "data" , ( data ) => ( stdout += data . toString ( ) ) ) ; formatter . stderr . on ( "data" , ( data ) => ( stderr += data . toString ( ) ) ) ; const code = await callback ( close , formatter ) ; if ( code >= 1 ) { const err_msg = `C/C++ code formatting utility "${ options . parser }" exited with code ${ code }\nOutput:\n${ stdout }\n${ stderr }` ; logger . debug ( `clang-format error: ${ err_msg }` ) ; throw Error ( err_msg ) ; } const output = await callback ( readFile , input_path ) ; const s = output . toString ( "utf-8" ) ; return s ; } finally { unlink ( input_path , ( ) => { } ) ; } }