valor-interview
Version:
CLI tool for downloading Valor interview challenges
5 lines (4 loc) • 7.18 kB
JavaScript
;var W=Object.create;var P=Object.defineProperty;var z=Object.getOwnPropertyDescriptor;var j=Object.getOwnPropertyNames;var q=Object.getPrototypeOf,V=Object.prototype.hasOwnProperty;var X=(e,t,o,i)=>{if(t&&typeof t=="object"||typeof t=="function")for(let r of j(t))!V.call(e,r)&&r!==o&&P(e,r,{get:()=>t[r],enumerable:!(i=z(t,r))||i.enumerable});return e};var h=(e,t,o)=>(o=e!=null?W(q(e)):{},X(t||!e||!e.__esModule?P(o,"default",{value:e,enumerable:!0}):o,e));var B=require("path");var g=require("fs-extra"),E=require("path"),A=h(require("ora"));var a={CHALLENGES_REPO_URL:"https://github.com/ryok90/valor-interview.git",PATHS:{CHALLENGES_DIR:"challenges",TEMP_DIR_PREFIX:"valor-challenges-"},GIT:{DEFAULT_BRANCH:"main",CLONE_DEPTH:1},GITHUB:{API_BASE:"https://api.github.com",RAW_BASE:"https://raw.githubusercontent.com"},FEATURES:{USE_SPARSE_CHECKOUT:!0,FILTER_NODE_MODULES:!0}};var p=class extends Error{constructor(o,i,r){super(o);this.statusCode=i;this.response=r;this.name="GitHubApiError"}},K=e=>{let t=e.match(/github\.com[/:]([^/]+)\/([^/.]+)(?:\.git)?/);if(!t)throw new Error(`Invalid GitHub repository URL: ${e}`);return{owner:t[1],repo:t[2],branch:a.GIT.DEFAULT_BRANCH}},I=async(e,t=a.PATHS.CHALLENGES_DIR)=>{let{owner:o,repo:i,branch:r}=K(e),s=`${a.GITHUB.API_BASE}/repos/${o}/${i}/contents/${t}?ref=${r}`;try{let n=await fetch(s);if(!n.ok)throw n.status===404?new p(`Challenges directory '${t}' not found in repository`,404,n):new p(`GitHub API request failed: ${n.status} ${n.statusText}`,n.status,n);return(await n.json()).filter(u=>u.type==="dir").map(u=>({name:u.name,path:`${t}/${u.name}`,description:`Challenge: ${u.name}`}))}catch(n){throw n instanceof p?n:new p(`Failed to fetch challenges from GitHub API: ${n instanceof Error?n.message:String(n)}`)}},y=e=>/github\.com[/:]/.test(e);var Y=async e=>{if(!y(e))throw new Error("API scanning only supports GitHub repositories");return await I(e,a.PATHS.CHALLENGES_DIR)};var $=async e=>{if(!y(e))throw new Error("Only GitHub repositories are supported for challenge scanning");return await Y(e)},x=async({source:e,destination:t,overwrite:o=!0})=>{let i=(0,A.default)("Copying challenge files...").start();try{o&&await(0,g.pathExists)(t)&&await(0,g.remove)(t);let r=a.FEATURES.FILTER_NODE_MODULES?s=>!s.includes("node_modules"):void 0;return await(0,g.copy)(e,t,{overwrite:o,filter:r}),i.succeed(`Challenge copied to: ${t}`),t}catch(r){throw i.fail("Failed to copy challenge"),r}},G=e=>!!e?.trim(),R=e=>(0,E.resolve)(e.trim()||process.cwd());var w=h(require("inquirer"));var H=async e=>{if(e.length===0)throw new Error("No challenges available for selection");let{selectedChallenge:t}=await w.default.prompt([{type:"list",name:"selectedChallenge",message:"Which challenge would you like to download?",choices:e.map(o=>({name:`${o.name}${o.description?` - ${o.description}`:""}`,value:o,short:o.name})),pageSize:Math.min(e.length,10)}]);return t},T=async()=>{let{destinationPath:e}=await w.default.prompt([{type:"input",name:"destinationPath",message:"Where would you like to copy the challenge? (Press Enter for current directory)",default:process.cwd(),validate:t=>G(t)?!0:"Please provide a valid path",filter:R}]);return e},F=async()=>{let{installDeps:e}=await w.default.prompt([{type:"confirm",name:"installDeps",message:"Would you like to install dependencies?",default:!0}]);return e};var b=require("child_process"),D=h(require("ora")),c=(e,t,o={})=>new Promise((i,r)=>{let s=(0,b.spawn)(e,t,{cwd:o.cwd,stdio:o.stdio||"pipe"});s.on("close",n=>{n===0?i():r(new Error(`Command '${e} ${t.join(" ")}' failed with exit code ${n}`))}),s.on("error",n=>{r(new Error(`Failed to execute command '${e}': ${n.message}`))})}),S=async({cwd:e,packageManager:t="pnpm"})=>{let o=(0,D.default)(`Installing dependencies with ${t}...`).start();try{await c(t,["install"],{cwd:e}),o.succeed("Dependencies installed successfully")}catch(i){throw o.fail(`Failed to install dependencies with ${t}`),i}},J=async e=>{try{return await c(e,["--version"]),!0}catch{return!1}},v=async()=>{let e=["pnpm","yarn","npm"];for(let t of e)if(await J(t))return t;return"npm"};var l=h(require("chalk")),_=()=>{console.log(l.default.blue.bold("\u{1F3AF} Valor Challenges CLI")),console.log(l.default.gray(`Download and setup interview challenges
`))},Q=e=>{console.log(l.default.green.bold(`\u2705 ${e}`))},Z=e=>{console.log(l.default.gray(`\u{1F4C1} ${e}`))},L=e=>{console.log(l.default.yellow(`\u26A0\uFE0F ${e}`))},d=(e,t)=>{if(console.error(l.default.red("\u274C Error:"),e),t){let o=t instanceof Error?t.message:String(t);console.error(l.default.red(o))}},O=(e,t)=>{Q("Challenge setup complete!"),Z(`Challenge location: ${e}`),console.log(t?l.default.gray("\u{1F389} Dependencies installed and ready to go!"):l.default.gray("\u{1F4A1} Don't forget to run `pnpm install` in the challenge directory"))};var m=require("fs-extra"),f=require("path"),N=require("os"),C=h(require("ora"));var ee=async()=>await(0,m.mkdtemp)((0,f.join)((0,N.tmpdir)(),a.PATHS.TEMP_DIR_PREFIX));var te=async e=>{try{await(0,m.remove)(e)}catch(t){console.warn(`Warning: Failed to cleanup temporary directory ${e}:`,t instanceof Error?t.message:String(t))}},oe=async(e,t,o,i=a.GIT.DEFAULT_BRANCH)=>{let r=(0,C.default)(`Cloning challenge: ${o}...`).start();try{await c("git",["init"],{cwd:t}),await c("git",["remote","add","origin",e],{cwd:t}),await c("git",["config","core.sparseCheckout","true"],{cwd:t});let s=(0,f.join)(t,".git","info");await(0,m.ensureDir)(s),await(0,m.writeFile)((0,f.join)(s,"sparse-checkout"),`${o}/*
`,"utf8"),await c("git",["pull","origin",i,"--depth",String(a.GIT.CLONE_DEPTH)],{cwd:t}),r.succeed(`Challenge cloned: ${o}`)}catch(s){throw r.fail("Failed to clone challenge"),new Error(`Sparse checkout failed: ${s instanceof Error?s.message:String(s)}`)}};var U=async(e,t,o,i)=>{let r=await ee();try{await oe(e,r,t,i);let s=(0,f.join)(r,t);return await o(s)}finally{await te(r)}},k=async e=>{let t=(0,C.default)("Initializing git repository...").start();try{await c("git",["init"],{cwd:e}),await c("git",["add","."],{cwd:e}),await c("git",["commit","-m","Initial commit"],{cwd:e}),t.succeed("Git repository initialized successfully")}catch{t.fail("Failed to initialize git repository"),console.warn("Warning: Failed to initialize git repository. You may need to set up git manually.")}};var re=async()=>{_();try{let e=a.CHALLENGES_REPO_URL,t=await $(e);if(t.length===0){L("No challenges found in the repository.");return}let o=await H(t),i=await T(),r=(0,B.join)(i,o.name);await U(e,o.path,async n=>{await x({source:n,destination:r,overwrite:!0})}),await k(r);let s=await F();if(s){let n=await v();await S({cwd:r,packageManager:n})}O(r,s)}catch(e){M(e)}},M=e=>{e instanceof p?e.statusCode===404?d('Repository or challenges directory not found. Please check the repository URL and ensure it contains a "challenges" directory.'):e.statusCode===403?d("Access denied to the repository. Please check if the repository is public or if you have access."):d("Failed to fetch challenges from GitHub API",e):e instanceof Error?d("Failed to setup challenge",e):d("An unexpected error occurred",e),process.exit(1)};re().catch(M);