Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Fix #2 - Improve async handling - Add progress bar - Add custom text message option
- Loading branch information
1 parent
eadee49
commit 1c4ad29
Showing
7 changed files
with
162 additions
and
134 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,48 @@ | ||
// @ts-ignore | ||
import ProgressBar from 'progress' | ||
|
||
export default function addProgressBar( | ||
text: string, | ||
completionCallback: () => Promise<void> | ||
): Promise<void> { | ||
return new Promise<void>(async (resolve, reject) => { | ||
const contentLength = 2048 * 1024 // 2MB | ||
const bar = new ProgressBar(`${text} [:bar] :percent :etas`, { | ||
complete: '=', | ||
incomplete: ' ', | ||
width: 50, | ||
total: contentLength | ||
}) | ||
|
||
// Simulate progress | ||
let progress = 0 | ||
|
||
const timer = setInterval(() => { | ||
const chunk = Math.random() * 10 * 1024 | ||
progress += chunk | ||
bar.tick(chunk) | ||
if (progress >= contentLength || bar.complete) { | ||
// Clear interval when progress is complete | ||
clearInterval(timer) | ||
} | ||
}, 50) | ||
|
||
try { | ||
// Wait for the cloning operation to complete | ||
await completionCallback() | ||
|
||
// Ensure the interval is cleared after operation completes | ||
clearInterval(timer) | ||
|
||
// Force-complete the progress bar | ||
bar.tick(contentLength) | ||
resolve() | ||
} catch (error) { | ||
// Ensure the interval is cleared in case of error | ||
clearInterval(timer) | ||
|
||
console.error('[go-git-it] An error occurred:', error) | ||
reject(error) | ||
} | ||
}) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,50 +1,49 @@ | ||
import path from 'path' | ||
import util from 'util' | ||
import shell from 'shelljs' | ||
import pullSource from './pullSource' | ||
|
||
const exec = util.promisify(shell.exec) | ||
|
||
interface DownloadMainRepo { | ||
owner: string | ||
project: string | ||
} | ||
|
||
export default function downloadMainRepo( | ||
export default async function downloadMainRepo( | ||
outputDirectory: string, | ||
options: DownloadMainRepo | ||
{owner, project}: DownloadMainRepo | ||
) { | ||
const {owner, project} = options | ||
shell.mkdir('-p', path.join(outputDirectory, project)) | ||
shell.cd(path.join(outputDirectory, project)) | ||
shell.exec('git init --quiet') | ||
shell.exec(`git remote add origin https://github.com/${owner}/${project}`) | ||
|
||
// User is in the project root directory, try pulling from `main` | ||
shell.exec(pullSource('main')) | ||
|
||
// Nothing added on `main`, try the old `master` | ||
const pullExit = shell.exec(`[ "$(ls -A .)" ] || ${pullSource('master')}`) | ||
|
||
// Nothing added. We need a branch so we exit with error | ||
const errorMessage = | ||
'No default branch found. Ensure you are pulling from `main` or `master` branch.' | ||
const projectPath = path.join(outputDirectory, project) | ||
shell.mkdir('-p', projectPath) | ||
shell.cd(projectPath) | ||
await exec('git init --quiet') | ||
await exec(`git remote add origin https://github.com/${owner}/${project}`) | ||
|
||
// Try to pull from 'main' first, then fallback to 'master' | ||
const branches = ['main', 'master'] | ||
let success = false | ||
|
||
for (const branch of branches) { | ||
try { | ||
await exec(pullSource(branch)) | ||
success = true | ||
console.log(`Successfully pulled from branch '${branch}'.`) | ||
break // Exit the loop on success | ||
} catch (error) { | ||
console.log( | ||
`Failed to pull using branch '${branch}'. Trying next option...` | ||
) | ||
} | ||
} | ||
|
||
const copyExit = shell.exec(`[ "$(ls -A .)" ] || echo ${errorMessage}`) | ||
if (!success) { | ||
console.error( | ||
'Error: Could not determine the default branch or failed to pull from it.' | ||
) | ||
process.exit(1) | ||
} | ||
|
||
// Remove the git folder as we don't need it | ||
// Clean up .git directory | ||
shell.rm('-rf', '.git') | ||
|
||
// Git data pull failed | ||
if (pullExit.code !== 0) { | ||
console.log('Error when trying to pull git data', pullExit.stderr) | ||
process.exit(pullExit.code) | ||
|
||
// The attempt to copy files failed | ||
} else if (copyExit.code !== 0) { | ||
console.log('Error when trying to copy git data', copyExit.stderr) | ||
process.exit(copyExit.code) | ||
|
||
// All good, project downloaded | ||
} else { | ||
console.log('') | ||
console.log(`Success! \`${project}\` downloaded to \`${outputDirectory}\`.`) | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,76 +1,42 @@ | ||
import path from 'path' | ||
import fs from 'fs' | ||
import util from 'util' | ||
import shell from 'shelljs' | ||
import pullSource from './pullSource' | ||
|
||
export default function downloadPartialRepo( | ||
const exec = util.promisify(shell.exec) | ||
|
||
export default async function downloadPartialRepo( | ||
outputDirectory: string, | ||
options: any | ||
{owner, project, filePath, branch}: any | ||
) { | ||
const {owner, project, filePath, branch} = options | ||
|
||
// Use sparse checkout to grab contents of a specific folders | ||
const tempDownloadName = '.go-git-it-temp-folder' | ||
|
||
// Create a temp directory to add a git repo. This is needed | ||
// so we can have the right config when pulling data, as we only | ||
// want the specific folder path defined by user. | ||
shell.mkdir('-p', path.join(outputDirectory, tempDownloadName)) | ||
shell.cd(path.join(outputDirectory, tempDownloadName)) | ||
const tempDownloadName = '.go-git-it-temp-folder' | ||
|
||
// Start git | ||
shell.exec('git init --quiet') | ||
const tempDownloadPath = path.join(outputDirectory, tempDownloadName) | ||
|
||
// Add sparse checkout to git so we can download specific files only | ||
shell.exec(`git remote add origin https://github.com/${owner}/${project}`) | ||
shell.mkdir('-p', tempDownloadPath) | ||
shell.cd(tempDownloadPath) | ||
|
||
shell.exec('git config core.sparsecheckout true') | ||
await exec('git init --quiet') | ||
await exec(`git remote add origin https://github.com/${owner}/${project}`) | ||
|
||
// Assume a dot in the filePath means a file and not a folder | ||
const isFile = filePath | ||
.split('/') | ||
[filePath.split('/').length - 1].includes('.') | ||
await exec('git config core.sparseCheckout true') | ||
|
||
const isFile = filePath.includes('.') | ||
const sparsePath = isFile ? filePath : `${filePath}/*` | ||
|
||
// Write to git the asset path user is trying to download | ||
shell.exec(`echo ${sparsePath} >> .git/info/sparse-checkout`) | ||
|
||
// User is in the project root directory, try pulling from `main` | ||
shell.exec(pullSource(branch)) | ||
|
||
// Nothing added on `main`, try the old `master` | ||
const pullExit = shell.exec(pullSource(branch)) | ||
|
||
// Move assets to the final output directory | ||
shell.mv(filePath, '..') | ||
|
||
// Go back to root directory so we can delete the temp folder | ||
shell.cd('..') | ||
|
||
// Remove the temp folder | ||
shell.rm('-rf', tempDownloadName) | ||
|
||
// Git data pull failed | ||
if (pullExit.code !== 0) { | ||
// Nothing added. We need a branch so we exit with error | ||
const errorMessage = | ||
'No branch found. Ensure the remote branch you are pulling exists.\n' + | ||
'If you think this is a bug, please report to ' + | ||
'https://github.com/cezaraugusto/go-git-it/issues.\n' + | ||
`Error: ${pullExit.stderr}` | ||
|
||
console.log(errorMessage) | ||
process.exit(pullExit.code) | ||
// All good, project downloaded | ||
} else { | ||
const filePathArray = filePath.split('/') | ||
const asset = filePathArray[filePathArray.length - 1] | ||
const isDirectory = fs.lstatSync(asset).isDirectory() | ||
const assetType = isDirectory ? 'Folder' : 'File' | ||
|
||
console.log(` | ||
\nSuccess! ${assetType} \`${asset}\` downloaded to \`${outputDirectory}\`. | ||
`) | ||
fs.writeFileSync('.git/info/sparse-checkout', sparsePath) | ||
|
||
try { | ||
await exec(pullSource(branch)) | ||
shell.mv(filePath, path.dirname(tempDownloadPath)) | ||
} catch (error) { | ||
console.error('Error pulling git repository:', error) | ||
process.exit(1) | ||
} finally { | ||
shell.cd('..') | ||
shell.rm('-rf', tempDownloadName) | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.