├── .gitattributes ├── .gitignore ├── ESD Download Links Viewer.sln ├── ESD Download Links Viewer ├── App.config ├── App.xaml ├── App.xaml.cs ├── DownloadItem.cs ├── EDBHelper.cs ├── ESD Download Links Viewer.csproj ├── MainWindow.xaml ├── MainWindow.xaml.cs ├── Properties │ ├── AssemblyInfo.cs │ ├── Resources.Designer.cs │ ├── Resources.resx │ ├── Settings.Designer.cs │ └── Settings.settings ├── SizeConverter.cs ├── app.manifest └── packages.config ├── LICENSE.md └── README.md /.gitattributes: -------------------------------------------------------------------------------- 1 | ############################################################################### 2 | # Set default behavior to automatically normalize line endings. 3 | ############################################################################### 4 | * text=auto 5 | 6 | ############################################################################### 7 | # Set default behavior for command prompt diff. 8 | # 9 | # This is need for earlier builds of msysgit that does not have it on by 10 | # default for csharp files. 11 | # Note: This is only used by command line 12 | ############################################################################### 13 | #*.cs diff=csharp 14 | 15 | ############################################################################### 16 | # Set the merge driver for project and solution files 17 | # 18 | # Merging from the command prompt will add diff markers to the files if there 19 | # are conflicts (Merging from VS is not affected by the settings below, in VS 20 | # the diff markers are never inserted). Diff markers may cause the following 21 | # file extensions to fail to load in VS. An alternative would be to treat 22 | # these files as binary and thus will always conflict and require user 23 | # intervention with every merge. To do so, just uncomment the entries below 24 | ############################################################################### 25 | #*.sln merge=binary 26 | #*.csproj merge=binary 27 | #*.vbproj merge=binary 28 | #*.vcxproj merge=binary 29 | #*.vcproj merge=binary 30 | #*.dbproj merge=binary 31 | #*.fsproj merge=binary 32 | #*.lsproj merge=binary 33 | #*.wixproj merge=binary 34 | #*.modelproj merge=binary 35 | #*.sqlproj merge=binary 36 | #*.wwaproj merge=binary 37 | 38 | ############################################################################### 39 | # behavior for image files 40 | # 41 | # image files are treated as binary by default. 42 | ############################################################################### 43 | #*.jpg binary 44 | #*.png binary 45 | #*.gif binary 46 | 47 | ############################################################################### 48 | # diff behavior for common document formats 49 | # 50 | # Convert binary document formats to text before diffing them. This feature 51 | # is only available from the command line. Turn it on by uncommenting the 52 | # entries below. 53 | ############################################################################### 54 | #*.doc diff=astextplain 55 | #*.DOC diff=astextplain 56 | #*.docx diff=astextplain 57 | #*.DOCX diff=astextplain 58 | #*.dot diff=astextplain 59 | #*.DOT diff=astextplain 60 | #*.pdf diff=astextplain 61 | #*.PDF diff=astextplain 62 | #*.rtf diff=astextplain 63 | #*.RTF diff=astextplain 64 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | ## Ignore Visual Studio temporary files, build results, and 2 | ## files generated by popular Visual Studio add-ons. 3 | 4 | # User-specific files 5 | *.suo 6 | *.user 7 | *.userosscache 8 | *.sln.docstates 9 | 10 | # User-specific files (MonoDevelop/Xamarin Studio) 11 | *.userprefs 12 | 13 | # Build results 14 | [Dd]ebug/ 15 | [Dd]ebugPublic/ 16 | [Rr]elease/ 17 | [Rr]eleases/ 18 | [Xx]64/ 19 | [Xx]86/ 20 | [Bb]uild/ 21 | bld/ 22 | [Bb]in/ 23 | [Oo]bj/ 24 | 25 | # Visual Studio 2015 cache/options directory 26 | .vs/ 27 | # Uncomment if you have tasks that create the project's static files in wwwroot 28 | #wwwroot/ 29 | 30 | # MSTest test Results 31 | [Tt]est[Rr]esult*/ 32 | [Bb]uild[Ll]og.* 33 | 34 | # NUNIT 35 | *.VisualState.xml 36 | TestResult.xml 37 | 38 | # Build Results of an ATL Project 39 | [Dd]ebugPS/ 40 | [Rr]eleasePS/ 41 | dlldata.c 42 | 43 | # DNX 44 | project.lock.json 45 | artifacts/ 46 | 47 | *_i.c 48 | *_p.c 49 | *_i.h 50 | *.ilk 51 | *.meta 52 | *.obj 53 | *.pch 54 | *.pdb 55 | *.pgc 56 | *.pgd 57 | *.rsp 58 | *.sbr 59 | *.tlb 60 | *.tli 61 | *.tlh 62 | *.tmp 63 | *.tmp_proj 64 | *.log 65 | *.vspscc 66 | *.vssscc 67 | .builds 68 | *.pidb 69 | *.svclog 70 | *.scc 71 | 72 | # Chutzpah Test files 73 | _Chutzpah* 74 | 75 | # Visual C++ cache files 76 | ipch/ 77 | *.aps 78 | *.ncb 79 | *.opendb 80 | *.opensdf 81 | *.sdf 82 | *.cachefile 83 | *.VC.db 84 | 85 | # Visual Studio profiler 86 | *.psess 87 | *.vsp 88 | *.vspx 89 | *.sap 90 | 91 | # TFS 2012 Local Workspace 92 | $tf/ 93 | 94 | # Guidance Automation Toolkit 95 | *.gpState 96 | 97 | # ReSharper is a .NET coding add-in 98 | _ReSharper*/ 99 | *.[Rr]e[Ss]harper 100 | *.DotSettings.user 101 | 102 | # JustCode is a .NET coding add-in 103 | .JustCode 104 | 105 | # TeamCity is a build add-in 106 | _TeamCity* 107 | 108 | # DotCover is a Code Coverage Tool 109 | *.dotCover 110 | 111 | # NCrunch 112 | _NCrunch_* 113 | .*crunch*.local.xml 114 | nCrunchTemp_* 115 | 116 | # MightyMoose 117 | *.mm.* 118 | AutoTest.Net/ 119 | 120 | # Web workbench (sass) 121 | .sass-cache/ 122 | 123 | # Installshield output folder 124 | [Ee]xpress/ 125 | 126 | # DocProject is a documentation generator add-in 127 | DocProject/buildhelp/ 128 | DocProject/Help/*.HxT 129 | DocProject/Help/*.HxC 130 | DocProject/Help/*.hhc 131 | DocProject/Help/*.hhk 132 | DocProject/Help/*.hhp 133 | DocProject/Help/Html2 134 | DocProject/Help/html 135 | 136 | # Click-Once directory 137 | publish/ 138 | 139 | # Publish Web Output 140 | *.[Pp]ublish.xml 141 | *.azurePubxml 142 | 143 | # TODO: Un-comment the next line if you do not want to checkin 144 | # your web deploy settings because they may include unencrypted 145 | # passwords 146 | #*.pubxml 147 | *.publishproj 148 | 149 | # NuGet Packages 150 | *.nupkg 151 | # The packages folder can be ignored because of Package Restore 152 | **/packages/* 153 | # except build/, which is used as an MSBuild target. 154 | !**/packages/build/ 155 | # Uncomment if necessary however generally it will be regenerated when needed 156 | #!**/packages/repositories.config 157 | # NuGet v3's project.json files produces more ignoreable files 158 | *.nuget.props 159 | *.nuget.targets 160 | 161 | # Microsoft Azure Build Output 162 | csx/ 163 | *.build.csdef 164 | 165 | # Microsoft Azure Emulator 166 | ecf/ 167 | rcf/ 168 | 169 | # Microsoft Azure ApplicationInsights config file 170 | ApplicationInsights.config 171 | 172 | # Windows Store app package directory 173 | AppPackages/ 174 | BundleArtifacts/ 175 | 176 | # Visual Studio cache files 177 | # files ending in .cache can be ignored 178 | *.[Cc]ache 179 | # but keep track of directories ending in .cache 180 | !*.[Cc]ache/ 181 | 182 | # Others 183 | ClientBin/ 184 | [Ss]tyle[Cc]op.* 185 | ~$* 186 | *~ 187 | *.dbmdl 188 | *.dbproj.schemaview 189 | *.pfx 190 | *.publishsettings 191 | node_modules/ 192 | orleans.codegen.cs 193 | 194 | # RIA/Silverlight projects 195 | Generated_Code/ 196 | 197 | # Backup & report files from converting an old project file 198 | # to a newer Visual Studio version. Backup files are not needed, 199 | # because we have git ;-) 200 | _UpgradeReport_Files/ 201 | Backup*/ 202 | UpgradeLog*.XML 203 | UpgradeLog*.htm 204 | 205 | # SQL Server files 206 | *.mdf 207 | *.ldf 208 | 209 | # Business Intelligence projects 210 | *.rdl.data 211 | *.bim.layout 212 | *.bim_*.settings 213 | 214 | # Microsoft Fakes 215 | FakesAssemblies/ 216 | 217 | # GhostDoc plugin setting file 218 | *.GhostDoc.xml 219 | 220 | # Node.js Tools for Visual Studio 221 | .ntvs_analysis.dat 222 | 223 | # Visual Studio 6 build log 224 | *.plg 225 | 226 | # Visual Studio 6 workspace options file 227 | *.opt 228 | 229 | # Visual Studio LightSwitch build output 230 | **/*.HTMLClient/GeneratedArtifacts 231 | **/*.DesktopClient/GeneratedArtifacts 232 | **/*.DesktopClient/ModelManifest.xml 233 | **/*.Server/GeneratedArtifacts 234 | **/*.Server/ModelManifest.xml 235 | _Pvt_Extensions 236 | 237 | # LightSwitch generated files 238 | GeneratedArtifacts/ 239 | ModelManifest.xml 240 | 241 | # Paket dependency manager 242 | .paket/paket.exe 243 | 244 | # FAKE - F# Make 245 | .fake/ -------------------------------------------------------------------------------- /ESD Download Links Viewer.sln: -------------------------------------------------------------------------------- 1 |  2 | Microsoft Visual Studio Solution File, Format Version 12.00 3 | # Visual Studio 14 4 | VisualStudioVersion = 14.0.25123.0 5 | MinimumVisualStudioVersion = 10.0.40219.1 6 | Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "ESD Download Links Viewer", "ESD Download Links Viewer\ESD Download Links Viewer.csproj", "{96E32165-AA04-4227-865F-2F30A424D368}" 7 | EndProject 8 | Global 9 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 10 | Debug|Any CPU = Debug|Any CPU 11 | Release|Any CPU = Release|Any CPU 12 | EndGlobalSection 13 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 14 | {96E32165-AA04-4227-865F-2F30A424D368}.Debug|Any CPU.ActiveCfg = Debug|Any CPU 15 | {96E32165-AA04-4227-865F-2F30A424D368}.Debug|Any CPU.Build.0 = Debug|Any CPU 16 | {96E32165-AA04-4227-865F-2F30A424D368}.Release|Any CPU.ActiveCfg = Release|Any CPU 17 | {96E32165-AA04-4227-865F-2F30A424D368}.Release|Any CPU.Build.0 = Release|Any CPU 18 | EndGlobalSection 19 | GlobalSection(SolutionProperties) = preSolution 20 | HideSolutionNode = FALSE 21 | EndGlobalSection 22 | EndGlobal 23 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/App.config: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/App.xaml: -------------------------------------------------------------------------------- 1 |  6 | 7 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/App.xaml.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Configuration; 4 | using System.Data; 5 | using System.Linq; 6 | using System.Threading.Tasks; 7 | using System.Windows; 8 | 9 | namespace ESD_Download_Links_Viewer 10 | { 11 | /// 12 | /// App.xaml 的交互逻辑 13 | /// 14 | public partial class App : Application 15 | { 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/DownloadItem.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | 3 | namespace ESD_Download_Links_Viewer 4 | { 5 | class DownloadItem 6 | { 7 | public string Name { get; private set; } 8 | public string Url { get; private set; } 9 | public ulong Size { get; private set; } 10 | public string FileType { get; private set; } 11 | public DateTime ModifiedDate { get; private set; } 12 | public string SHA1 { get; private set; } 13 | public string SHA256 { get; private set; } 14 | 15 | public DownloadItem(string name, string url, ulong size, string ext, DateTime date, string sha1, string sha256) 16 | { 17 | Name = name; 18 | Url = url; 19 | Size = size; 20 | FileType = ext; 21 | ModifiedDate = date; 22 | SHA1 = sha1; 23 | SHA256 = sha256; 24 | } 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/EDBHelper.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Collections.ObjectModel; 4 | using System.Text; 5 | using System.Text.RegularExpressions; 6 | using System.Threading.Tasks; 7 | using System.IO; 8 | using Microsoft.Isam.Esent.Interop; 9 | 10 | namespace ESD_Download_Links_Viewer 11 | { 12 | class EDBHelper 13 | { 14 | private static JET_COLUMNID columnidName; 15 | private static JET_COLUMNID columnidUrl; 16 | private static JET_COLUMNID columnidSize; 17 | private static JET_COLUMNID columnidModifiedDate; 18 | private static JET_COLUMNID columnidDigest; 19 | private static JET_COLUMNID columnidStrongDigest; 20 | 21 | public Task> ReadDataAsync(string filename) 22 | { 23 | return Task.Run(() => 24 | { 25 | JET_INSTANCE instance = JET_INSTANCE.Nil; 26 | 27 | try 28 | { 29 | string dbpath = Path.GetDirectoryName(filename) + Path.DirectorySeparatorChar; 30 | JET_DBINFOMISC infomisc; 31 | Api.JetGetDatabaseFileInfo(filename, out infomisc, JET_DbInfo.Misc); 32 | SystemParameters.DatabasePageSize = infomisc.cbPageSize; 33 | Api.JetCreateInstance(out instance, Guid.NewGuid().ToString("N")); 34 | Api.JetSetSystemParameter(instance, JET_SESID.Nil, JET_param.CircularLog, 1, null); 35 | Api.JetSetSystemParameter(instance, JET_SESID.Nil, JET_param.TempPath, 0, dbpath); 36 | Api.JetSetSystemParameter(instance, JET_SESID.Nil, JET_param.Recovery, 0, "off"); 37 | Api.JetInit(ref instance); 38 | 39 | using (var session = new Session(instance)) 40 | { 41 | JET_DBID dbid = JET_DBID.Nil; 42 | 43 | Api.JetAttachDatabase(session, filename, AttachDatabaseGrbit.ReadOnly); 44 | Api.JetOpenDatabase(session, filename, null, out dbid, OpenDatabaseGrbit.ReadOnly); 45 | 46 | using (var table = new Table(session, dbid, "tbFiles", OpenTableGrbit.ReadOnly)) 47 | { 48 | // Load the columnids from the table. This should be done each time the database is attached 49 | // because an offline defrag (esentutl /d) can change the name => columnid mapping. 50 | IDictionary columnids = Api.GetColumnDictionary(session, table); 51 | 52 | columnidName = columnids["Name"]; 53 | columnidUrl = columnids["Urls"]; 54 | columnidSize = columnids["Size"]; 55 | columnidModifiedDate = columnids["Modified"]; 56 | columnidDigest = columnids["Digest"]; 57 | columnidStrongDigest = columnids["StrongDigest"]; 58 | 59 | return GetAllRecords(session, table); 60 | } 61 | } 62 | } 63 | finally 64 | { 65 | if (instance != JET_INSTANCE.Nil) { Api.JetTerm(instance); } 66 | } 67 | }); 68 | } 69 | 70 | /// 71 | /// Print all rows in the table. 72 | /// 73 | /// The session to use. 74 | /// The table to dump the records from. 75 | private ObservableCollection GetAllRecords(JET_SESID sesid, JET_TABLEID tableid) 76 | { 77 | if (Api.TryMoveFirst(sesid, tableid)) 78 | { 79 | return RetriveRecordsToEnd(sesid, tableid); 80 | } 81 | else 82 | { 83 | return new ObservableCollection(); 84 | } 85 | } 86 | 87 | /// 88 | /// Print records from the current point to the end of the table. 89 | /// 90 | /// The session to use. 91 | /// The table to dump the records from. 92 | private ObservableCollection RetriveRecordsToEnd(JET_SESID sesid, JET_TABLEID tableid) 93 | { 94 | ObservableCollection itemsList = new ObservableCollection(); 95 | 96 | do 97 | { 98 | itemsList.Add(GetOneRow(sesid, tableid)); 99 | } 100 | while (Api.TryMoveNext(sesid, tableid)); 101 | 102 | return itemsList; 103 | } 104 | 105 | /// 106 | /// Get the current record. 107 | /// 108 | /// The session to use. 109 | /// The table to use. 110 | private DownloadItem GetOneRow(JET_SESID sesid, JET_TABLEID tableid) 111 | { 112 | string fileName = Api.RetrieveColumnAsString(sesid, tableid, columnidName); 113 | fileName = fileName.Substring(0, fileName.Length - 1); 114 | 115 | string url = ""; 116 | string tempUrl = Api.RetrieveColumnAsString(sesid, tableid, columnidUrl); 117 | if(!String.IsNullOrEmpty(tempUrl)) 118 | { 119 | url = tempUrl.Substring(8).Trim(); 120 | url = url.Substring(0, url.Length - 2); 121 | } 122 | 123 | ulong fileSize = (ulong)Api.RetrieveColumnAsUInt64(sesid, tableid, columnidSize); 124 | 125 | string fileType = GetFileExtension(fileName); 126 | 127 | long dateValue = (long)Api.RetrieveColumnAsInt64(sesid, tableid, columnidModifiedDate); 128 | DateTime fileDate = new DateTime(dateValue, DateTimeKind.Utc); 129 | fileDate = fileDate.AddYears(1600); 130 | 131 | byte[] sha1Bytes = Api.RetrieveColumn(sesid, tableid, columnidDigest); 132 | string sha1 = ByteArrayToString(sha1Bytes); 133 | 134 | byte[] sha256Bytes = Api.RetrieveColumn(sesid, tableid, columnidStrongDigest); 135 | string sha256 = ByteArrayToString(sha256Bytes); 136 | 137 | DownloadItem item = new DownloadItem(fileName, url, fileSize, fileType, fileDate.ToLocalTime(), sha1, sha256); 138 | 139 | return item; 140 | } 141 | 142 | private static string ByteArrayToString(byte[] byteArray) 143 | { 144 | StringBuilder hex = new StringBuilder(byteArray.Length * 2); 145 | foreach (byte b in byteArray) 146 | { 147 | hex.AppendFormat("{0:X2}", b); 148 | } 149 | 150 | return hex.ToString(); 151 | } 152 | 153 | private string GetFileExtension(string fileName) 154 | { 155 | Regex regex = new Regex(@"(?<=.+)\.[a-z]{3}$"); 156 | 157 | return regex.Match(fileName).Value; 158 | } 159 | } 160 | } 161 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/ESD Download Links Viewer.csproj: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | Debug 6 | AnyCPU 7 | {96E32165-AA04-4227-865F-2F30A424D368} 8 | WinExe 9 | Properties 10 | ESD_Download_Links_Viewer 11 | ESD Download Links Viewer 12 | v4.6.2 13 | 512 14 | {60dc8134-eba5-43b8-bcc9-bb4bc16c2548};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC} 15 | 4 16 | true 17 | 18 | 19 | AnyCPU 20 | true 21 | full 22 | false 23 | bin\Debug\ 24 | DEBUG;TRACE 25 | prompt 26 | 4 27 | false 28 | 29 | 30 | AnyCPU 31 | pdbonly 32 | true 33 | bin\Release\ 34 | TRACE 35 | prompt 36 | 4 37 | false 38 | 39 | 40 | app.manifest 41 | 42 | 43 | 44 | ..\packages\ManagedEsent.1.9.4\lib\net40\Esent.Interop.dll 45 | True 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 4.0 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | MSBuild:Compile 65 | Designer 66 | 67 | 68 | 69 | MSBuild:Compile 70 | Designer 71 | 72 | 73 | App.xaml 74 | Code 75 | 76 | 77 | 78 | 79 | MainWindow.xaml 80 | Code 81 | 82 | 83 | 84 | 85 | Code 86 | 87 | 88 | True 89 | True 90 | Resources.resx 91 | 92 | 93 | True 94 | Settings.settings 95 | True 96 | 97 | 98 | ResXFileCodeGenerator 99 | Resources.Designer.cs 100 | 101 | 102 | Designer 103 | 104 | 105 | 106 | SettingsSingleFileGenerator 107 | Settings.Designer.cs 108 | 109 | 110 | 111 | 112 | 113 | 114 | 115 | 122 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/MainWindow.xaml: -------------------------------------------------------------------------------- 1 |  9 | 10 | 57 | 58 | 105 | 106 | 115 | 116 | 123 | 124 | 125 | 126 | 127 | 128 | 129 | 130 | 131 | 132 | 133 | 134 | 135 | 136 | 137 | 138 | 139 | 140 | 141 | 142 | 143 | 144 | 145 | 146 | 147 | 148 | 149 | 150 | 151 | 152 | 153 | 154 | Filter : 155 | All 156 | ESD 157 | 158 | 159 | 160 | 161 | 162 | 163 | 167 | 168 | 169 | 170 | 171 | 172 | 173 | 174 | 175 | 176 | 177 | 178 | 182 | 183 | 184 | 185 | 186 | 190 | 191 | 192 | 193 | 194 | 195 | 196 | 197 | 198 | 199 | 200 | 201 | 202 | 203 | 204 | 205 | 206 | 207 | 208 | 209 | 210 | 211 | 212 | File Name : 213 | Url : 214 | Url Expire at : 215 | Size : 216 | Modified Date : 217 | SHA-1 : 218 | SHA-256 : 219 | 220 | 221 | 222 | 223 | 224 | 225 | 226 | 227 | 228 | 229 | 230 | 231 | 232 | 233 | 234 | 235 | 236 | 237 | 238 | 239 | 240 | 251 | 252 | 253 | 254 | 255 | Created by: Crimson Arc 256 | 257 | https://github.com/crimsonarc 258 | 259 | 260 | 261 | 262 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/MainWindow.xaml.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.ObjectModel; 3 | using System.Diagnostics; 4 | using System.Text.RegularExpressions; 5 | using System.Windows; 6 | using System.Windows.Controls; 7 | using System.Windows.Data; 8 | using System.Windows.Media; 9 | using System.Windows.Navigation; 10 | using Microsoft.Isam.Esent.Interop; 11 | using Microsoft.Win32; 12 | 13 | namespace ESD_Download_Links_Viewer 14 | { 15 | /// 16 | /// MainWindow.xaml 的交互逻辑 17 | /// 18 | public partial class MainWindow : Window 19 | { 20 | ObservableCollection fileList; 21 | 22 | double tempExpireDateUnixTime = 0; 23 | 24 | public MainWindow() 25 | { 26 | InitializeComponent(); 27 | } 28 | 29 | private void Window_Loaded(object sender, RoutedEventArgs e) 30 | { 31 | LoadData(); 32 | } 33 | 34 | private async void LoadData() 35 | { 36 | try 37 | { 38 | EDBHelper edbHelper = new EDBHelper(); 39 | fileList = await edbHelper.ReadDataAsync(@"C:\Windows.old\WINDOWS\SoftwareDistribution\DataStore\DataStore.edb"); 40 | gridView.ItemsSource = fileList; 41 | 42 | radioFilterESD.IsChecked = true; 43 | } 44 | catch (EsentFileNotFoundException) 45 | { 46 | MessageBox.Show("Can't found C:\\Windows.old\\WINDOWS\\SoftwareDistribution\\DataStore\\DataStore.edb\n\n"+ 47 | "Please make sure you did not cleaned up the Previous Windows Installation.\n"+ 48 | "Or you can open a DataStore file manually.", "File Not Found", MessageBoxButton.OK, MessageBoxImage.Warning); 49 | } 50 | catch (Exception ex) 51 | { 52 | MessageBox.Show(ex.Message); 53 | } 54 | } 55 | 56 | private bool FilterESD(object item) 57 | { 58 | DownloadItem fileItem = item as DownloadItem; 59 | if (fileItem != null) 60 | { 61 | if (fileItem.FileType == ".esd") 62 | { 63 | return true; 64 | } 65 | } 66 | return false; 67 | } 68 | 69 | private DateTime UnixTimeToDateTime(double unixTime) 70 | { 71 | return new DateTime(1970, 1, 1, 0, 0, 0, 0, DateTimeKind.Utc).AddSeconds(unixTime); 72 | } 73 | 74 | private void radioFilterAll_Checked(object sender, RoutedEventArgs e) 75 | { 76 | ListCollectionView view = CollectionViewSource.GetDefaultView(gridView.ItemsSource) as ListCollectionView; 77 | if (view != null) 78 | { 79 | view.Filter = null; 80 | } 81 | } 82 | 83 | private void radioFilterESD_Checked(object sender, RoutedEventArgs e) 84 | { 85 | ListCollectionView view = CollectionViewSource.GetDefaultView(gridView.ItemsSource) as ListCollectionView; 86 | if (view != null) 87 | { 88 | view.Filter = new Predicate(FilterESD); 89 | } 90 | } 91 | 92 | private void gridView_SelectionChanged(object sender, SelectionChangedEventArgs e) 93 | { 94 | tempExpireDateUnixTime = 0; 95 | txtUrlExpireDate.Text = ""; 96 | txtUrlExpireDate.Foreground = Brushes.Black; 97 | 98 | if (gridView.SelectedItem != null) 99 | { 100 | DownloadItem item = gridView.SelectedItem as DownloadItem; 101 | 102 | if(!String.IsNullOrEmpty(item.Url)) 103 | { 104 | Regex matchUnixTime = new Regex(@"(?<=\D+)\d{10}(?=\D.+)"); 105 | string timeStr = matchUnixTime.Match(item.Url).Value; 106 | 107 | if(!String.IsNullOrEmpty(timeStr)) 108 | { 109 | double unixTime; 110 | double.TryParse(timeStr, out unixTime); 111 | 112 | tempExpireDateUnixTime = unixTime; 113 | 114 | DateTime expireDate = UnixTimeToDateTime(unixTime); 115 | 116 | txtUrlExpireDate.Text = expireDate.ToLocalTime().ToString(); 117 | 118 | if (DateTime.UtcNow > expireDate) 119 | { 120 | txtUrlExpireDate.Foreground = Brushes.Red; 121 | } 122 | } 123 | } 124 | } 125 | } 126 | 127 | private void btnCopyFileName_Click(object sender, RoutedEventArgs e) 128 | { 129 | Clipboard.SetText(txtFileName.Text); 130 | } 131 | 132 | private void btnCopyUrl_Click(object sender, RoutedEventArgs e) 133 | { 134 | Clipboard.SetText(txtUrl.Text); 135 | } 136 | 137 | private void btnCopySHA1_Click(object sender, RoutedEventArgs e) 138 | { 139 | Clipboard.SetText(txtSHA1.Text); 140 | } 141 | 142 | private void btnCopySHA256_Click(object sender, RoutedEventArgs e) 143 | { 144 | Clipboard.SetText(txtSHA256.Text); 145 | } 146 | 147 | private void btnCopyDetails_Click(object sender, RoutedEventArgs e) 148 | { 149 | string infos; 150 | 151 | if (tempExpireDateUnixTime != 0) 152 | { 153 | infos = "File Name: " + txtFileName.Text + "\r\n" + 154 | "Url: " + txtUrl.Text + "\r\n" + 155 | "Expire At: " + UnixTimeToDateTime(tempExpireDateUnixTime).ToString() + " UTC\r\n" + 156 | "SHA-1: " + txtSHA1.Text + "\r\n" + 157 | "SHA-256: " + txtSHA256.Text + "\r\n"; 158 | } 159 | else 160 | { 161 | infos = "File Name: " + txtFileName.Text + "\r\n" + 162 | "Url: " + txtUrl.Text + "\r\n" + 163 | "SHA-1: " + txtSHA1.Text + "\r\n" + 164 | "SHA-256: " + txtSHA256.Text + "\r\n"; 165 | } 166 | 167 | Clipboard.SetText(infos); 168 | } 169 | 170 | private async void btnOpenDB_Click(object sender, RoutedEventArgs e) 171 | { 172 | OpenFileDialog openfile = new OpenFileDialog(); 173 | openfile.Filter = "Esent Database(*.edb)|*.edb"; 174 | 175 | if ((bool)openfile.ShowDialog() && openfile.FileName != "") 176 | { 177 | try 178 | { 179 | if ((bool)radioFilterESD.IsChecked) 180 | { 181 | radioFilterESD.IsChecked = false; 182 | } 183 | 184 | EDBHelper edbHelper = new EDBHelper(); 185 | fileList = await edbHelper.ReadDataAsync(openfile.FileName); 186 | gridView.ItemsSource = fileList; 187 | 188 | radioFilterESD.IsChecked = true; 189 | } 190 | catch (Exception ex) 191 | { 192 | MessageBox.Show(ex.Message); 193 | } 194 | } 195 | } 196 | 197 | private void GitHubLink_RequestNavigate(object sender, RequestNavigateEventArgs e) 198 | { 199 | Process.Start(new ProcessStartInfo(e.Uri.AbsoluteUri)); 200 | 201 | e.Handled = true; 202 | } 203 | } 204 | } 205 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Resources; 3 | using System.Runtime.CompilerServices; 4 | using System.Runtime.InteropServices; 5 | using System.Windows; 6 | 7 | // 有关程序集的一般信息由以下 8 | // 控制。更改这些特性值可修改 9 | // 与程序集关联的信息。 10 | [assembly: AssemblyTitle("ESD Download Links Viewer")] 11 | [assembly: AssemblyDescription("")] 12 | [assembly: AssemblyConfiguration("")] 13 | [assembly: AssemblyCompany("")] 14 | [assembly: AssemblyProduct("ESD Download Links Viewer")] 15 | [assembly: AssemblyCopyright("© Crimson Arc 2016")] 16 | [assembly: AssemblyTrademark("")] 17 | [assembly: AssemblyCulture("")] 18 | 19 | //将 ComVisible 设置为 false 将使此程序集中的类型 20 | //对 COM 组件不可见。 如果需要从 COM 访问此程序集中的类型, 21 | //请将此类型的 ComVisible 特性设置为 true。 22 | [assembly: ComVisible(false)] 23 | 24 | //若要开始生成可本地化的应用程序,请 25 | // 中的 .csproj 文件中 26 | //例如,如果您在源文件中使用的是美国英语, 27 | //使用的是美国英语,请将 设置为 en-US。 然后取消 28 | //对以下 NeutralResourceLanguage 特性的注释。 更新 29 | //以下行中的“en-US”以匹配项目文件中的 UICulture 设置。 30 | 31 | //[assembly: NeutralResourcesLanguage("en-US", UltimateResourceFallbackLocation.Satellite)] 32 | 33 | 34 | [assembly: ThemeInfo( 35 | ResourceDictionaryLocation.None, //主题特定资源词典所处位置 36 | //(当资源未在页面 37 | //或应用程序资源字典中找到时使用) 38 | ResourceDictionaryLocation.SourceAssembly //常规资源词典所处位置 39 | //(当资源未在页面 40 | //、应用程序或任何主题专用资源字典中找到时使用) 41 | )] 42 | 43 | 44 | // 程序集的版本信息由下列四个值组成: 45 | // 46 | // 主版本 47 | // 次版本 48 | // 生成号 49 | // 修订号 50 | // 51 | //可以指定所有这些值,也可以使用“生成号”和“修订号”的默认值, 52 | // 方法是按如下所示使用“*”: : 53 | // [assembly: AssemblyVersion("1.0.*")] 54 | [assembly: AssemblyVersion("1.0.0.0")] 55 | [assembly: AssemblyFileVersion("1.0.0.0")] 56 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/Properties/Resources.Designer.cs: -------------------------------------------------------------------------------- 1 | //------------------------------------------------------------------------------ 2 | // 3 | // 此代码由工具生成。 4 | // 运行时版本: 4.0.30319.42000 5 | // 6 | // 对此文件的更改可能导致不正确的行为,如果 7 | // 重新生成代码,则所做更改将丢失。 8 | // 9 | //------------------------------------------------------------------------------ 10 | 11 | namespace ESD_Download_Links_Viewer.Properties 12 | { 13 | 14 | 15 | /// 16 | /// 强类型资源类,用于查找本地化字符串等。 17 | /// 18 | // 此类是由 StronglyTypedResourceBuilder 19 | // 类通过类似于 ResGen 或 Visual Studio 的工具自动生成的。 20 | // 若要添加或删除成员,请编辑 .ResX 文件,然后重新运行 ResGen 21 | // (以 /str 作为命令选项),或重新生成 VS 项目。 22 | [global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "4.0.0.0")] 23 | [global::System.Diagnostics.DebuggerNonUserCodeAttribute()] 24 | [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()] 25 | internal class Resources 26 | { 27 | 28 | private static global::System.Resources.ResourceManager resourceMan; 29 | 30 | private static global::System.Globalization.CultureInfo resourceCulture; 31 | 32 | [global::System.Diagnostics.CodeAnalysis.SuppressMessageAttribute("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode")] 33 | internal Resources() 34 | { 35 | } 36 | 37 | /// 38 | /// 返回此类使用的缓存 ResourceManager 实例。 39 | /// 40 | [global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)] 41 | internal static global::System.Resources.ResourceManager ResourceManager 42 | { 43 | get 44 | { 45 | if ((resourceMan == null)) 46 | { 47 | global::System.Resources.ResourceManager temp = new global::System.Resources.ResourceManager("ESD_Download_Links_Viewer.Properties.Resources", typeof(Resources).Assembly); 48 | resourceMan = temp; 49 | } 50 | return resourceMan; 51 | } 52 | } 53 | 54 | /// 55 | /// 覆盖当前线程的 CurrentUICulture 属性 56 | /// 使用此强类型的资源类的资源查找。 57 | /// 58 | [global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)] 59 | internal static global::System.Globalization.CultureInfo Culture 60 | { 61 | get 62 | { 63 | return resourceCulture; 64 | } 65 | set 66 | { 67 | resourceCulture = value; 68 | } 69 | } 70 | } 71 | } 72 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/Properties/Resources.resx: -------------------------------------------------------------------------------- 1 |  2 | 3 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | 105 | 106 | text/microsoft-resx 107 | 108 | 109 | 2.0 110 | 111 | 112 | System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 113 | 114 | 115 | System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 116 | 117 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/Properties/Settings.Designer.cs: -------------------------------------------------------------------------------- 1 | //------------------------------------------------------------------------------ 2 | // 3 | // This code was generated by a tool. 4 | // Runtime Version:4.0.30319.42000 5 | // 6 | // Changes to this file may cause incorrect behavior and will be lost if 7 | // the code is regenerated. 8 | // 9 | //------------------------------------------------------------------------------ 10 | 11 | namespace ESD_Download_Links_Viewer.Properties 12 | { 13 | 14 | 15 | [global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()] 16 | [global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.VisualStudio.Editors.SettingsDesigner.SettingsSingleFileGenerator", "11.0.0.0")] 17 | internal sealed partial class Settings : global::System.Configuration.ApplicationSettingsBase 18 | { 19 | 20 | private static Settings defaultInstance = ((Settings)(global::System.Configuration.ApplicationSettingsBase.Synchronized(new Settings()))); 21 | 22 | public static Settings Default 23 | { 24 | get 25 | { 26 | return defaultInstance; 27 | } 28 | } 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/Properties/Settings.settings: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/SizeConverter.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Globalization; 3 | using System.Windows.Data; 4 | 5 | namespace ESD_Download_Links_Viewer 6 | { 7 | [ValueConversion(typeof(ulong), typeof(string))] 8 | public class SizeConverter : IValueConverter 9 | { 10 | public object Convert(object value, Type targetType, object parameter, CultureInfo culture) 11 | { 12 | ulong bytesValue = (ulong)value; 13 | double KBytesValue = (double)bytesValue / 1024; 14 | 15 | return KBytesValue.ToString("N", culture) + " KB"; 16 | } 17 | 18 | //Actually, this method's implementation is not necessary, because I just using OneWay binding mode. 19 | public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture) 20 | { 21 | string valueStr = value.ToString(); 22 | valueStr = valueStr.Replace("KB", "").Trim(); 23 | 24 | double doubleValue; 25 | if (double.TryParse(valueStr, NumberStyles.Any, culture, out doubleValue)) 26 | { 27 | return (ulong)(doubleValue * 1024); 28 | } 29 | else 30 | { 31 | return 0; 32 | } 33 | } 34 | } 35 | } 36 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/app.manifest: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 51 | 52 | 53 | 54 | true/PM 55 | 56 | 57 | 58 | 59 | 60 | 74 | 75 | 76 | -------------------------------------------------------------------------------- /ESD Download Links Viewer/packages.config: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | -------------------------------------------------------------------------------- /LICENSE.md: -------------------------------------------------------------------------------- 1 | Microsoft Public License (Ms-PL) 2 | 3 | This license governs use of the accompanying software. If you use the software, you accept this license. If you do not accept the license, do not use the software. 4 | 5 | 1. Definitions 6 | 7 | The terms "reproduce," "reproduction," "derivative works," and "distribution" have the same meaning here as under U.S. copyright law. 8 | 9 | A "contribution" is the original software, or any additions or changes to the software. 10 | 11 | A "contributor" is any person that distributes its contribution under this license. 12 | 13 | "Licensed patents" are a contributor's patent claims that read directly on its contribution. 14 | 15 | 2. Grant of Rights 16 | 17 | (A) Copyright Grant- Subject to the terms of this license, including the license conditions and limitations in section 3, each contributor grants you a non-exclusive, worldwide, royalty-free copyright license to reproduce its contribution, prepare derivative works of its contribution, and distribute its contribution or any derivative works that you create. 18 | 19 | (B) Patent Grant- Subject to the terms of this license, including the license conditions and limitations in section 3, each contributor grants you a non-exclusive, worldwide, royalty-free license under its licensed patents to make, have made, use, sell, offer for sale, import, and/or otherwise dispose of its contribution in the software or derivative works of the contribution in the software. 20 | 21 | 3. Conditions and Limitations 22 | 23 | (A) No Trademark License- This license does not grant you rights to use any contributors' name, logo, or trademarks. 24 | 25 | (B) If you bring a patent claim against any contributor over patents that you claim are infringed by the software, your patent license from such contributor to the software ends automatically. 26 | 27 | (C) If you distribute any portion of the software, you must retain all copyright, patent, trademark, and attribution notices that are present in the software. 28 | 29 | (D) If you distribute any portion of the software in source code form, you may do so only under this license by including a complete copy of this license with your distribution. If you distribute any portion of the software in compiled or object code form, you may only do so under a license that complies with this license. 30 | 31 | (E) The software is licensed "as-is." You bear the risk of using it. The contributors give no express warranties, guarantees or conditions. You may have additional consumer rights under your local laws which this license cannot change. To the extent permitted under your local laws, the contributors exclude the implied warranties of merchantability, fitness for a particular purpose and non-infringement. 32 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # ESD-Download-Links-Viewer 2 | 3 | This tool is for Windows 10 Insiders easily to get the new Insider Preview Build's ESD file download link and then share for others. 4 | 5 | For this purpose, you must finished your system's upgrade before you run this tool. 6 | 7 | Because it reads the C:\Windows.old\WINDOWS\SoftwareDistribution\DataStore\DataStore.edb file. 8 | 9 | To read this file properly, the program has to run with Administrative privilege. 10 | 11 | You can also open a DataStore.edb file manually. 12 | 13 | This tool's UI is based on WPF, fully vectorize and support Per-Monitor DPI scale. But you have to install .Net Framework 4.6.2 to support Per-Monitor DPI scaling. 14 | 15 | 16 | ## Chinese Description 中文简介 17 | 18 | 这个工具专门用于参与Windows 10 Insider测试的会员在更新新版Insider预览版后能够轻松分享新版Insider预览版的esd安装文件的下载链接。 19 | 20 | 下载链接具有时效性,本工具会在界面上告知用户链接的有效时间(软件界面上会转换为本地时间显示),一键复制出来的详细分享信息也会包含这个时间信息(但会以UTC时间显示)。 21 | 22 | 为了让这个工具能够正确运行,你必须在自己完成新版系统更新后才能运行使用,并且请确保你更新完后还没清理旧的Windows安装,因为本程序需要读取 C:\Windows.old\WINDOWS\SoftwareDistribution\DataStore\DataStore.edb 文件。 23 | 24 | 另外,为了让程序能成功读取到这个路径的数据库文件,程序强制使用管理员权限运行。 25 | 26 | 你也可以手动打开一个你存放到其他路径的DataStore.edb文件,软件界面能筛选显示数据库里的所有文件下载记录或者筛选只显示ESD文件的记录。每一个记录都能查看对应的文件SHA-1以及SHA-256的Hash数值。 27 | 28 | 本程序的界面基于WPF技术开发,完全矢量化,并且支持Per-Monitor DPI缩放(独立显示器DPI缩放,或叫动态DPI缩放),但为了支持Per-Monitor DPI缩放,你必须安装.Net Framework 4.6.2。程序最低要求.Net Framework 4.5(但不支持Per-Monitor DPI缩放)。 29 | --------------------------------------------------------------------------------