Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ Apache 2.0 - see LICENSE

### COMPILATION REQUIREMENTS
* Visual Studio 2010
* .NET Framewrok 4.0
* .NET Framework 4.0
* NuGet Package Manager with "Allow NuGet to download missing packages" setting enabled

### SYNTAX
Expand Down
4 changes: 4 additions & 0 deletions src/ChocolateStore/Arguments.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,11 @@
{
class Arguments
{
// where the packages are saved and referenced
public string Directory { get; set; }
//where to download the package from
public string Url { get; set; }
// where to save the packages
public string CacheDir { get; set; }
}
}
193 changes: 98 additions & 95 deletions src/ChocolateStore/PackageCacher.cs
Original file line number Diff line number Diff line change
@@ -1,101 +1,104 @@
using System;
using System.IO;
using System.Linq;
using System.Net;
using System.Text;
using System.Text.RegularExpressions;
using Ionic.Zip;

namespace ChocolateStore
{
class PackageCacher
{

private const string INSTALL_FILE = "tools/chocolateyInstall.ps1";

public delegate void FileHandler(string fileName);
public delegate void DownloadFailedHandler(string url, Exception ex);

public event FileHandler SkippingFile = delegate { };
public event FileHandler DownloadingFile = delegate { };
public event DownloadFailedHandler DownloadFailed = delegate { };

public void CachePackage(string dir, string url)
{
var packagePath = DownloadFile(url, dir);

using (var zip = ZipFile.Read(packagePath))
{
var entry = zip.FirstOrDefault(x => string.Equals(x.FileName, INSTALL_FILE, StringComparison.OrdinalIgnoreCase));

if (entry != null) {
string content = null;
var packageName = Path.GetFileNameWithoutExtension(packagePath);

using (MemoryStream ms = new MemoryStream()) {
using System;
using System.IO;
using System.Linq;
using System.Net;
using System.Text;
using System.Text.RegularExpressions;
using Ionic.Zip;
namespace ChocolateStore
{
class PackageCacher
{
private const string INSTALL_FILE = "tools/chocolateyInstall.ps1";
public delegate void FileHandler(string fileName);
public delegate void DownloadFailedHandler(string url, Exception ex);
public event FileHandler SkippingFile = delegate { };
public event FileHandler DownloadingFile = delegate { };
public event DownloadFailedHandler DownloadFailed = delegate { };
public void CachePackage(string dir, string url, string cachedir)
{
var packagePath = DownloadFile(url, cachedir, cachedir);
using (var zip = ZipFile.Read(packagePath))
{
var entry = zip.FirstOrDefault(x => string.Equals(x.FileName, INSTALL_FILE, StringComparison.OrdinalIgnoreCase));
if (entry != null) {
string content = null;
var packageName = Path.GetFileNameWithoutExtension(packagePath);
using (MemoryStream ms = new MemoryStream()) {
entry.Extract(ms);
ms.Position = 0;
using (StreamReader reader = new StreamReader(ms, true))
{
content = reader.ReadToEnd();
}
}

content = CacheUrlFiles(Path.Combine(dir, packageName), content);
zip.UpdateEntry(INSTALL_FILE, content);
zip.Save();

}

}

}

private string CacheUrlFiles(string folder, string content)
{

const string pattern = "(?<=['\"])http[\\S ]*(?=['\"])";

if (!Directory.Exists(folder)) {
Directory.CreateDirectory(folder);
}

return Regex.Replace(content, pattern, new MatchEvaluator(m => DownloadFile(m.Value, folder)));

}

private string DownloadFile(string url, string destination)
{

try
{
var request = WebRequest.Create(url);
var response = request.GetResponse();
var fileName = Path.GetFileName(response.ResponseUri.LocalPath);
var filePath = Path.Combine(destination, fileName);

if (File.Exists(filePath))
{
SkippingFile(fileName);
}
else
{
DownloadingFile(fileName);
using (var fs = File.Create(filePath))
{
response.GetResponseStream().CopyTo(fs);
}
}

return filePath;
}
catch (Exception ex)
{
DownloadFailed(url, ex);
return url;
}

}

}
}
}

content = CacheUrlFiles(Path.Combine(dir, packageName), content, Path.Combine(cachedir, packageName));
zip.UpdateEntry(INSTALL_FILE, content);
zip.Save();

}

}

}

private string CacheUrlFiles(string folder, string content, string cachedir)
{

const string pattern = "(?<=['\"])http[\\S ]*(?=['\"])";

if (!Directory.Exists(cachedir)) {
Directory.CreateDirectory(cachedir);
}

return Regex.Replace(content, pattern, new MatchEvaluator(m => DownloadFile(m.Value, cachedir, folder)));

}

// the third parameter is used as return value for the matcher,
// the file is downloaded at destination
private string DownloadFile(string url, string destination, string store)
{

try
{
var request = WebRequest.Create(url);
var response = request.GetResponse();
var fileName = Path.GetFileName(response.ResponseUri.LocalPath);
var filePath = Path.Combine(destination, fileName);

if (File.Exists(filePath))
{
SkippingFile(fileName);
}
else
{
DownloadingFile(fileName);
using (var fs = File.Create(filePath))
{
response.GetResponseStream().CopyTo(fs);
}
}

return Path.Combine(store, fileName);
}
catch (Exception ex)
{
DownloadFailed(url, ex);
return url;
}

}

}
}

21 changes: 15 additions & 6 deletions src/ChocolateStore/Program.cs
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ static void Main(string[] args)

if (arguments != null)
{
cacher.CachePackage(arguments.Directory, arguments.Url);
cacher.CachePackage(arguments.Directory, arguments.Url, arguments.CacheDir);
}

}
Expand All @@ -37,17 +37,26 @@ private static Arguments ParseArguments(string[] args)

Arguments arguments = new Arguments();

if (args.Length != 2)
{
WriteError("USAGE: ChocolateStore <directory> <url>");
if (args.Length != 2 && args.Length != 3 )
{
WriteError("USAGE: ChocolateStore <directory> <url> <optional: store directory>");
return null;
}

arguments.Directory = args[0];

if (!Directory.Exists(arguments.Directory))
if (args.Length == 3)
{
arguments.CacheDir = args[2];
}
else
{
arguments.CacheDir = arguments.Directory;
}

if (!Directory.Exists(arguments.CacheDir))
{
WriteError("Directory '{0}' does not exist.", arguments.Directory);
WriteError("Directory '{0}' does not exist.", arguments.CacheDir);
return null;
}

Expand Down