원래 https://github.com/Hyo-Seong/ChromeDriverUpdater
저기에 올라와 있던 것을 주워다 쓰면서 날먹을 하고 싶었는데 뭔가 좀 바뀌어서 404 에러나면서 잘 안되더라.
그래서 소스 보고 뜯어서 되게 고쳐두었다.
ChromeDriverUpdator cdu = new ChromeDriverUpdator();
//cdu.LogEventAssign(LogAppend);
cdu.UpdateStart(Directory.GetCurrentDirectory() + @"\chromedriver.exe");
대충 이렇게 하면 돌아간다.
코드 간소화하기 귀찮아서 그냥 대충 막 고쳐놓고는 줄창 써먹을 예정
namespace JprCeleniumChromeDriverUpdater {
public class PlatformUrl {
public string platform;
public string url;
}
public class GoodVersions {
public string version;
public string revision;
public Dictionary<string, PlatformUrl[]> downloads;
}
public class GoodVersionJson {
public string timestamp;
public GoodVersions[] versions;
}
public class ChromeDriverUpdator {
private GoodVersionJson m_versionInfo;
private Action<string> m_logAction;
private const string URL_JSON_GOODVERTION = "https://googlechromelabs.github.io/chrome-for-testing/known-good-versions-with-downloads.json";
public void LogEventAssign(Action<string> action) {
m_logAction += action;
}
private void LogWrite(string _str) {
m_logAction?.Invoke(_str);
}
public void UpdateStart(string chromeDriverFullPath) {
if (string.IsNullOrEmpty(chromeDriverFullPath)) {
throw new ArgumentNullException(nameof(chromeDriverFullPath));
}
chromeDriverFullPath = Path.GetFullPath(chromeDriverFullPath);
LogWrite(chromeDriverFullPath);
if (!File.Exists(chromeDriverFullPath)) {
throw new FileNotFoundException();
}
Version chromeDriverVersion = GetChromeDriverVersion(chromeDriverFullPath);
Version chromeVersion = GetChromeVersion();
LogWrite($"크롬 버전: {chromeVersion}\n크롬 드라이버 버전: {chromeDriverVersion}");
if (UpdateNecessary(chromeDriverVersion, chromeVersion)) {
LogWrite($"크롬 드라이버 버전을 업데이트합니다...");
ShutdownChromeDriver(chromeDriverFullPath);
using (WebClient client = new WebClient()) {
string jsonContent = client.DownloadString(URL_JSON_GOODVERTION);
m_versionInfo = JsonConvert.DeserializeObject<GoodVersionJson>(jsonContent);
}
UpdateChromeDriver(chromeDriverFullPath, chromeVersion);
Version newChromeDriverVersion = GetChromeDriverVersion(chromeDriverFullPath);
} else {
LogWrite($"크롬 드라이버 버전을 업데이트하지 않습니다.");
}
}
public class ProcessExecuter {
public string Run(string fileName, string arguments) {
Process process = new Process();
process.StartInfo = GetProcessStartInfoForHiddenWindow(fileName, arguments);
process.Start();
string output = process.StandardOutput.ReadToEnd();
process.WaitForExit();
return output;
}
private ProcessStartInfo GetProcessStartInfoForHiddenWindow(string fileName, string arguments) {
ProcessStartInfo processStartInfo = new ProcessStartInfo();
processStartInfo.UseShellExecute = false;
processStartInfo.RedirectStandardOutput = true;
processStartInfo.WindowStyle = ProcessWindowStyle.Hidden;
processStartInfo.CreateNoWindow = true;
processStartInfo.FileName = fileName;
processStartInfo.Arguments = arguments;
return processStartInfo;
}
}
internal Version GetChromeDriverVersion(string chromeDriverPath) {
string output = new ProcessExecuter().Run($"{chromeDriverPath}", "-v");
string versionStr = output.Split(' ')[1];
Version version = new Version(versionStr);
return version;
}
public string ChromeDriverName => "chromedriver.exe";
public string ChromeDriverZipFileName => "chromedriver_win64.zip";
public Version GetChromeVersion() {
using (RegistryKey key = Registry.CurrentUser.OpenSubKey("Software\\Google\\Chrome\\BLBeacon")) {
if (key != null) {
object versionObject = key.GetValue("version");
if (versionObject != null) {
Version version = new Version(versionObject as String);
return version;
}
}
}
return null;
}
internal bool UpdateNecessary(Version chromeVersion, Version driverVersion) {
//revision은 하지마
if (chromeVersion.Major == driverVersion.Major &&
chromeVersion.Minor == driverVersion.Minor &&
chromeVersion.Build == driverVersion.Build) {
return false;
} else return true;
}
internal void ShutdownChromeDriver(string chromeDriverFullPath) {
var processes = Process.GetProcesses();
foreach (Process process in processes) {
// find exact path
if (process.MainWindowTitle == chromeDriverFullPath) {
process.Kill();
}
}
}
private void UpdateChromeDriver(string existChromeDriverFullPath, Version chromeVersion) {
string zipFileDownloadPath = DownloadChromeDriverZipFile(chromeVersion);
string newChromeDriverFullPath = GetNewChromeDriverFromZipFile(zipFileDownloadPath);
if (newChromeDriverFullPath != null) {
File.Copy(newChromeDriverFullPath, existChromeDriverFullPath, true);
File.Delete(newChromeDriverFullPath);
LogWrite("새로운 크롬 드라이버 버전 설치 완료");
}
}
internal string DownloadChromeDriverZipFile(Version chromeVersion) {
int bestVersionIndex = -1;
Version bestNewVersion = null;
for (int i = 0; i < m_versionInfo.versions.Length; i++) {
GoodVersions sample = m_versionInfo.versions[i];
if (Version.TryParse(sample.version, out Version parsedVersion)) {
if (((bestNewVersion == null) || (bestNewVersion < parsedVersion))
&& (chromeVersion.Major == parsedVersion.Major)
&& (chromeVersion.Minor == parsedVersion.Minor)
&& (chromeVersion.Build == parsedVersion.Build)) {
bestVersionIndex = i;
bestNewVersion = parsedVersion;
}
} else {
continue;
}
}
string downloadUrl = string.Empty;
if (bestNewVersion != null) {
GoodVersions gv = m_versionInfo.versions[bestVersionIndex];
LogWrite($"다운 받을 크롬 드라이버 버전: {gv.version}");
PlatformUrl[] PU = gv.downloads["chromedriver"];
for (int i = 0; i < PU.Length; i++) {
if (PU[i].platform == "win64") {
downloadUrl = PU[i].url;
break;
}
}
} else {
return null;
}
if (string.IsNullOrEmpty(downloadUrl) == false) {
string downloadZipFileFullPath = Path.Combine(Path.GetTempPath(), ChromeDriverZipFileName);
DownloadFile(downloadUrl, downloadZipFileFullPath);
return downloadZipFileFullPath;
} else {
return null;
}
}
internal string GetNewChromeDriverFromZipFile(string zipFileDownloadPath) {
string unzipPath = Path.Combine(Path.GetDirectoryName(zipFileDownloadPath), Path.GetFileNameWithoutExtension(zipFileDownloadPath));
UnzipFile(zipFileDownloadPath, unzipPath, true);
return FindNewChromeDriverFullPathFromUnzipPath(unzipPath);
}
internal string FindNewChromeDriverFullPathFromUnzipPath(string chromeDriverUnzipPath) {
chromeDriverUnzipPath += "\\chromedriver-win64";
DirectoryInfo directoryInfo = new DirectoryInfo(chromeDriverUnzipPath);
FileInfo[] files = directoryInfo.GetFiles();
LogWrite(chromeDriverUnzipPath);
foreach (FileInfo file in files) {
// ignore case
if (file.Name.ToLower() == ChromeDriverName.ToLower()) {
string newPath = Path.Combine(Path.GetDirectoryName(chromeDriverUnzipPath), file.Name);
File.Copy(file.FullName, newPath, true);
Directory.Delete(chromeDriverUnzipPath, true);
return newPath;
}
LogWrite($"찾은 파일 : {file.FullName}");
}
return null;
//throw new Exception("Can't find chromedriver name. name: " + ChromeDriverName.ToLower());
}
internal void DownloadFile(string downloadUrl, string downloadPath) {
new WebClient().DownloadFile(downloadUrl, downloadPath);
}
internal void UnzipFile(string zipPath, string unzipPath, bool deleteZipFile = true) {
if (Directory.Exists(unzipPath)) {
Directory.Delete(unzipPath, true);
}
ZipFile.ExtractToDirectory(zipPath, unzipPath);
if (deleteZipFile) {
File.Delete(zipPath);
}
}
}
}