Compare commits
86 Commits
1.0.7388.2
...
master
Author | SHA1 | Date | |
---|---|---|---|
|
2fe4fa4592 | ||
|
531a1c1e34 | ||
|
5814336814 | ||
|
6af8eba6c6 | ||
|
ba106c1783 | ||
|
3d710854b3 | ||
|
f9b56c91af | ||
|
3ddc958e0b | ||
|
536b549114 | ||
|
94c0273304 | ||
|
e92a074544 | ||
|
9b1935e7a7 | ||
|
3bd245b277 | ||
|
9d42aefe24 | ||
|
ef5947f54c | ||
|
f38a0e054d | ||
|
5e31ff3b45 | ||
|
c602b59f21 | ||
|
042b126634 | ||
|
0976297348 | ||
|
ddbfb39e87 | ||
|
14b2643cbf | ||
|
0eccafa9ea | ||
|
b2d353b0bb | ||
|
c5de2e6886 | ||
|
73669e16ea | ||
|
ffa645c991 | ||
|
e642161206 | ||
|
568d17e3fa | ||
|
08dfef1498 | ||
|
2670a04542 | ||
|
e36005558d | ||
|
da1dbca8f6 | ||
|
2fd34f5576 | ||
|
bc7875c512 | ||
|
2dea7f8138 | ||
|
07ef29d807 | ||
|
c59bb90032 | ||
|
b3bf4f7026 | ||
|
0f48d64121 | ||
|
984044f1b0 | ||
|
a8479cd577 | ||
|
12b946fdf0 | ||
|
651992285c | ||
|
4afa77abca | ||
|
bc418aaef6 | ||
|
3291f7c460 | ||
|
50c422b701 | ||
|
24529a59e7 | ||
|
c8eaeebbde | ||
|
df8099e3d0 | ||
|
5364fa250c | ||
|
90a3aacce0 | ||
|
55cf52df26 | ||
|
802340e418 | ||
|
a42b9b624d | ||
|
0ac90790b8 | ||
|
8d3bc22af7 | ||
|
f58334c8a4 | ||
|
eca073fab3 | ||
|
c186afa8b4 | ||
|
daca8d5b9a | ||
|
a76a09051b | ||
|
0fc0b9eead | ||
|
a64d3ab4bc | ||
|
b395ab2d81 | ||
|
2ca1bd5408 | ||
|
29e35dbec0 | ||
|
1ad1d0f8f8 | ||
|
5619de376a | ||
|
21dc22965d | ||
|
5cae428440 | ||
|
f931169ebe | ||
|
1d690c738d | ||
|
ca89e1c94d | ||
|
ac5fc1cd5e | ||
|
ff2e7e63de | ||
|
f6acde934e | ||
|
b6d2c18b31 | ||
|
86009c2d88 | ||
|
18c8419495 | ||
|
4b7980d138 | ||
|
3210028469 | ||
|
101ea5843a | ||
|
d7306150e8 | ||
|
023f452b26 |
129
.github/workflows/main.yml
vendored
129
.github/workflows/main.yml
vendored
@ -1,129 +0,0 @@
|
|||||||
name: CD
|
|
||||||
|
|
||||||
on: [push]
|
|
||||||
|
|
||||||
jobs:
|
|
||||||
build:
|
|
||||||
|
|
||||||
runs-on: windows-latest
|
|
||||||
|
|
||||||
steps:
|
|
||||||
- uses: actions/checkout@v2.0.0
|
|
||||||
- name: Build
|
|
||||||
id: base_init
|
|
||||||
run: |
|
|
||||||
cd $Env:GITHUB_WORKSPACE
|
|
||||||
dotnet build --verbosity:m -p:Configuration=Release
|
|
||||||
cp ".\UpTool build tool\bin\Release\netcoreapp3.1\package.zip" $Env:GITHUB_WORKSPACE\Tools.zip
|
|
||||||
& "C:\Program Files\7-Zip\7z" a .\Release.zip .\UpTool2\bin\Release\netcoreapp3.1\*
|
|
||||||
$asmver = $([Reflection.Assembly]::Loadfile($(pwd).Path + "\\UpTool2\\bin\\Release\\netcoreapp3.1\\UpTool2.dll").GetName().version.ToString())
|
|
||||||
$pkgtoolver = $([Reflection.Assembly]::Loadfile($(pwd).Path + "\\UpTool build tool\\bin\\Release\\netcoreapp3.1\\pkgtool.dll").GetName().version.ToString())
|
|
||||||
echo "::set-output name=vers::$asmver"
|
|
||||||
echo "::set-output name=pkgvers::$pkgtoolver"
|
|
||||||
- name: Create Release
|
|
||||||
id: create_release
|
|
||||||
uses: actions/create-release@v1.0.1
|
|
||||||
env:
|
|
||||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
||||||
with:
|
|
||||||
tag_name: ${{ steps.base_init.outputs.vers }}
|
|
||||||
release_name: Release ${{ steps.base_init.outputs.vers }}
|
|
||||||
draft: false
|
|
||||||
prerelease: false
|
|
||||||
- name: Upload Release Asset
|
|
||||||
id: upload_release_asset
|
|
||||||
uses: actions/upload-release-asset@v1.0.2
|
|
||||||
env:
|
|
||||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
||||||
with:
|
|
||||||
upload_url: ${{ steps.create_release.outputs.upload_url }}
|
|
||||||
asset_path: ./Release.zip
|
|
||||||
asset_name: Release.zip
|
|
||||||
asset_content_type: application/zip
|
|
||||||
- name: Upload Tool Asset
|
|
||||||
id: upload_tool_asset
|
|
||||||
uses: actions/upload-release-asset@v1.0.2
|
|
||||||
env:
|
|
||||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
||||||
with:
|
|
||||||
upload_url: ${{ steps.create_release.outputs.upload_url }}
|
|
||||||
asset_path: ./Tools.zip
|
|
||||||
asset_name: Tools.zip
|
|
||||||
asset_content_type: application/zip
|
|
||||||
- name: Create XML
|
|
||||||
run: |
|
|
||||||
[System.XML.XMLDocument]$xml=New-Object System.XML.XMLDocument
|
|
||||||
[System.XML.XMLElement]$app=$xml.CreateElement("app")
|
|
||||||
$xml.appendChild($app)
|
|
||||||
$app.appendChild($xml.CreateElement("Name")).InnerText = "UpTool2 package tools"
|
|
||||||
$app.appendChild($xml.CreateElement("Description")).InnerText = "Tools for automating package creation"
|
|
||||||
$app.appendChild($xml.CreateElement("Version")).InnerText = "${{ steps.base_init.outputs.pkgvers }}"
|
|
||||||
$app.appendChild($xml.CreateElement("ID")).InnerText = "0e35d154-d0d3-45e0-b080-62f521263a44"
|
|
||||||
$app.appendChild($xml.CreateElement("File")).InnerText = "${{ steps.upload_tool_asset.outputs.browser_download_url }}"
|
|
||||||
$app.appendChild($xml.CreateElement("Hash")).InnerText = $(Get-FileHash $Env:GITHUB_WORKSPACE\Tools.zip).Hash
|
|
||||||
echo NULL > tools.xml
|
|
||||||
$xml.save($(gi .\tools.xml).Fullname)
|
|
||||||
[System.XML.XMLDocument]$xml=New-Object System.XML.XMLDocument
|
|
||||||
[System.XML.XMLElement]$app=$xml.CreateElement("meta")
|
|
||||||
$xml.appendChild($app)
|
|
||||||
$app.appendChild($xml.CreateElement("Version")).InnerText = "${{ steps.base_init.outputs.vers }}"
|
|
||||||
$app.appendChild($xml.CreateElement("File")).InnerText = "${{ steps.upload_release_asset.outputs.browser_download_url }}"
|
|
||||||
$app.appendChild($xml.CreateElement("Hash")).InnerText = $(Get-FileHash $Env:GITHUB_WORKSPACE\Release.zip).Hash
|
|
||||||
echo NULL > meta.xml
|
|
||||||
$xml.save($(gi .\meta.xml).Fullname)
|
|
||||||
- name: Upload Meta XML
|
|
||||||
uses: actions/upload-release-asset@v1.0.2
|
|
||||||
env:
|
|
||||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
||||||
with:
|
|
||||||
upload_url: ${{ steps.create_release.outputs.upload_url }}
|
|
||||||
asset_path: ./meta.xml
|
|
||||||
asset_name: meta.xml
|
|
||||||
asset_content_type: text/xml
|
|
||||||
- name: Upload Tool XML
|
|
||||||
uses: actions/upload-release-asset@v1.0.2
|
|
||||||
env:
|
|
||||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
||||||
with:
|
|
||||||
upload_url: ${{ steps.create_release.outputs.upload_url }}
|
|
||||||
asset_path: ./tools.xml
|
|
||||||
asset_name: tools.xml
|
|
||||||
asset_content_type: text/xml
|
|
||||||
- name: Build non-generic installers
|
|
||||||
run: |
|
|
||||||
cd $Env:GITHUB_WORKSPACE\Installer
|
|
||||||
& "C:\Program Files\7-Zip\7z" a ..\Installer-generic.zip .\bin\Release\netcoreapp3.1\Installer.exe
|
|
||||||
& "C:\Program Files\7-Zip\7z" a ..\Installer-generic.zip .\bin\Release\netcoreapp3.1\Installer.dll
|
|
||||||
& "C:\Program Files\7-Zip\7z" a ..\Installer-generic.zip .\bin\Release\netcoreapp3.1\Installer.runtimeconfig.json
|
|
||||||
dotnet publish -r win-x64 -c Release /p:PublishSingleFile=true /p:PublishTrimmed=true
|
|
||||||
dotnet publish -r win-x86 -c Release /p:PublishSingleFile=true /p:PublishTrimmed=true
|
|
||||||
cp .\bin\Release\netcoreapp3.1\win-x64\publish\Installer.exe ..\Installer-x64.exe
|
|
||||||
cp .\bin\Release\netcoreapp3.1\win-x86\publish\Installer.exe ..\Installer-x86.exe
|
|
||||||
cd $Env:GITHUB_WORKSPACE
|
|
||||||
- name: Upload x86 Installer
|
|
||||||
uses: actions/upload-release-asset@v1.0.2
|
|
||||||
env:
|
|
||||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
||||||
with:
|
|
||||||
upload_url: ${{ steps.create_release.outputs.upload_url }}
|
|
||||||
asset_path: ./Installer-x86.exe
|
|
||||||
asset_name: Installer-x86.exe
|
|
||||||
asset_content_type: application/vnd.microsoft.portable-executable
|
|
||||||
- name: Upload x64 Installer
|
|
||||||
uses: actions/upload-release-asset@v1.0.2
|
|
||||||
env:
|
|
||||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
||||||
with:
|
|
||||||
upload_url: ${{ steps.create_release.outputs.upload_url }}
|
|
||||||
asset_path: ./Installer-x64.exe
|
|
||||||
asset_name: Installer-x64.exe
|
|
||||||
asset_content_type: application/vnd.microsoft.portable-executable
|
|
||||||
- name: Upload generic Installer
|
|
||||||
uses: actions/upload-release-asset@v1.0.2
|
|
||||||
env:
|
|
||||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
||||||
with:
|
|
||||||
upload_url: ${{ steps.create_release.outputs.upload_url }}
|
|
||||||
asset_path: ./Installer-generic.zip
|
|
||||||
asset_name: Installer-generic.zip
|
|
||||||
asset_content_type: application/zip
|
|
72
.gitlab-ci.yml
Normal file
72
.gitlab-ci.yml
Normal file
@ -0,0 +1,72 @@
|
|||||||
|
.shared_windows_runners:
|
||||||
|
tags:
|
||||||
|
- windows
|
||||||
|
|
||||||
|
uptool:
|
||||||
|
extends:
|
||||||
|
- .shared_windows_runners
|
||||||
|
stage: deploy
|
||||||
|
script: |
|
||||||
|
Invoke-WebRequest -Uri https://dotnet.microsoft.com/download/dotnet-core/scripts/v1/dotnet-install.ps1 -OutFile dotnet-install.ps1
|
||||||
|
Set-ExecutionPolicy Unrestricted -Scope Process
|
||||||
|
.\dotnet-install.ps1 -Channel 5.0
|
||||||
|
$env:Path = "C:\Users\gitlab_runner\AppData\Local\Microsoft\dotnet;" + $env:Path + ";C:\Users\gitlab_runner\AppData\Local\Microsoft\dotnet"
|
||||||
|
dotnet build --verbosity:m -p:Configuration=Release
|
||||||
|
cp ".\UpTool build tool\bin\Release\net5.0\package.zip" .\Tools.zip
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Release.zip .\UpTool2\bin\Release\net5.0-windows\UpTool2.exe
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Release.zip .\UpTool2\bin\Release\net5.0-windows\*.dll
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Release.zip .\UpTool2\bin\Release\net5.0-windows\UpTool2.runtimeconfig.json
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Release.zip .\UpToolCLI\bin\Release\net5.0\uptool.exe
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Release.zip .\UpToolCLI\bin\Release\net5.0\*.dll
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Release.zip .\UpToolCLI\bin\Release\net5.0\uptool.runtimeconfig.json
|
||||||
|
$asmver = $([Reflection.Assembly]::Loadfile($(pwd).Path + "\\UpTool2\\bin\\Release\\net5.0-windows\\UpTool2.dll").GetName().version.ToString())
|
||||||
|
$pkgtoolver = $([Reflection.Assembly]::Loadfile($(pwd).Path + "\\UpTool build tool\\bin\\Release\\net5.0\\pkgtool.dll").GetName().version.ToString())
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Installer-generic.zip .\InstallerCLI\bin\Release\net5.0\Installer.exe
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Installer-generic.zip .\InstallerCLI\bin\Release\net5.0\*.dll
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Installer-generic.zip .\InstallerCLI\bin\Release\net5.0\Installer.runtimeconfig.json
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Installer-generic.zip .\InstallerCLI\Info.txt
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Installer-gui.zip .\Installer\bin\Release\net5.0-windows\Installer.exe
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Installer-gui.zip .\Installer\bin\Release\net5.0-windows\*.dll
|
||||||
|
& "C:\Program Files\7-Zip\7z" a .\Installer-gui.zip .\Installer\bin\Release\net5.0-windows\Installer.runtimeconfig.json
|
||||||
|
[System.XML.XMLDocument]$xml=New-Object System.XML.XMLDocument
|
||||||
|
[System.XML.XMLElement]$app=$xml.CreateElement("app")
|
||||||
|
$xml.appendChild($app)
|
||||||
|
$app.appendChild($xml.CreateElement("Name")).InnerText = "UpTool2 package tools"
|
||||||
|
$app.appendChild($xml.CreateElement("Description")).InnerText = "Tools for automating package creation"
|
||||||
|
$app.appendChild($xml.CreateElement("Version")).InnerText = $pkgtoolver
|
||||||
|
$app.appendChild($xml.CreateElement("ID")).InnerText = "0e35d154-d0d3-45e0-b080-62f521263a44"
|
||||||
|
$app.appendChild($xml.CreateElement("File")).InnerText = $CI_PROJECT_URL + "/-/jobs/" + $CI_JOB_ID + "/artifacts/raw/Tools.zip"
|
||||||
|
$app.appendChild($xml.CreateElement("Hash")).InnerText = $(Get-FileHash .\Tools.zip).Hash
|
||||||
|
$app.appendChild($xml.CreateElement("MainFile")).InnerText = "pkgtool.exe"
|
||||||
|
$app.appendChild($xml.CreateElement("Icon")).InnerText = "https://gitlab.com/JFronny/UpTool2/-/raw/master/UpTool2.ico"
|
||||||
|
echo NULL > tools.xml
|
||||||
|
$xml.save($(gi .\tools.xml).Fullname)
|
||||||
|
[System.XML.XMLDocument]$xml=New-Object System.XML.XMLDocument
|
||||||
|
[System.XML.XMLElement]$app=$xml.CreateElement("meta")
|
||||||
|
$xml.appendChild($app)
|
||||||
|
$app.appendChild($xml.CreateElement("Version")).InnerText = $asmver
|
||||||
|
$app.appendChild($xml.CreateElement("File")).InnerText = $CI_PROJECT_URL + "/-/jobs/" + $CI_JOB_ID + "/artifacts/raw/Release.zip"
|
||||||
|
$app.appendChild($xml.CreateElement("Hash")).InnerText = $(Get-FileHash .\Release.zip).Hash
|
||||||
|
$app.appendChild($xml.CreateElement("Installer")).InnerText = $CI_PROJECT_URL + "/-/jobs/" + $CI_JOB_ID + "/artifacts/raw/Installer-generic.zip"
|
||||||
|
$app.appendChild($xml.CreateElement("InstallerHash")).InnerText = $(Get-FileHash .\Installer-generic.zip).Hash
|
||||||
|
$app.appendChild($xml.CreateElement("InstallerGui")).InnerText = $CI_PROJECT_URL + "/-/jobs/" + $CI_JOB_ID + "/artifacts/raw/Installer-gui.zip"
|
||||||
|
$app.appendChild($xml.CreateElement("InstallerGuiHash")).InnerText = $(Get-FileHash .\Installer-gui.zip).Hash
|
||||||
|
echo NULL > meta.xml
|
||||||
|
$xml.save($(gi .\meta.xml).Fullname)
|
||||||
|
#cd Installer
|
||||||
|
#dotnet publish -r win-x64 -c Release /p:PublishSingleFile=true /p:PublishTrimmed=true
|
||||||
|
#dotnet publish -r win-x86 -c Release /p:PublishSingleFile=true /p:PublishTrimmed=true
|
||||||
|
#cp .\bin\Release\net5.0-windows\win-x64\publish\Installer.exe ..\Installer-x64.exe
|
||||||
|
#cp .\bin\Release\net5.0-windows\win-x86\publish\Installer.exe ..\Installer-x86.exe
|
||||||
|
#cd ..
|
||||||
|
#Installer-x64 and Installer-x86 were also originally artifacts but there doesn't seem to be a x86-64 windows runner
|
||||||
|
artifacts:
|
||||||
|
paths:
|
||||||
|
- Release.zip
|
||||||
|
- Tools.zip
|
||||||
|
- Installer-generic.zip
|
||||||
|
- Installer-gui.zip
|
||||||
|
- meta.xml
|
||||||
|
- tools.xml
|
||||||
|
only:
|
||||||
|
- master
|
5
.idea/.idea.UpTool2/.idea/codeStyles/codeStyleConfig.xml
Normal file
5
.idea/.idea.UpTool2/.idea/codeStyles/codeStyleConfig.xml
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
<component name="ProjectCodeStyleConfiguration">
|
||||||
|
<state>
|
||||||
|
<option name="PREFERRED_PROJECT_CODE_STYLE" value="Default" />
|
||||||
|
</state>
|
||||||
|
</component>
|
@ -1,7 +1,7 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<project version="4">
|
<project version="4">
|
||||||
<component name="DiscordProjectSettings">
|
<component name="DiscordProjectSettings">
|
||||||
<option name="show" value="true" />
|
<option name="show" value="PROJECT_FILES" />
|
||||||
</component>
|
</component>
|
||||||
<component name="ProjectNotificationSettings">
|
<component name="ProjectNotificationSettings">
|
||||||
<option name="askShowProject" value="false" />
|
<option name="askShowProject" value="false" />
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
<project version="4">
|
<project version="4">
|
||||||
<component name="ProjectModuleManager">
|
<component name="ProjectModuleManager">
|
||||||
<modules>
|
<modules>
|
||||||
<module fileurl="file://$PROJECT_DIR$/.idea/.idea.UpTool2/riderModule.iml" filepath="$PROJECT_DIR$/.idea/.idea.UpTool2/riderModule.iml" />
|
<module fileurl="file://$PROJECT_DIR$/.idea/.idea.UpTool2/.idea/riderModule.iml" filepath="$PROJECT_DIR$/.idea/.idea.UpTool2/.idea/riderModule.iml" />
|
||||||
</modules>
|
</modules>
|
||||||
</component>
|
</component>
|
||||||
</project>
|
</project>
|
@ -1,6 +1,6 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<project version="4">
|
<project version="4">
|
||||||
<component name="RiderProjectSettingsUpdater">
|
<component name="RiderProjectSettingsUpdater">
|
||||||
<option name="vcsConfiguration" value="1" />
|
<option name="vcsConfiguration" value="2" />
|
||||||
</component>
|
</component>
|
||||||
</project>
|
</project>
|
7
.idea/.idea.UpTool2/.idea/riderModule.iml
Normal file
7
.idea/.idea.UpTool2/.idea/riderModule.iml
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<module type="RIDER_MODULE" version="4">
|
||||||
|
<component name="NewModuleRootManager">
|
||||||
|
<content url="file://$MODULE_DIR$/../.." />
|
||||||
|
<orderEntry type="sourceFolder" forTests="false" />
|
||||||
|
</component>
|
||||||
|
</module>
|
39
CLI.md
Normal file
39
CLI.md
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
# CLI
|
||||||
|
|
||||||
|
### Package Management
|
||||||
|
|
||||||
|
Installing a package (set \<package> to a file for local): uptool install \<package>
|
||||||
|
|
||||||
|
Upgrading a package: uptool upgrade \<package>
|
||||||
|
|
||||||
|
Reinstalling a package: uptool reinstall \<package>
|
||||||
|
|
||||||
|
Removing a package: uptool remove \<package>
|
||||||
|
|
||||||
|
Removing a package and all its configuration and data files: uptool purge \<package>
|
||||||
|
|
||||||
|
Upgrade all packages: uptool dist-upgrade
|
||||||
|
|
||||||
|
### Cache Management
|
||||||
|
|
||||||
|
List installed packages: uptool list
|
||||||
|
|
||||||
|
Search for a package: uptool search \<text>
|
||||||
|
|
||||||
|
Show package info: uptool show \<package>
|
||||||
|
|
||||||
|
Updating the cache: uptool update
|
||||||
|
|
||||||
|
### Repos Management
|
||||||
|
|
||||||
|
Add a repository: uptool add-repo \<name> \<link>
|
||||||
|
|
||||||
|
Remove a repository: uptool remove-repo \<name>
|
||||||
|
|
||||||
|
List repositories: uptool list-repo
|
||||||
|
|
||||||
|
### Other
|
||||||
|
|
||||||
|
Upgrading UpToolCLI: uptool upgrade-self
|
||||||
|
|
||||||
|
Start an app: uptool start \<package>
|
@ -1,8 +1,8 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk.WindowsDesktop">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<OutputType>WinExe</OutputType>
|
<OutputType>WinExe</OutputType>
|
||||||
<TargetFramework>netcoreapp3.1</TargetFramework>
|
<TargetFramework>net5.0-windows</TargetFramework>
|
||||||
<UseWindowsForms>true</UseWindowsForms>
|
<UseWindowsForms>true</UseWindowsForms>
|
||||||
<ApplicationIcon>..\UpTool2.ico</ApplicationIcon>
|
<ApplicationIcon>..\UpTool2.ico</ApplicationIcon>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
@ -11,4 +11,8 @@
|
|||||||
<Folder Include="Properties\" />
|
<Folder Include="Properties\" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<ProjectReference Include="..\UpToolLib\UpToolLib.csproj" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
</Project>
|
</Project>
|
87
Installer/InstallerForm.Designer.cs
generated
87
Installer/InstallerForm.Designer.cs
generated
@ -17,69 +17,56 @@
|
|||||||
{
|
{
|
||||||
components.Dispose();
|
components.Dispose();
|
||||||
}
|
}
|
||||||
|
_lib.Dispose();
|
||||||
base.Dispose(disposing);
|
base.Dispose(disposing);
|
||||||
}
|
}
|
||||||
|
|
||||||
#region Windows Form Designer generated code
|
#region Windows Form Designer generated code
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Required method for Designer support - do not modify
|
/// Required method for Designer support - do not modify
|
||||||
/// the contents of this method with the code editor.
|
/// the contents of this method with the code editor.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
private void InitializeComponent()
|
private void InitializeComponent()
|
||||||
{
|
{
|
||||||
System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(InstallerForm));
|
System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(Installer.InstallerForm));
|
||||||
this.install = new System.Windows.Forms.Button();
|
this.install = new System.Windows.Forms.Button();
|
||||||
this.installLabel = new System.Windows.Forms.Label();
|
this.installLabel = new System.Windows.Forms.Label();
|
||||||
this.progress = new System.Windows.Forms.ProgressBar();
|
this.progress = new System.Windows.Forms.ProgressBar();
|
||||||
this.processLabel = new System.Windows.Forms.Label();
|
this.processLabel = new System.Windows.Forms.Label();
|
||||||
this.log = new System.Windows.Forms.Button();
|
this.log = new System.Windows.Forms.Button();
|
||||||
|
this.startupBox = new System.Windows.Forms.CheckBox();
|
||||||
|
this.pathBox = new System.Windows.Forms.CheckBox();
|
||||||
|
this.updateAppsBox = new System.Windows.Forms.CheckBox();
|
||||||
this.SuspendLayout();
|
this.SuspendLayout();
|
||||||
//
|
this.install.Anchor = ((System.Windows.Forms.AnchorStyles) (((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left) | System.Windows.Forms.AnchorStyles.Right)));
|
||||||
// install
|
this.install.Location = new System.Drawing.Point(12, 116);
|
||||||
//
|
|
||||||
this.install.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left)
|
|
||||||
| System.Windows.Forms.AnchorStyles.Right)));
|
|
||||||
this.install.Location = new System.Drawing.Point(12, 92);
|
|
||||||
this.install.Name = "install";
|
this.install.Name = "install";
|
||||||
this.install.Size = new System.Drawing.Size(539, 27);
|
this.install.Size = new System.Drawing.Size(539, 27);
|
||||||
this.install.TabIndex = 0;
|
this.install.TabIndex = 0;
|
||||||
this.install.Text = "Install";
|
this.install.Text = "Install";
|
||||||
this.install.UseVisualStyleBackColor = true;
|
this.install.UseVisualStyleBackColor = true;
|
||||||
this.install.Click += new System.EventHandler(this.install_Click);
|
this.install.Click += new System.EventHandler(this.install_Click);
|
||||||
//
|
|
||||||
// installLabel
|
|
||||||
//
|
|
||||||
this.installLabel.AutoSize = true;
|
this.installLabel.AutoSize = true;
|
||||||
this.installLabel.Location = new System.Drawing.Point(12, 9);
|
this.installLabel.Location = new System.Drawing.Point(12, 9);
|
||||||
this.installLabel.Name = "installLabel";
|
this.installLabel.Name = "installLabel";
|
||||||
this.installLabel.Size = new System.Drawing.Size(550, 75);
|
this.installLabel.Size = new System.Drawing.Size(550, 75);
|
||||||
this.installLabel.TabIndex = 1;
|
this.installLabel.TabIndex = 1;
|
||||||
this.installLabel.Text = resources.GetString("installLabel.Text");
|
this.installLabel.Text = resources.GetString("installLabel.Text");
|
||||||
//
|
this.progress.Anchor = ((System.Windows.Forms.AnchorStyles) (((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left) | System.Windows.Forms.AnchorStyles.Right)));
|
||||||
// progress
|
this.progress.Location = new System.Drawing.Point(12, 116);
|
||||||
//
|
this.progress.Maximum = 8;
|
||||||
this.progress.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left)
|
|
||||||
| System.Windows.Forms.AnchorStyles.Right)));
|
|
||||||
this.progress.Location = new System.Drawing.Point(12, 92);
|
|
||||||
this.progress.Maximum = 6;
|
|
||||||
this.progress.Name = "progress";
|
this.progress.Name = "progress";
|
||||||
this.progress.Size = new System.Drawing.Size(539, 27);
|
this.progress.Size = new System.Drawing.Size(539, 27);
|
||||||
this.progress.TabIndex = 2;
|
this.progress.TabIndex = 2;
|
||||||
this.progress.Visible = false;
|
this.progress.Visible = false;
|
||||||
//
|
this.processLabel.Anchor = ((System.Windows.Forms.AnchorStyles) (((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left) | System.Windows.Forms.AnchorStyles.Right)));
|
||||||
// processLabel
|
|
||||||
//
|
|
||||||
this.processLabel.ForeColor = System.Drawing.SystemColors.ControlText;
|
this.processLabel.ForeColor = System.Drawing.SystemColors.ControlText;
|
||||||
this.processLabel.Location = new System.Drawing.Point(422, 70);
|
this.processLabel.Location = new System.Drawing.Point(386, 91);
|
||||||
this.processLabel.Name = "processLabel";
|
this.processLabel.Name = "processLabel";
|
||||||
this.processLabel.Size = new System.Drawing.Size(129, 19);
|
this.processLabel.Size = new System.Drawing.Size(165, 22);
|
||||||
this.processLabel.TabIndex = 3;
|
this.processLabel.TabIndex = 3;
|
||||||
this.processLabel.TextAlign = System.Drawing.ContentAlignment.TopRight;
|
this.processLabel.TextAlign = System.Drawing.ContentAlignment.TopRight;
|
||||||
//
|
this.log.Anchor = ((System.Windows.Forms.AnchorStyles) ((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right)));
|
||||||
// log
|
|
||||||
//
|
|
||||||
this.log.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right)));
|
|
||||||
this.log.Location = new System.Drawing.Point(524, 3);
|
this.log.Location = new System.Drawing.Point(524, 3);
|
||||||
this.log.Name = "log";
|
this.log.Name = "log";
|
||||||
this.log.Size = new System.Drawing.Size(36, 23);
|
this.log.Size = new System.Drawing.Size(36, 23);
|
||||||
@ -88,34 +75,60 @@
|
|||||||
this.log.UseVisualStyleBackColor = true;
|
this.log.UseVisualStyleBackColor = true;
|
||||||
this.log.Visible = false;
|
this.log.Visible = false;
|
||||||
this.log.Click += new System.EventHandler(this.log_Click);
|
this.log.Click += new System.EventHandler(this.log_Click);
|
||||||
//
|
this.startupBox.Anchor = ((System.Windows.Forms.AnchorStyles) ((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left)));
|
||||||
// InstallerForm
|
this.startupBox.AutoSize = true;
|
||||||
//
|
this.startupBox.Enabled = false;
|
||||||
|
this.startupBox.Location = new System.Drawing.Point(130, 91);
|
||||||
|
this.startupBox.Name = "startupBox";
|
||||||
|
this.startupBox.Size = new System.Drawing.Size(122, 19);
|
||||||
|
this.startupBox.TabIndex = 5;
|
||||||
|
this.startupBox.Text = "Update on Startup";
|
||||||
|
this.startupBox.CheckedChanged += new System.EventHandler(this.startupBox_CheckedChanged);
|
||||||
|
this.pathBox.Anchor = ((System.Windows.Forms.AnchorStyles) ((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left)));
|
||||||
|
this.pathBox.AutoSize = true;
|
||||||
|
this.pathBox.Location = new System.Drawing.Point(12, 91);
|
||||||
|
this.pathBox.Name = "pathBox";
|
||||||
|
this.pathBox.Size = new System.Drawing.Size(112, 19);
|
||||||
|
this.pathBox.TabIndex = 6;
|
||||||
|
this.pathBox.Text = "Register in PATH";
|
||||||
|
this.pathBox.CheckedChanged += new System.EventHandler(this.pathBox_CheckedChanged);
|
||||||
|
this.updateAppsBox.Anchor = ((System.Windows.Forms.AnchorStyles) ((System.Windows.Forms.AnchorStyles.Bottom | System.Windows.Forms.AnchorStyles.Left)));
|
||||||
|
this.updateAppsBox.AutoSize = true;
|
||||||
|
this.updateAppsBox.Enabled = false;
|
||||||
|
this.updateAppsBox.Location = new System.Drawing.Point(258, 91);
|
||||||
|
this.updateAppsBox.Name = "updateAppsBox";
|
||||||
|
this.updateAppsBox.Size = new System.Drawing.Size(94, 19);
|
||||||
|
this.updateAppsBox.TabIndex = 5;
|
||||||
|
this.updateAppsBox.Text = "Update Apps";
|
||||||
this.AutoScaleDimensions = new System.Drawing.SizeF(7F, 15F);
|
this.AutoScaleDimensions = new System.Drawing.SizeF(7F, 15F);
|
||||||
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
||||||
this.ClientSize = new System.Drawing.Size(563, 132);
|
this.ClientSize = new System.Drawing.Size(563, 156);
|
||||||
|
this.Controls.Add(this.updateAppsBox);
|
||||||
this.Controls.Add(this.log);
|
this.Controls.Add(this.log);
|
||||||
this.Controls.Add(this.processLabel);
|
this.Controls.Add(this.processLabel);
|
||||||
this.Controls.Add(this.progress);
|
this.Controls.Add(this.progress);
|
||||||
this.Controls.Add(this.installLabel);
|
this.Controls.Add(this.installLabel);
|
||||||
this.Controls.Add(this.install);
|
this.Controls.Add(this.install);
|
||||||
|
this.Controls.Add(this.startupBox);
|
||||||
|
this.Controls.Add(this.pathBox);
|
||||||
this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedDialog;
|
this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedDialog;
|
||||||
this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon")));
|
this.Icon = ((System.Drawing.Icon) (resources.GetObject("$this.Icon")));
|
||||||
this.Name = "InstallerForm";
|
this.Name = "InstallerForm";
|
||||||
this.ShowIcon = false;
|
this.ShowIcon = false;
|
||||||
this.Text = "UpTool2 Installer";
|
this.Text = "UpTool2 Installer";
|
||||||
this.ResumeLayout(false);
|
this.ResumeLayout(false);
|
||||||
this.PerformLayout();
|
this.PerformLayout();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
|
||||||
|
|
||||||
private System.Windows.Forms.Button install;
|
private System.Windows.Forms.Button install;
|
||||||
private System.Windows.Forms.Label installLabel;
|
private System.Windows.Forms.Label installLabel;
|
||||||
private System.Windows.Forms.ProgressBar progress;
|
|
||||||
private System.Windows.Forms.Label processLabel;
|
|
||||||
private System.Windows.Forms.Button log;
|
private System.Windows.Forms.Button log;
|
||||||
|
private System.Windows.Forms.CheckBox pathBox;
|
||||||
|
private System.Windows.Forms.Label processLabel;
|
||||||
|
private System.Windows.Forms.ProgressBar progress;
|
||||||
|
private System.Windows.Forms.CheckBox startupBox;
|
||||||
|
private System.Windows.Forms.CheckBox updateAppsBox;
|
||||||
|
#endregion
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,25 +1,40 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Drawing;
|
using System.Drawing;
|
||||||
using System.Globalization;
|
using System.Globalization;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.IO.Compression;
|
using System.IO.Compression;
|
||||||
|
using System.Linq;
|
||||||
using System.Net;
|
using System.Net;
|
||||||
using System.Security.Cryptography;
|
using System.Security.Cryptography;
|
||||||
using System.Threading;
|
using System.Threading;
|
||||||
using System.Windows.Forms;
|
using System.Windows.Forms;
|
||||||
using System.Xml.Linq;
|
using System.Xml.Linq;
|
||||||
|
using Microsoft.Win32;
|
||||||
|
using UpToolLib;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
|
||||||
namespace Installer
|
namespace Installer
|
||||||
{
|
{
|
||||||
public partial class InstallerForm : Form
|
public partial class InstallerForm : Form
|
||||||
{
|
{
|
||||||
private string Log = "";
|
private const string AppName = "UpTool2";
|
||||||
|
private readonly RegistryKey _rkApp;
|
||||||
|
private string _log = "";
|
||||||
|
private UpToolLibMain _lib;
|
||||||
|
|
||||||
public InstallerForm()
|
public InstallerForm()
|
||||||
{
|
{
|
||||||
|
_lib = new UpToolLibMain(new UtLibFunctionsGui(Log));
|
||||||
InitializeComponent();
|
InitializeComponent();
|
||||||
Step(0, "Initialized");
|
Step(0, "Initialized");
|
||||||
Log.TrimStart(Environment.NewLine.ToCharArray());
|
_log = _log.TrimStart(Environment.NewLine.ToCharArray());
|
||||||
|
_rkApp = Registry.CurrentUser.OpenSubKey(@"SOFTWARE\Microsoft\Windows\CurrentVersion\Run", true);
|
||||||
|
pathBox.Checked = !File.Exists(_lib.V1.PathTool.InfoXml) ||
|
||||||
|
Path.Content.Contains(Path.GetName(_lib.V1.PathTool.GetRelative("Install")));
|
||||||
|
startupBox.Checked = pathBox.Checked && _rkApp.GetValue(AppName) != null;
|
||||||
|
updateAppsBox.Checked = pathBox.Checked && startupBox.Checked &&
|
||||||
|
(string) _rkApp.GetValue(AppName) == "uptool dist-upgrade";
|
||||||
}
|
}
|
||||||
|
|
||||||
private void install_Click(object sender, EventArgs e)
|
private void install_Click(object sender, EventArgs e)
|
||||||
@ -28,33 +43,50 @@ namespace Installer
|
|||||||
try
|
try
|
||||||
{
|
{
|
||||||
progress.Visible = true;
|
progress.Visible = true;
|
||||||
WebClient client = new WebClient();
|
WebClient client = new();
|
||||||
Step(1, "Downloading metadata");
|
Step(1, "Downloading metadata");
|
||||||
XElement meta = XDocument.Load("https://github.com/JFronny/UpTool2/releases/latest/download/meta.xml")
|
XElement meta = XDocument
|
||||||
|
.Load("https://gitlab.com/JFronny/UpTool2/-/jobs/artifacts/master/raw/meta.xml?job=uptool")
|
||||||
.Element("meta");
|
.Element("meta");
|
||||||
Step(2, "Downloading binary");
|
Step(2, "Downloading binary");
|
||||||
byte[] dl = client.DownloadData(meta.Element("File").Value);
|
byte[] dl = client.DownloadData(meta.Element("File").Value);
|
||||||
Step(3, "Verifying integrity");
|
Step(3, "Verifying integrity");
|
||||||
using (SHA256CryptoServiceProvider sha256 = new SHA256CryptoServiceProvider())
|
using (SHA256CryptoServiceProvider sha256 = new())
|
||||||
{
|
{
|
||||||
string pkgHash = BitConverter.ToString(sha256.ComputeHash(dl)).Replace("-", string.Empty).ToUpper();
|
string pkgHash = BitConverter.ToString(sha256.ComputeHash(dl)).Replace("-", string.Empty).ToUpper();
|
||||||
if (pkgHash != meta.Element("Hash").Value.ToUpper())
|
if (pkgHash != meta.Element("Hash").Value.ToUpper())
|
||||||
throw new Exception(
|
throw new Exception(
|
||||||
$"The hash is not equal to the one stored in the repo:\r\nPackage: {pkgHash}\r\nOnline: {meta.Element("Hash").Value.ToUpper()}");
|
$@"The hash is not equal to the one stored in the repo:
|
||||||
|
Package: {pkgHash}
|
||||||
|
Online: {meta.Element("Hash").Value.ToUpper()}");
|
||||||
}
|
}
|
||||||
Step(4, "Extracting");
|
Step(4, "Extracting");
|
||||||
if (Directory.Exists(PathTool.GetRelative("Install")))
|
if (Directory.Exists(_lib.V1.PathTool.GetRelative("Install")))
|
||||||
Directory.Delete(PathTool.GetRelative("Install"), true);
|
Directory.Delete(_lib.V1.PathTool.GetRelative("Install"), true);
|
||||||
Directory.CreateDirectory(PathTool.GetRelative("Install"));
|
Directory.CreateDirectory(_lib.V1.PathTool.GetRelative("Install"));
|
||||||
using (MemoryStream ms = new MemoryStream(dl))
|
using (MemoryStream ms = new(dl))
|
||||||
{
|
{
|
||||||
using ZipArchive ar = new ZipArchive(ms);
|
using ZipArchive ar = new(ms);
|
||||||
ar.ExtractToDirectory(PathTool.GetRelative("Install"), true);
|
ar.ExtractToDirectory(_lib.V1.PathTool.GetRelative("Install"), true);
|
||||||
}
|
}
|
||||||
Step(5, "Creating shortcut");
|
Step(5, "Creating shortcut");
|
||||||
Shortcut.Make(PathTool.GetRelative("Install", "UpTool2.exe"),
|
Shortcut.Make(_lib.V1.PathTool.GetRelative("Install", "UpTool2.exe"),
|
||||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Programs), "UpTool2.lnk"));
|
System.IO.Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Programs),
|
||||||
Step(6, "Done!");
|
"UpTool2.lnk"));
|
||||||
|
Step(6, "Preparing Repos");
|
||||||
|
_lib.V1.XmlTool.FixXml();
|
||||||
|
_lib.V2.RepoManagement.FetchRepos();
|
||||||
|
if (pathBox.Checked)
|
||||||
|
{
|
||||||
|
Step(7, startupBox.Checked ? "Creating PATH & Autostart entry" : "Creating PATH entry");
|
||||||
|
if (!Path.Content.Contains(Path.GetName(_lib.V1.PathTool.GetRelative("Install"))))
|
||||||
|
Path.Append(_lib.V1.PathTool.GetRelative("Install"));
|
||||||
|
if (startupBox.Checked)
|
||||||
|
_rkApp.SetValue(AppName, updateAppsBox.Checked ? "uptool dist-upgrade" : "uptool upgrade-self");
|
||||||
|
else if (_rkApp.GetValue(AppName) != null)
|
||||||
|
_rkApp.DeleteValue(AppName, false);
|
||||||
|
}
|
||||||
|
Step(8, "Done!");
|
||||||
}
|
}
|
||||||
catch (Exception ex)
|
catch (Exception ex)
|
||||||
{
|
{
|
||||||
@ -81,9 +113,30 @@ namespace Installer
|
|||||||
{
|
{
|
||||||
progress.Value = p;
|
progress.Value = p;
|
||||||
processLabel.Text = text;
|
processLabel.Text = text;
|
||||||
Log += $"{Environment.NewLine}[{DateTime.Now.ToString(CultureInfo.InvariantCulture).Split(' ')[1]}] {text}";
|
Log(text);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void log_Click(object sender, EventArgs e) => new Thread(() => MessageBox.Show(Log)).Start();
|
private void Log(string text) => _log +=
|
||||||
|
$"{Environment.NewLine}[{DateTime.Now.ToString(CultureInfo.InvariantCulture).Split(' ')[1]}] {text}";
|
||||||
|
|
||||||
|
private void log_Click(object sender, EventArgs e) => new Thread(() => MessageBox.Show(_log)).Start();
|
||||||
|
|
||||||
|
private void pathBox_CheckedChanged(object sender, EventArgs e)
|
||||||
|
{
|
||||||
|
startupBox.Enabled = pathBox.Checked;
|
||||||
|
if (!pathBox.Checked)
|
||||||
|
{
|
||||||
|
startupBox.Checked = false;
|
||||||
|
updateAppsBox.Checked = false;
|
||||||
|
updateAppsBox.Enabled = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void startupBox_CheckedChanged(object sender, EventArgs e)
|
||||||
|
{
|
||||||
|
updateAppsBox.Enabled = startupBox.Checked;
|
||||||
|
if (!startupBox.Checked)
|
||||||
|
updateAppsBox.Checked = false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -61,7 +61,7 @@
|
|||||||
<value>Thank you for downloading UpTool2.
|
<value>Thank you for downloading UpTool2.
|
||||||
To prevent inconsistent behavior you will need to install this before running.
|
To prevent inconsistent behavior you will need to install this before running.
|
||||||
Files will be placed in %appdata%\UpTool2 and %appdata%\Microsoft\Windows\Start Menu\Programs
|
Files will be placed in %appdata%\UpTool2 and %appdata%\Microsoft\Windows\Start Menu\Programs
|
||||||
|
There will also be a new PATH Entry for your user.
|
||||||
Do you want to continue?</value>
|
Do you want to continue?</value>
|
||||||
</data>
|
</data>
|
||||||
<assembly alias="System.Drawing.Common" name="System.Drawing.Common, Version=4.0.2.0, Culture=neutral, PublicKeyToken=cc7b13ffcd2ddd51" />
|
<assembly alias="System.Drawing.Common" name="System.Drawing.Common, Version=4.0.2.0, Culture=neutral, PublicKeyToken=cc7b13ffcd2ddd51" />
|
||||||
|
19
Installer/PATH.cs
Normal file
19
Installer/PATH.cs
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
using System;
|
||||||
|
using System.Linq;
|
||||||
|
|
||||||
|
namespace Installer
|
||||||
|
{
|
||||||
|
public static class Path
|
||||||
|
{
|
||||||
|
public static string[] Content
|
||||||
|
{
|
||||||
|
get => Environment.GetEnvironmentVariable("path", EnvironmentVariableTarget.User).Split(';');
|
||||||
|
set => Environment.SetEnvironmentVariable("path", string.Join(';', value), EnvironmentVariableTarget.User);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void Append(string path, bool escape = true) =>
|
||||||
|
Content = Content.Append(escape ? GetName(path) : path).ToArray();
|
||||||
|
|
||||||
|
public static string GetName(string path) => System.IO.Path.GetFullPath(path);
|
||||||
|
}
|
||||||
|
}
|
@ -1,19 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.IO;
|
|
||||||
using System.Linq;
|
|
||||||
|
|
||||||
namespace Installer
|
|
||||||
{
|
|
||||||
internal static class PathTool
|
|
||||||
{
|
|
||||||
public static string dir =>
|
|
||||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), "UpTool2");
|
|
||||||
|
|
||||||
public static string tempPath => GetRelative("tmp");
|
|
||||||
public static string appsPath => GetRelative("Apps");
|
|
||||||
public static string InfoXml => GetRelative("info.xml");
|
|
||||||
|
|
||||||
public static string GetRelative(params string[] segments) =>
|
|
||||||
Path.Combine(new[] {dir}.Concat(segments).ToArray());
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,5 +1,6 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Windows.Forms;
|
using System.Windows.Forms;
|
||||||
|
using UpToolLib;
|
||||||
|
|
||||||
namespace Installer
|
namespace Installer
|
||||||
{
|
{
|
||||||
|
65
Installer/UTLibFunctions.cs
Normal file
65
Installer/UTLibFunctions.cs
Normal file
@ -0,0 +1,65 @@
|
|||||||
|
using System;
|
||||||
|
using System.Drawing;
|
||||||
|
using System.Drawing.Drawing2D;
|
||||||
|
using System.Drawing.Imaging;
|
||||||
|
using System.IO;
|
||||||
|
using System.Net;
|
||||||
|
using System.Windows.Forms;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
|
||||||
|
namespace Installer
|
||||||
|
{
|
||||||
|
internal class UtLibFunctionsGui : IExternalFunctionality
|
||||||
|
{
|
||||||
|
private readonly Action<string> _log;
|
||||||
|
public UtLibFunctionsGui(Action<string> log) => _log = log;
|
||||||
|
|
||||||
|
public Tuple<bool, byte[]> Download(Uri link)
|
||||||
|
{
|
||||||
|
using WebClient cli = new();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
return new Tuple<bool, byte[]>(true, cli.DownloadData(link));
|
||||||
|
}
|
||||||
|
catch
|
||||||
|
{
|
||||||
|
return new Tuple<bool, byte[]>(false, new byte[0]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public string FetchImageB64(Uri link)
|
||||||
|
{
|
||||||
|
using WebClient client = new();
|
||||||
|
Image src = Image.FromStream(
|
||||||
|
client.OpenRead(link));
|
||||||
|
Bitmap dest = new(70, 70);
|
||||||
|
dest.SetResolution(src.HorizontalResolution, src.VerticalResolution);
|
||||||
|
using (Graphics g = Graphics.FromImage(dest))
|
||||||
|
{
|
||||||
|
g.CompositingMode = CompositingMode.SourceCopy;
|
||||||
|
g.CompositingQuality = CompositingQuality.HighQuality;
|
||||||
|
g.InterpolationMode = InterpolationMode.HighQualityBicubic;
|
||||||
|
g.SmoothingMode = SmoothingMode.HighQuality;
|
||||||
|
g.PixelOffsetMode = PixelOffsetMode.HighQuality;
|
||||||
|
using ImageAttributes wrapMode = new();
|
||||||
|
wrapMode.SetWrapMode(WrapMode.TileFlipXY);
|
||||||
|
g.DrawImage(src, new Rectangle(0, 0, 70, 70), 0, 0, src.Width, src.Height,
|
||||||
|
GraphicsUnit.Pixel, wrapMode);
|
||||||
|
}
|
||||||
|
using MemoryStream ms = new();
|
||||||
|
dest.Save(ms, ImageFormat.Png);
|
||||||
|
return Convert.ToBase64String(ms.ToArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool YesNoDialog(string text, bool _) =>
|
||||||
|
MessageBox.Show(text, "", MessageBoxButtons.YesNo) == DialogResult.Yes;
|
||||||
|
|
||||||
|
public void OkDialog(string text) => MessageBox.Show(text);
|
||||||
|
public object GetDefaultIcon() => 0;
|
||||||
|
|
||||||
|
public object ImageFromB64(string b64) =>
|
||||||
|
(Bitmap) new ImageConverter().ConvertFrom(Convert.FromBase64String(b64));
|
||||||
|
|
||||||
|
public void Log(string text) => _log(text);
|
||||||
|
}
|
||||||
|
}
|
2
InstallerCLI/Info.txt
Normal file
2
InstallerCLI/Info.txt
Normal file
@ -0,0 +1,2 @@
|
|||||||
|
Use "Installer --help" for info
|
||||||
|
(on non-windows platforms, use the dotnet CLI to run Installer.dll)
|
19
InstallerCLI/InstallerCLI.csproj
Normal file
19
InstallerCLI/InstallerCLI.csproj
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<OutputType>Exe</OutputType>
|
||||||
|
<TargetFramework>net5.0</TargetFramework>
|
||||||
|
<AssemblyName>Installer</AssemblyName>
|
||||||
|
<RootNamespace>Installer</RootNamespace>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<ProjectReference Include="..\UpToolLib\UpToolLib.csproj" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<PackageReference Include="SixLabors.ImageSharp" Version="1.0.2" />
|
||||||
|
<PackageReference Include="System.CommandLine" Version="2.0.0-beta1.20574.7" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
</Project>
|
90
InstallerCLI/Program.cs
Normal file
90
InstallerCLI/Program.cs
Normal file
@ -0,0 +1,90 @@
|
|||||||
|
using System;
|
||||||
|
using System.CommandLine;
|
||||||
|
using System.CommandLine.Invocation;
|
||||||
|
using System.IO;
|
||||||
|
using System.IO.Compression;
|
||||||
|
using System.Net;
|
||||||
|
using System.Security.Cryptography;
|
||||||
|
using System.Threading;
|
||||||
|
using UpToolLib;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
|
||||||
|
namespace Installer
|
||||||
|
{
|
||||||
|
public static class Program
|
||||||
|
{
|
||||||
|
public static bool Basic;
|
||||||
|
private static UpToolLibMain _lib;
|
||||||
|
public static int Main(string[] args)
|
||||||
|
{
|
||||||
|
Thread.Sleep(2000);
|
||||||
|
try
|
||||||
|
{
|
||||||
|
Basic = args.Length > 0 && args[0].ToLower() == "--basic";
|
||||||
|
_lib = new UpToolLibMain(new UtLibFunctions());
|
||||||
|
RootCommand rootCommand = new();
|
||||||
|
rootCommand.AddGlobalOption(new Option<bool>("--basic",
|
||||||
|
"Use only basic console functionality. Must be the first parameter in the call"));
|
||||||
|
Command install = new("install", "Install UpTool")
|
||||||
|
{
|
||||||
|
new Option<bool>(new[] {"--noPrep", "-p"}, "Doesn't initialize repos. Use with caution!")
|
||||||
|
};
|
||||||
|
install.AddAlias("-i");
|
||||||
|
install.AddAlias("i");
|
||||||
|
install.Handler = CommandHandler.Create<bool>(Install);
|
||||||
|
rootCommand.AddCommand(install);
|
||||||
|
return rootCommand.InvokeAsync(args).Result;
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
Console.WriteLine($"FAILED: {e}");
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
_lib?.Dispose();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void Install(bool noPrep)
|
||||||
|
{
|
||||||
|
WebClient client = new();
|
||||||
|
Console.WriteLine("Downloading metadata");
|
||||||
|
UpdateCheck check =
|
||||||
|
_lib.V2.UpdateChecker.Check(
|
||||||
|
"https://gitlab.com/JFronny/UpTool2/-/jobs/artifacts/master/raw/meta.xml?job=uptool");
|
||||||
|
PathTool pathTool = _lib.V1.PathTool;
|
||||||
|
Console.WriteLine("Downloading binary");
|
||||||
|
byte[] dl = client.DownloadData(check.App);
|
||||||
|
Console.WriteLine("Verifying integrity");
|
||||||
|
using (SHA256CryptoServiceProvider sha256 = new())
|
||||||
|
{
|
||||||
|
string pkgHash = BitConverter.ToString(sha256.ComputeHash(dl)).Replace("-", string.Empty)
|
||||||
|
.ToUpper();
|
||||||
|
if (pkgHash != check.AppHash)
|
||||||
|
throw new Exception($@"The hash is not equal to the one stored in the repo:
|
||||||
|
Package: {pkgHash}
|
||||||
|
Online: {check.AppHash}");
|
||||||
|
}
|
||||||
|
Console.WriteLine("Extracting");
|
||||||
|
if (Directory.Exists(pathTool.GetRelative("Install")))
|
||||||
|
{
|
||||||
|
foreach (string file in Directory.GetFiles(pathTool.GetRelative("Install"))) File.Delete(file);
|
||||||
|
foreach (string dir in Directory.GetDirectories(pathTool.GetRelative("Install")))
|
||||||
|
if (Path.GetFileName(dir) != "tmp")
|
||||||
|
Directory.Delete(dir, true);
|
||||||
|
}
|
||||||
|
Directory.CreateDirectory(pathTool.GetRelative("Install"));
|
||||||
|
using (MemoryStream ms = new(dl))
|
||||||
|
{
|
||||||
|
using ZipArchive ar = new(ms);
|
||||||
|
ar.ExtractToDirectory(pathTool.GetRelative("Install"), true);
|
||||||
|
}
|
||||||
|
if (noPrep) return;
|
||||||
|
Console.WriteLine("Preparing Repos");
|
||||||
|
_lib.V1.XmlTool.FixXml();
|
||||||
|
_lib.V2.RepoManagement.FetchRepos();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
116
InstallerCLI/UTLibFunctions.cs
Normal file
116
InstallerCLI/UTLibFunctions.cs
Normal file
@ -0,0 +1,116 @@
|
|||||||
|
using System;
|
||||||
|
using System.IO;
|
||||||
|
using System.Net;
|
||||||
|
using System.Threading;
|
||||||
|
using SixLabors.ImageSharp;
|
||||||
|
using SixLabors.ImageSharp.Processing;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using static Installer.Program;
|
||||||
|
|
||||||
|
namespace Installer
|
||||||
|
{
|
||||||
|
public class UtLibFunctions : IExternalFunctionality
|
||||||
|
{
|
||||||
|
public Tuple<bool, byte[]> Download(Uri link)
|
||||||
|
{
|
||||||
|
using WebClient client = new();
|
||||||
|
byte[] result = new byte[0];
|
||||||
|
bool finished = false;
|
||||||
|
bool success = true;
|
||||||
|
client.DownloadDataCompleted += (sender, e) =>
|
||||||
|
{
|
||||||
|
success = !e.Cancelled;
|
||||||
|
if (success)
|
||||||
|
result = e.Result;
|
||||||
|
finished = true;
|
||||||
|
};
|
||||||
|
client.DownloadProgressChanged += (sender, e) =>
|
||||||
|
{
|
||||||
|
if (!Basic)
|
||||||
|
{
|
||||||
|
Console.Write(
|
||||||
|
$"{new string('=', e.ProgressPercentage / 10)}[{e.ProgressPercentage}]{new string('-', 10 - e.ProgressPercentage / 10)}");
|
||||||
|
Console.CursorLeft = 0;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
client.DownloadDataAsync(link);
|
||||||
|
while (!finished)
|
||||||
|
Thread.Sleep(100);
|
||||||
|
return new Tuple<bool, byte[]>(success, result);
|
||||||
|
}
|
||||||
|
|
||||||
|
public string FetchImageB64(Uri link)
|
||||||
|
{
|
||||||
|
using WebClient client = new();
|
||||||
|
using Image image = Image.Load(client.OpenRead(link));
|
||||||
|
using MemoryStream ms = new();
|
||||||
|
image.SaveAsPng(ms);
|
||||||
|
return Convert.ToBase64String(ms.ToArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool YesNoDialog(string text, bool defaultVal)
|
||||||
|
{
|
||||||
|
if (Basic)
|
||||||
|
{
|
||||||
|
Console.WriteLine(text);
|
||||||
|
Console.WriteLine($"Selecting: {defaultVal}");
|
||||||
|
return defaultVal;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
bool choosing = true;
|
||||||
|
bool current = defaultVal;
|
||||||
|
Console.WriteLine(text);
|
||||||
|
while (choosing)
|
||||||
|
{
|
||||||
|
Console.CursorLeft = 0;
|
||||||
|
Console.BackgroundColor = current ? ConsoleColor.White : ConsoleColor.Black;
|
||||||
|
Console.ForegroundColor = current ? ConsoleColor.Black : ConsoleColor.White;
|
||||||
|
Console.Write("Yes");
|
||||||
|
Console.ResetColor();
|
||||||
|
Console.Write(" ");
|
||||||
|
Console.BackgroundColor = current ? ConsoleColor.Black : ConsoleColor.White;
|
||||||
|
Console.ForegroundColor = current ? ConsoleColor.White : ConsoleColor.Black;
|
||||||
|
Console.Write("No");
|
||||||
|
Console.ResetColor();
|
||||||
|
switch (Console.ReadKey().Key)
|
||||||
|
{
|
||||||
|
case ConsoleKey.LeftArrow:
|
||||||
|
case ConsoleKey.RightArrow:
|
||||||
|
current = !current;
|
||||||
|
break;
|
||||||
|
case ConsoleKey.Enter:
|
||||||
|
choosing = false;
|
||||||
|
break;
|
||||||
|
case ConsoleKey.Escape:
|
||||||
|
current = defaultVal;
|
||||||
|
choosing = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Console.ResetColor();
|
||||||
|
Console.WriteLine($" Selecting: {current}");
|
||||||
|
return current;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void OkDialog(string text)
|
||||||
|
{
|
||||||
|
if (Basic)
|
||||||
|
Console.WriteLine(text);
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Console.WriteLine(text);
|
||||||
|
Console.BackgroundColor = ConsoleColor.White;
|
||||||
|
Console.Write("OK");
|
||||||
|
Console.ResetColor();
|
||||||
|
Console.ReadKey();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public object GetDefaultIcon() => 0;
|
||||||
|
|
||||||
|
public object ImageFromB64(string b64) => 0;
|
||||||
|
public void Log(string text) => Console.WriteLine(text);
|
||||||
|
}
|
||||||
|
}
|
21
LICENSE
Normal file
21
LICENSE
Normal file
@ -0,0 +1,21 @@
|
|||||||
|
MIT License
|
||||||
|
|
||||||
|
Copyright (c) 2020 J. Fronny
|
||||||
|
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
of this software and associated documentation files (the "Software"), to deal
|
||||||
|
in the Software without restriction, including without limitation the rights
|
||||||
|
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
copies of the Software, and to permit persons to whom the Software is
|
||||||
|
furnished to do so, subject to the following conditions:
|
||||||
|
|
||||||
|
The above copyright notice and this permission notice shall be included in all
|
||||||
|
copies or substantial portions of the Software.
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
SOFTWARE.
|
20
README.md
20
README.md
@ -1,11 +1,8 @@
|
|||||||
# UpTool2
|
# UpTool2
|
||||||
Downloading software from online repos since 2019\
|
Downloading software from online repos since 2019\
|
||||||
[![CodeFactor](https://www.codefactor.io/repository/github/jfronny/uptool2/badge)](https://www.codefactor.io/repository/github/jfronny/uptool2)
|
[![GitLab pipeline](https://img.shields.io/gitlab/pipeline/JFronny/UpTool2)](https://gitlab.com/JFronny/UpTool2/builds)
|
||||||
[![GitHub release (latest by date)](https://img.shields.io/github/v/release/JFronny/UpTool2)](https://github.com/JFronny/UpTool2/releases/latest)
|
|
||||||
[![GitHub repo size](https://img.shields.io/github/repo-size/JFronny/UpTool2)](https://github.com/JFronny/UpTool2/archive/master.zip)
|
|
||||||
[![GitHub All Releases](https://img.shields.io/github/downloads/JFronny/UpTool2/total)](https://github.com/JFronny/UpTool2/releases)
|
|
||||||
[![Discord](https://img.shields.io/discord/466965965658128384)](https://discordapp.com/invite/UjhHBqt)
|
[![Discord](https://img.shields.io/discord/466965965658128384)](https://discordapp.com/invite/UjhHBqt)
|
||||||
[![Default Repo](https://img.shields.io/badge/Default-Repo-informational)](https://gist.github.com/JFronny/f1ccbba3d8a2f5862592bb29fdb612c4)
|
[![Default Repo](https://img.shields.io/badge/Default-Repo-informational)](https://gitlab.com/JFronny/UpTool2/snippets/1988600)
|
||||||
## How to automate UpTool2 deployments
|
## How to automate UpTool2 deployments
|
||||||
You will want the assembly version to automatically increment.
|
You will want the assembly version to automatically increment.
|
||||||
To achieve this you have to add this:\
|
To achieve this you have to add this:\
|
||||||
@ -15,15 +12,15 @@ Now you can add this\
|
|||||||
```if exist "$(SolutionDir)Data\pkgtool.exe" ($(SolutionDir)Data\pkgtool.exe build --noLogo --binDir .) else if exist "%appdata%\UpTool2\Apps\0e35d154-d0d3-45e0-b080-62f521263a44\app\pkgtool.exe" ("%appdata%\UpTool2\Apps\0e35d154-d0d3-45e0-b080-62f521263a44\app\pkgtool.exe" build --noLogo --binDir .) else echo Cound not find Package build tools, skipping```\
|
```if exist "$(SolutionDir)Data\pkgtool.exe" ($(SolutionDir)Data\pkgtool.exe build --noLogo --binDir .) else if exist "%appdata%\UpTool2\Apps\0e35d154-d0d3-45e0-b080-62f521263a44\app\pkgtool.exe" ("%appdata%\UpTool2\Apps\0e35d154-d0d3-45e0-b080-62f521263a44\app\pkgtool.exe" build --noLogo --binDir .) else echo Cound not find Package build tools, skipping```\
|
||||||
as a PostBuild event to automatically run pkgtool. Customize this if you need to.\
|
as a PostBuild event to automatically run pkgtool. Customize this if you need to.\
|
||||||
For GitHub actions I wrote [this](https://github.com/JFronny/CC-Clicker/blob/master/.github/workflows/main.yml).\
|
For GitHub actions I wrote [this](https://github.com/JFronny/CC-Clicker/blob/master/.github/workflows/main.yml).\
|
||||||
If you copy it, make sure to replace the descriptions and ID under the `Fenerate XML` step\
|
If you copy it, make sure to replace the descriptions and ID under the `Generate XML` step\
|
||||||
You can also add something like this to your Readme: [![UpTool2](https://img.shields.io/badge/dynamic/xml?color=informational&label=UpTool2&query=%2F%2Fapp%2FVersion&url=https%3A%2F%2Fgithub.com%2FJFronny%2FCC-Clicker%2Freleases%2Fdownload%2F1.0.7380.28108%2Fapp.xml&style=flat)](https://jfronny.github.io/home/uptool)\
|
You can also add something like this to your Readme: [![UpTool2](https://img.shields.io/badge/Get%20it-on%20UpTool2-blue)](https://jfronny.gitlab.io/home/uptool)\
|
||||||
(Look at the source for the MD Code)
|
(Look at the source for the MD Code)
|
||||||
## Folder layout
|
## Folder layout
|
||||||
- %APPDATA%\UpTool2
|
- %APPDATA%\UpTool2
|
||||||
- Apps
|
- Apps
|
||||||
- __APPGUID
|
- __APPGUID
|
||||||
- `info.xml` Local copy of some app information, like [this](https://github.com/JFronny/UpTool2#app-layout) but missing ID, File, Hash and Icon
|
- `info.xml` Local copy of some app information, like [this](https://gitlab.com/JFronny/UpTool2#app-layout) but missing ID, File, Hash, Platform and Icon
|
||||||
- [`package.zip`](https://github.com/JFronny/UpTool2#package-layout) The package that was downloaded on install
|
- [`package.zip`](https://gitlab.com/JFronny/UpTool2#package-layout) The package that was downloaded on install
|
||||||
- `app` The app install path
|
- `app` The app install path
|
||||||
- `__APPFILES` Copy of the app files from above, may contain user-configs
|
- `__APPFILES` Copy of the app files from above, may contain user-configs
|
||||||
- `info.xml` File used by UpTool2 for saving info
|
- `info.xml` File used by UpTool2 for saving info
|
||||||
@ -33,7 +30,7 @@ You can also add something like this to your Readme: [![UpTool2](https://img.shi
|
|||||||
- `Name` The display name of the repository
|
- `Name` The display name of the repository
|
||||||
- `Link` The source of the repo xml
|
- `Link` The source of the repo xml
|
||||||
- `Local Repo` A preprocessed copy of the online repos
|
- `Local Repo` A preprocessed copy of the online repos
|
||||||
- [`__APP`](https://github.com/JFronny/UpTool2#app-layout) A normal app with the icon processed as Base64
|
- [`__APP`](https://gitlab.com/JFronny/UpTool2#app-layout) A normal app with the icon processed as Base64
|
||||||
- `Install` The folder containing the actual tool
|
- `Install` The folder containing the actual tool
|
||||||
- `__ZIP CONTENTS` The app files
|
- `__ZIP CONTENTS` The app files
|
||||||
- `tmp` A temporary folder used during updates
|
- `tmp` A temporary folder used during updates
|
||||||
@ -42,7 +39,7 @@ You can also add something like this to your Readme: [![UpTool2](https://img.shi
|
|||||||
- `repo` The main repo tag
|
- `repo` The main repo tag
|
||||||
- `__APPLINK` Links to external app XMLs
|
- `__APPLINK` Links to external app XMLs
|
||||||
- `__REPOLINK` Links to external repos
|
- `__REPOLINK` Links to external repos
|
||||||
- [`__APP`](https://github.com/JFronny/UpTool2#app-layout) Apps
|
- [`__APP`](https://gitlab.com/JFronny/UpTool2#app-layout) Apps
|
||||||
## App layout
|
## App layout
|
||||||
- app
|
- app
|
||||||
- `Name` Name of the application
|
- `Name` Name of the application
|
||||||
@ -53,6 +50,7 @@ You can also add something like this to your Readme: [![UpTool2](https://img.shi
|
|||||||
- `Hash` The files SHA256 Hash
|
- `Hash` The files SHA256 Hash
|
||||||
- `Icon` The apps icon, (optional)
|
- `Icon` The apps icon, (optional)
|
||||||
- `MainFile` Main binary, used for starting, (optional)
|
- `MainFile` Main binary, used for starting, (optional)
|
||||||
|
- `Platform` The platform this works on (optional, defaults to current)
|
||||||
## Package layout
|
## Package layout
|
||||||
- `Install.bat` The script for installing the app
|
- `Install.bat` The script for installing the app
|
||||||
- `Remove.bat` The script for removing the app
|
- `Remove.bat` The script for removing the app
|
||||||
|
31
UpTool build tool/BatchScripts.cs
Normal file
31
UpTool build tool/BatchScripts.cs
Normal file
@ -0,0 +1,31 @@
|
|||||||
|
using System;
|
||||||
|
using System.IO;
|
||||||
|
|
||||||
|
namespace UpTool_build_tool
|
||||||
|
{
|
||||||
|
internal static class BatchScripts
|
||||||
|
{
|
||||||
|
public static Tuple<string, string> Create(bool shortcuts, string? mainBin, string programName,
|
||||||
|
string? postInstall, string? postRemove)
|
||||||
|
{
|
||||||
|
string installBat = "@echo off\r\necho INSTALL";
|
||||||
|
string removeBat = "@echo off\r\necho REMOVE";
|
||||||
|
if (shortcuts)
|
||||||
|
{
|
||||||
|
installBat += "\r\n";
|
||||||
|
installBat +=
|
||||||
|
$@"powershell ""$s=(New-Object -COM WScript.Shell).CreateShortcut('%appdata%\Microsoft\Windows\Start Menu\Programs\{programName}.lnk');$s.TargetPath='%cd%\{Path.GetFileName(mainBin)}';$s.Save()""";
|
||||||
|
removeBat += "\r\n";
|
||||||
|
removeBat += $@"del ""%appdata%\Microsoft\Windows\Start Menu\Programs\{programName}.lnk""";
|
||||||
|
}
|
||||||
|
if (!string.IsNullOrWhiteSpace(mainBin))
|
||||||
|
{
|
||||||
|
removeBat += "\r\n";
|
||||||
|
removeBat += $@"taskkill /f /im ""{Path.GetFileName(mainBin)}""";
|
||||||
|
}
|
||||||
|
installBat += $"\r\n{postInstall}";
|
||||||
|
removeBat += $"\r\n{postRemove}";
|
||||||
|
return new Tuple<string, string>(installBat, removeBat);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -5,7 +5,7 @@ using System.Diagnostics;
|
|||||||
using System.IO;
|
using System.IO;
|
||||||
using System.IO.Compression;
|
using System.IO.Compression;
|
||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
using CC_Functions.Misc;
|
using CC_Functions.Core;
|
||||||
|
|
||||||
namespace UpTool_build_tool
|
namespace UpTool_build_tool
|
||||||
{
|
{
|
||||||
@ -14,21 +14,29 @@ namespace UpTool_build_tool
|
|||||||
public static int Main(string[] args)
|
public static int Main(string[] args)
|
||||||
{
|
{
|
||||||
RootCommand rootCommand = new RootCommand();
|
RootCommand rootCommand = new RootCommand();
|
||||||
Command build = new Command("build", "Builds a generic package with or without shortcuts from a directory");
|
Command build = new Command("build", "Builds a generic package with or without shortcuts from a directory")
|
||||||
build.AddOption(new Option<string>("--binDir", "Directory to package"));
|
{
|
||||||
build.AddOption(new Option<string>("--mainBin", "The applications main binary"));
|
new Option<string>("--binDir", "Directory to package"),
|
||||||
build.AddOption(new Option<string>("--packageFile", "Directory to package"));
|
new Option<string>("--mainBin", () => "FIND_BIN", "The applications main binary"),
|
||||||
build.AddOption(new Option<string>("--postInstall", () => "", "Command(s) to run after installing the package"));
|
new Option<string>("--packageFile", "Directory to package"),
|
||||||
build.AddOption(new Option<string>("--postRemove", () => "", "Command(s) to run after removing the package"));
|
new Option<string>("--postInstall", () => "",
|
||||||
build.AddOption(new Option<bool>("--noLogo", "Disables the logo"));
|
"Command(s) to run after installing the package (This will be pasted into the .bat AND .sh file)"),
|
||||||
build.AddOption(new Option<bool>("--noShortcuts",
|
new Option<string>("--postRemove", () => "",
|
||||||
"When this is enabled the scripts will not generate a start-menu item"));
|
"Command(s) to run after removing the package (This will be pasted into the .bat AND .sh file)"),
|
||||||
build.Handler = CommandHandler.Create<string, string, string, string, string, bool, bool>(Build);
|
new Option<bool>("--noLogo", "Disables the logo"),
|
||||||
|
new Option<bool>("--noShortcuts",
|
||||||
|
"When this is enabled the scripts will not generate a start-menu item"),
|
||||||
|
new Option<bool>("--noWine",
|
||||||
|
"This indicates that your program supports multiple platforms natively and doesn't require WINE")
|
||||||
|
};
|
||||||
|
build.Handler =
|
||||||
|
CommandHandler.Create((Action<string?, string, string, string, string, bool, bool, bool>) Build);
|
||||||
rootCommand.AddCommand(build);
|
rootCommand.AddCommand(build);
|
||||||
return rootCommand.InvokeAsync(args).Result;
|
return rootCommand.InvokeAsync(args).Result;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static void Build(string binDir, string mainBin, string packageFile, string postInstall, string postRemove, bool noLogo, bool noShortcuts)
|
private static void Build(string? binDir, string? mainBin, string? packageFile, string? postInstall,
|
||||||
|
string? postRemove, bool noLogo, bool noShortcuts, bool noWine)
|
||||||
{
|
{
|
||||||
Stopwatch watch = Stopwatch.StartNew();
|
Stopwatch watch = Stopwatch.StartNew();
|
||||||
if (!noLogo)
|
if (!noLogo)
|
||||||
@ -52,9 +60,7 @@ namespace UpTool_build_tool
|
|||||||
{
|
{
|
||||||
archive.AddDirectory(binDir, "Data", new[] {".xml", ".pdb"}, new[] {packageFile});
|
archive.AddDirectory(binDir, "Data", new[] {".xml", ".pdb"}, new[] {packageFile});
|
||||||
Console.WriteLine("Creating batch scripts...");
|
Console.WriteLine("Creating batch scripts...");
|
||||||
string installBat = "@echo off\r\necho INSTALL";
|
if (mainBin == "FIND_BIN")
|
||||||
string removeBat = "@echo off\r\necho REMOVE";
|
|
||||||
if (string.IsNullOrWhiteSpace(mainBin))
|
|
||||||
{
|
{
|
||||||
string[] tmp = Directory.GetFiles(binDir, "*.exe");
|
string[] tmp = Directory.GetFiles(binDir, "*.exe");
|
||||||
if (tmp.Length > 0)
|
if (tmp.Length > 0)
|
||||||
@ -68,35 +74,22 @@ namespace UpTool_build_tool
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
string programName = Path.GetFileNameWithoutExtension(mainBin);
|
string programName = Path.GetFileNameWithoutExtension(mainBin);
|
||||||
if (!noShortcuts)
|
(string installBat, string removeBat) =
|
||||||
{
|
BatchScripts.Create(!noShortcuts, mainBin, programName, postInstall, postRemove);
|
||||||
installBat += "\r\n";
|
archive.AddFile("Install.bat", installBat);
|
||||||
installBat +=
|
archive.AddFile("Remove.bat", removeBat);
|
||||||
$@"powershell ""$s=(New-Object -COM WScript.Shell).CreateShortcut('%appdata%\Microsoft\Windows\Start Menu\Programs\{programName}.lnk');$s.TargetPath='%cd%\{mainBin}';$s.Save()""";
|
ShScripts.Create(archive.AddFile, !noShortcuts, mainBin, programName, postInstall, postRemove, !noWine);
|
||||||
removeBat += "\r\n";
|
|
||||||
removeBat += $@"del ""%appdata%\Microsoft\Windows\Start Menu\Programs\{programName}.lnk""";
|
|
||||||
}
|
|
||||||
if (!string.IsNullOrWhiteSpace(mainBin))
|
|
||||||
{
|
|
||||||
removeBat += "\r\n";
|
|
||||||
removeBat += $@"taskkill /f /im ""{Path.GetFileName(mainBin)}""";
|
|
||||||
}
|
|
||||||
installBat += $"\r\n{postInstall}";
|
|
||||||
removeBat += $"\r\n{postRemove}";
|
|
||||||
using (Stream s = archive.CreateEntry("Install.bat").Open())
|
|
||||||
{
|
|
||||||
using StreamWriter writer = new StreamWriter(s);
|
|
||||||
writer.Write(installBat);
|
|
||||||
}
|
|
||||||
using (Stream s = archive.CreateEntry("Remove.bat").Open())
|
|
||||||
{
|
|
||||||
using StreamWriter writer = new StreamWriter(s);
|
|
||||||
writer.Write(removeBat);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
watch.Stop();
|
watch.Stop();
|
||||||
Console.WriteLine($"Completed package creation in {watch.Elapsed}");
|
Console.WriteLine($"Completed package creation in {watch.Elapsed}");
|
||||||
Console.WriteLine($"Output file: {Path.GetFullPath(packageFile)}");
|
Console.WriteLine($"Output file: {Path.GetFullPath(packageFile)}");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static void AddFile(this ZipArchive archive, string fileName, string content)
|
||||||
|
{
|
||||||
|
using Stream s = archive.CreateEntry(fileName).Open();
|
||||||
|
using StreamWriter writer = new StreamWriter(s);
|
||||||
|
writer.Write(content);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -1,35 +0,0 @@
|
|||||||
using System.Reflection;
|
|
||||||
using System.Runtime.InteropServices;
|
|
||||||
|
|
||||||
// General Information about an assembly is controlled through the following
|
|
||||||
// set of attributes. Change these attribute values to modify the information
|
|
||||||
// associated with an assembly.
|
|
||||||
[assembly: AssemblyTitle("UpTool_build_tool")]
|
|
||||||
[assembly: AssemblyDescription("")]
|
|
||||||
[assembly: AssemblyConfiguration("")]
|
|
||||||
[assembly: AssemblyCompany("")]
|
|
||||||
[assembly: AssemblyProduct("UpTool_build_tool")]
|
|
||||||
[assembly: AssemblyCopyright("Copyright © 2020")]
|
|
||||||
[assembly: AssemblyTrademark("")]
|
|
||||||
[assembly: AssemblyCulture("")]
|
|
||||||
|
|
||||||
// Setting ComVisible to false makes the types in this assembly not visible
|
|
||||||
// to COM components. If you need to access a type in this assembly from
|
|
||||||
// COM, set the ComVisible attribute to true on that type.
|
|
||||||
[assembly: ComVisible(false)]
|
|
||||||
|
|
||||||
// The following GUID is for the ID of the typelib if this project is exposed to COM
|
|
||||||
[assembly: Guid("AAB8D6BA-3A43-4DC4-95EE-6757482B77FD")]
|
|
||||||
|
|
||||||
// Version information for an assembly consists of the following four values:
|
|
||||||
//
|
|
||||||
// Major Version
|
|
||||||
// Minor Version
|
|
||||||
// Build Number
|
|
||||||
// Revision
|
|
||||||
//
|
|
||||||
// You can specify all the values or you can default the Build and Revision Numbers
|
|
||||||
// by using the '*' as shown below:
|
|
||||||
// [assembly: AssemblyVersion("1.0.*")]
|
|
||||||
[assembly: AssemblyVersion("1.0.*")]
|
|
||||||
[assembly: AssemblyFileVersion("1.0.0.0")]
|
|
41
UpTool build tool/ShScripts.cs
Normal file
41
UpTool build tool/ShScripts.cs
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
using System;
|
||||||
|
using System.IO;
|
||||||
|
using System.Text.RegularExpressions;
|
||||||
|
|
||||||
|
namespace UpTool_build_tool
|
||||||
|
{
|
||||||
|
internal static class ShScripts
|
||||||
|
{
|
||||||
|
public static void Create(Action<string, string> fileSave, bool shortcuts, string? mainBin, string programName,
|
||||||
|
string? postInstall, string? postRemove, bool wine)
|
||||||
|
{
|
||||||
|
Regex rgx = new Regex("[^a-z0-9]");
|
||||||
|
Regex upRgx = new Regex("[^a-zA-Z0-9 -]");
|
||||||
|
string lnkName = $"~/.local/share/applications/{rgx.Replace(programName.ToLower(), "")}.desktop";
|
||||||
|
string installSh = "#!/bin/bash\necho INSTALL";
|
||||||
|
string removeSh = "#!/bin/bash\necho REMOVE";
|
||||||
|
if (shortcuts)
|
||||||
|
{
|
||||||
|
installSh += $@"
|
||||||
|
echo ""[Desktop Entry]"" > {lnkName}
|
||||||
|
echo ""Exec={(wine ? "wine " : "")}{Path.GetFileName(mainBin)}"" >> {lnkName}
|
||||||
|
echo ""Icon=application/x-shellscript"" >> {lnkName}
|
||||||
|
echo ""Name={upRgx.Replace(programName, "")}"" >> {lnkName}
|
||||||
|
echo ""StartupNotify=false"" >> {lnkName}
|
||||||
|
echo ""Terminal=false"" >> {lnkName}
|
||||||
|
echo ""Type=Application"" >> {lnkName}";
|
||||||
|
removeSh += "\r\n";
|
||||||
|
removeSh += $@"rm {lnkName}";
|
||||||
|
}
|
||||||
|
if (!string.IsNullOrWhiteSpace(mainBin))
|
||||||
|
{
|
||||||
|
removeSh += "\r\n";
|
||||||
|
removeSh += $@"pkill -f ""{Path.GetFileName(mainBin)}""";
|
||||||
|
}
|
||||||
|
installSh += $"\r\n{postInstall}";
|
||||||
|
removeSh += $"\r\n{postRemove}";
|
||||||
|
fileSave("Install.sh", installSh);
|
||||||
|
fileSave("Remove.sh", removeSh);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -1,20 +1,21 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>netcoreapp3.1</TargetFramework>
|
<TargetFramework>net5.0</TargetFramework>
|
||||||
<OutputType>Exe</OutputType>
|
<OutputType>Exe</OutputType>
|
||||||
<RootNamespace>UpTool_build_tool</RootNamespace>
|
<RootNamespace>UpTool_build_tool</RootNamespace>
|
||||||
<AssemblyName>pkgtool</AssemblyName>
|
<AssemblyName>pkgtool</AssemblyName>
|
||||||
<Deterministic>false</Deterministic>
|
<Deterministic>false</Deterministic>
|
||||||
<LangVersion>8</LangVersion>
|
<LangVersion>8</LangVersion>
|
||||||
<Nullable>enable</Nullable>
|
<Nullable>enable</Nullable>
|
||||||
<GenerateAssemblyInfo>false</GenerateAssemblyInfo>
|
<AssemblyVersion>1.0.*</AssemblyVersion>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<PostBuildEvent>.\pkgtool.exe build --noLogo --noShortcuts --binDir .</PostBuildEvent>
|
<PostBuildEvent Condition="'$(OS)' != 'Windows_NT'">.\pkgtool build --noLogo --noShortcuts --binDir . --mainBin ""</PostBuildEvent>
|
||||||
|
<PostBuildEvent Condition="'$(OS)' == 'Windows_NT'">pkgtool.exe build --noLogo --noShortcuts --binDir . --mainBin ""</PostBuildEvent>
|
||||||
<ApplicationIcon>..\UpTool2.ico</ApplicationIcon>
|
<ApplicationIcon>..\UpTool2.ico</ApplicationIcon>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="CC-Functions.Misc" Version="1.1.7384.27745" />
|
<PackageReference Include="CC-Functions.Core" Version="1.1.7628.34181" />
|
||||||
<PackageReference Include="System.CommandLine" Version="2.0.0-beta1.20104.2" />
|
<PackageReference Include="System.CommandLine" Version="2.0.0-beta1.20574.7" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
</Project>
|
</Project>
|
||||||
|
56
UpTool2.sln
56
UpTool2.sln
@ -8,14 +8,33 @@ EndProject
|
|||||||
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{9841227C-3F1B-4C32-8123-3DB2CF4E15EE}"
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{9841227C-3F1B-4C32-8123-3DB2CF4E15EE}"
|
||||||
ProjectSection(SolutionItems) = preProject
|
ProjectSection(SolutionItems) = preProject
|
||||||
.gitignore = .gitignore
|
.gitignore = .gitignore
|
||||||
.github\workflows\main.yml = .github\workflows\main.yml
|
|
||||||
README.md = README.md
|
README.md = README.md
|
||||||
|
CLI.md = CLI.md
|
||||||
|
.gitlab-ci.yml = .gitlab-ci.yml
|
||||||
EndProjectSection
|
EndProjectSection
|
||||||
EndProject
|
EndProject
|
||||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "UpTool build tool", "UpTool build tool\UpTool build tool.csproj", "{AAB8D6BA-3A43-4DC4-95EE-6757482B77FD}"
|
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "UpTool build tool", "UpTool build tool\UpTool build tool.csproj", "{AAB8D6BA-3A43-4DC4-95EE-6757482B77FD}"
|
||||||
EndProject
|
EndProject
|
||||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Installer", "Installer\Installer.csproj", "{1D273392-3796-4BE9-A67F-BB402315D52D}"
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Installer", "Installer\Installer.csproj", "{1D273392-3796-4BE9-A67F-BB402315D52D}"
|
||||||
EndProject
|
EndProject
|
||||||
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "UpToolLib", "UpToolLib\UpToolLib.csproj", "{FACD621F-6C6D-4D4B-B322-4364A0F9B4C2}"
|
||||||
|
EndProject
|
||||||
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "UpToolCLI", "UpToolCLI\UpToolCLI.csproj", "{3EC369B9-D927-4A53-BE1A-7E7006081BCE}"
|
||||||
|
EndProject
|
||||||
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "GUI", "GUI", "{EA919DFD-766B-423C-99DF-C99356592842}"
|
||||||
|
EndProject
|
||||||
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "CLI", "CLI", "{3CFAB991-C12A-4B51-BC91-6965133DAF53}"
|
||||||
|
EndProject
|
||||||
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Common", "Common", "{0E778462-504C-4183-A27E-44EEE7B8CCDD}"
|
||||||
|
EndProject
|
||||||
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "InstallerCLI", "InstallerCLI\InstallerCLI.csproj", "{493B2CC5-29E9-4F10-A2F5-E10B9584D667}"
|
||||||
|
EndProject
|
||||||
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "UpToolEto", "UpToolEto\UpToolEto\UpToolEto.csproj", "{213FF69B-426E-475F-8A77-0A20EA4257C2}"
|
||||||
|
EndProject
|
||||||
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "UpToolEto.Gtk", "UpToolEto\UpToolEto.Gtk\UpToolEto.Gtk.csproj", "{8A544AEA-3081-45C9-BED2-7E424EB287B1}"
|
||||||
|
EndProject
|
||||||
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "UpToolEto.Wpf", "UpToolEto\UpToolEto.Wpf\UpToolEto.Wpf.csproj", "{C89EC79F-CC2B-4B8E-B4CB-D4DFD30A58AB}"
|
||||||
|
EndProject
|
||||||
Global
|
Global
|
||||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||||
Debug|Any CPU = Debug|Any CPU
|
Debug|Any CPU = Debug|Any CPU
|
||||||
@ -34,6 +53,30 @@ Global
|
|||||||
{1D273392-3796-4BE9-A67F-BB402315D52D}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
{1D273392-3796-4BE9-A67F-BB402315D52D}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
{1D273392-3796-4BE9-A67F-BB402315D52D}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
{1D273392-3796-4BE9-A67F-BB402315D52D}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
{1D273392-3796-4BE9-A67F-BB402315D52D}.Release|Any CPU.Build.0 = Release|Any CPU
|
{1D273392-3796-4BE9-A67F-BB402315D52D}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{FACD621F-6C6D-4D4B-B322-4364A0F9B4C2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{FACD621F-6C6D-4D4B-B322-4364A0F9B4C2}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{FACD621F-6C6D-4D4B-B322-4364A0F9B4C2}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{FACD621F-6C6D-4D4B-B322-4364A0F9B4C2}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{3EC369B9-D927-4A53-BE1A-7E7006081BCE}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{3EC369B9-D927-4A53-BE1A-7E7006081BCE}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{3EC369B9-D927-4A53-BE1A-7E7006081BCE}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{3EC369B9-D927-4A53-BE1A-7E7006081BCE}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{493B2CC5-29E9-4F10-A2F5-E10B9584D667}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{493B2CC5-29E9-4F10-A2F5-E10B9584D667}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{493B2CC5-29E9-4F10-A2F5-E10B9584D667}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{493B2CC5-29E9-4F10-A2F5-E10B9584D667}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{213FF69B-426E-475F-8A77-0A20EA4257C2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{213FF69B-426E-475F-8A77-0A20EA4257C2}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{213FF69B-426E-475F-8A77-0A20EA4257C2}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{213FF69B-426E-475F-8A77-0A20EA4257C2}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{8A544AEA-3081-45C9-BED2-7E424EB287B1}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{8A544AEA-3081-45C9-BED2-7E424EB287B1}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{8A544AEA-3081-45C9-BED2-7E424EB287B1}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{8A544AEA-3081-45C9-BED2-7E424EB287B1}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{C89EC79F-CC2B-4B8E-B4CB-D4DFD30A58AB}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{C89EC79F-CC2B-4B8E-B4CB-D4DFD30A58AB}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{C89EC79F-CC2B-4B8E-B4CB-D4DFD30A58AB}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{C89EC79F-CC2B-4B8E-B4CB-D4DFD30A58AB}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
EndGlobalSection
|
EndGlobalSection
|
||||||
GlobalSection(SolutionProperties) = preSolution
|
GlobalSection(SolutionProperties) = preSolution
|
||||||
HideSolutionNode = FALSE
|
HideSolutionNode = FALSE
|
||||||
@ -41,4 +84,15 @@ Global
|
|||||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||||
SolutionGuid = {008127DC-F473-4709-A763-75F5FCED93AB}
|
SolutionGuid = {008127DC-F473-4709-A763-75F5FCED93AB}
|
||||||
EndGlobalSection
|
EndGlobalSection
|
||||||
|
GlobalSection(NestedProjects) = preSolution
|
||||||
|
{FACD621F-6C6D-4D4B-B322-4364A0F9B4C2} = {0E778462-504C-4183-A27E-44EEE7B8CCDD}
|
||||||
|
{AAB8D6BA-3A43-4DC4-95EE-6757482B77FD} = {0E778462-504C-4183-A27E-44EEE7B8CCDD}
|
||||||
|
{C0C1E002-9E13-4E8F-A035-DBDC5128E00E} = {EA919DFD-766B-423C-99DF-C99356592842}
|
||||||
|
{3EC369B9-D927-4A53-BE1A-7E7006081BCE} = {3CFAB991-C12A-4B51-BC91-6965133DAF53}
|
||||||
|
{1D273392-3796-4BE9-A67F-BB402315D52D} = {EA919DFD-766B-423C-99DF-C99356592842}
|
||||||
|
{493B2CC5-29E9-4F10-A2F5-E10B9584D667} = {3CFAB991-C12A-4B51-BC91-6965133DAF53}
|
||||||
|
{213FF69B-426E-475F-8A77-0A20EA4257C2} = {EA919DFD-766B-423C-99DF-C99356592842}
|
||||||
|
{8A544AEA-3081-45C9-BED2-7E424EB287B1} = {EA919DFD-766B-423C-99DF-C99356592842}
|
||||||
|
{C89EC79F-CC2B-4B8E-B4CB-D4DFD30A58AB} = {EA919DFD-766B-423C-99DF-C99356592842}
|
||||||
|
EndGlobalSection
|
||||||
EndGlobal
|
EndGlobal
|
||||||
|
@ -1,14 +0,0 @@
|
|||||||
using System;
|
|
||||||
|
|
||||||
namespace UpTool2.DataStructures
|
|
||||||
{
|
|
||||||
[Flags]
|
|
||||||
public enum Status
|
|
||||||
{
|
|
||||||
Not_Installed = 1,
|
|
||||||
Updatable = 2,
|
|
||||||
Installed = 4,
|
|
||||||
Local = 8,
|
|
||||||
All = 15
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,14 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using UpTool2.DataStructures;
|
|
||||||
|
|
||||||
namespace UpTool2
|
|
||||||
{
|
|
||||||
internal static class GlobalVariables
|
|
||||||
{
|
|
||||||
public static readonly Dictionary<Guid, App> Apps = new Dictionary<Guid, App>();
|
|
||||||
public static bool RelE = true;
|
|
||||||
public static Action ReloadElements;
|
|
||||||
public static Version minimumVer => Version.Parse("0.0.0.0");
|
|
||||||
}
|
|
||||||
}
|
|
71
UpTool2/MainForm.Designer.cs
generated
71
UpTool2/MainForm.Designer.cs
generated
@ -46,13 +46,18 @@
|
|||||||
this.controls_settings = new System.Windows.Forms.Button();
|
this.controls_settings = new System.Windows.Forms.Button();
|
||||||
this.controls_reload = new System.Windows.Forms.Button();
|
this.controls_reload = new System.Windows.Forms.Button();
|
||||||
this.toolTip = new System.Windows.Forms.ToolTip(this.components);
|
this.toolTip = new System.Windows.Forms.ToolTip(this.components);
|
||||||
|
this.changesButton = new System.Windows.Forms.Button();
|
||||||
this.searchPackageDialog = new System.Windows.Forms.OpenFileDialog();
|
this.searchPackageDialog = new System.Windows.Forms.OpenFileDialog();
|
||||||
|
this.changesPanel = new System.Windows.Forms.Panel();
|
||||||
|
this.progressBar1 = new System.Windows.Forms.ProgressBar();
|
||||||
|
this.changesLabel = new System.Windows.Forms.Label();
|
||||||
this.infoPanel.SuspendLayout();
|
this.infoPanel.SuspendLayout();
|
||||||
((System.ComponentModel.ISupportInitialize)(this.splitContainer)).BeginInit();
|
((System.ComponentModel.ISupportInitialize)(this.splitContainer)).BeginInit();
|
||||||
this.splitContainer.Panel1.SuspendLayout();
|
this.splitContainer.Panel1.SuspendLayout();
|
||||||
this.splitContainer.Panel2.SuspendLayout();
|
this.splitContainer.Panel2.SuspendLayout();
|
||||||
this.splitContainer.SuspendLayout();
|
this.splitContainer.SuspendLayout();
|
||||||
this.optionsPanel.SuspendLayout();
|
this.optionsPanel.SuspendLayout();
|
||||||
|
this.changesPanel.SuspendLayout();
|
||||||
this.SuspendLayout();
|
this.SuspendLayout();
|
||||||
//
|
//
|
||||||
// sidebarPanel
|
// sidebarPanel
|
||||||
@ -62,7 +67,7 @@
|
|||||||
this.sidebarPanel.Dock = System.Windows.Forms.DockStyle.Fill;
|
this.sidebarPanel.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||||
this.sidebarPanel.Location = new System.Drawing.Point(0, 68);
|
this.sidebarPanel.Location = new System.Drawing.Point(0, 68);
|
||||||
this.sidebarPanel.Name = "sidebarPanel";
|
this.sidebarPanel.Name = "sidebarPanel";
|
||||||
this.sidebarPanel.Size = new System.Drawing.Size(312, 451);
|
this.sidebarPanel.Size = new System.Drawing.Size(312, 425);
|
||||||
this.sidebarPanel.TabIndex = 0;
|
this.sidebarPanel.TabIndex = 0;
|
||||||
//
|
//
|
||||||
// infoPanel
|
// infoPanel
|
||||||
@ -76,7 +81,7 @@
|
|||||||
this.infoPanel.Dock = System.Windows.Forms.DockStyle.Fill;
|
this.infoPanel.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||||
this.infoPanel.Location = new System.Drawing.Point(0, 0);
|
this.infoPanel.Location = new System.Drawing.Point(0, 0);
|
||||||
this.infoPanel.Name = "infoPanel";
|
this.infoPanel.Name = "infoPanel";
|
||||||
this.infoPanel.Size = new System.Drawing.Size(616, 519);
|
this.infoPanel.Size = new System.Drawing.Size(616, 493);
|
||||||
this.infoPanel.TabIndex = 1;
|
this.infoPanel.TabIndex = 1;
|
||||||
//
|
//
|
||||||
// action_run
|
// action_run
|
||||||
@ -128,9 +133,12 @@
|
|||||||
//
|
//
|
||||||
// infoPanel_Description
|
// infoPanel_Description
|
||||||
//
|
//
|
||||||
|
this.infoPanel_Description.Anchor = ((System.Windows.Forms.AnchorStyles)((((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Bottom)
|
||||||
|
| System.Windows.Forms.AnchorStyles.Left)
|
||||||
|
| System.Windows.Forms.AnchorStyles.Right)));
|
||||||
this.infoPanel_Description.Location = new System.Drawing.Point(3, 51);
|
this.infoPanel_Description.Location = new System.Drawing.Point(3, 51);
|
||||||
this.infoPanel_Description.Name = "infoPanel_Description";
|
this.infoPanel_Description.Name = "infoPanel_Description";
|
||||||
this.infoPanel_Description.Size = new System.Drawing.Size(611, 458);
|
this.infoPanel_Description.Size = new System.Drawing.Size(611, 439);
|
||||||
this.infoPanel_Description.TabIndex = 1;
|
this.infoPanel_Description.TabIndex = 1;
|
||||||
//
|
//
|
||||||
// infoPanel_Title
|
// infoPanel_Title
|
||||||
@ -158,7 +166,7 @@
|
|||||||
//
|
//
|
||||||
this.splitContainer.Panel2.Controls.Add(this.infoPanel);
|
this.splitContainer.Panel2.Controls.Add(this.infoPanel);
|
||||||
this.splitContainer.Panel2MinSize = 160;
|
this.splitContainer.Panel2MinSize = 160;
|
||||||
this.splitContainer.Size = new System.Drawing.Size(933, 519);
|
this.splitContainer.Size = new System.Drawing.Size(933, 493);
|
||||||
this.splitContainer.SplitterDistance = 312;
|
this.splitContainer.SplitterDistance = 312;
|
||||||
this.splitContainer.SplitterWidth = 5;
|
this.splitContainer.SplitterWidth = 5;
|
||||||
this.splitContainer.TabIndex = 0;
|
this.splitContainer.TabIndex = 0;
|
||||||
@ -237,16 +245,63 @@
|
|||||||
this.toolTip.ReshowDelay = 100;
|
this.toolTip.ReshowDelay = 100;
|
||||||
this.toolTip.ShowAlways = true;
|
this.toolTip.ShowAlways = true;
|
||||||
//
|
//
|
||||||
|
// changesButton
|
||||||
|
//
|
||||||
|
this.changesButton.Anchor = ((System.Windows.Forms.AnchorStyles)((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Right)));
|
||||||
|
this.changesButton.Location = new System.Drawing.Point(906, 0);
|
||||||
|
this.changesButton.Name = "changesButton";
|
||||||
|
this.changesButton.Size = new System.Drawing.Size(27, 26);
|
||||||
|
this.changesButton.TabIndex = 4;
|
||||||
|
this.changesButton.Text = "→";
|
||||||
|
this.toolTip.SetToolTip(this.changesButton, "Perform changes");
|
||||||
|
this.changesButton.UseVisualStyleBackColor = true;
|
||||||
|
this.changesButton.Click += new System.EventHandler(this.changesButton_Click);
|
||||||
|
//
|
||||||
// searchPackageDialog
|
// searchPackageDialog
|
||||||
//
|
//
|
||||||
this.searchPackageDialog.Filter = "Packages (*.zip)|*.zip";
|
this.searchPackageDialog.Filter = "Packages (*.zip)|*.zip";
|
||||||
//
|
//
|
||||||
|
// changesPanel
|
||||||
|
//
|
||||||
|
this.changesPanel.Controls.Add(this.progressBar1);
|
||||||
|
this.changesPanel.Controls.Add(this.changesButton);
|
||||||
|
this.changesPanel.Controls.Add(this.changesLabel);
|
||||||
|
this.changesPanel.Dock = System.Windows.Forms.DockStyle.Bottom;
|
||||||
|
this.changesPanel.Location = new System.Drawing.Point(0, 493);
|
||||||
|
this.changesPanel.Name = "changesPanel";
|
||||||
|
this.changesPanel.Size = new System.Drawing.Size(933, 26);
|
||||||
|
this.changesPanel.TabIndex = 1;
|
||||||
|
this.changesPanel.Visible = false;
|
||||||
|
//
|
||||||
|
// progressBar1
|
||||||
|
//
|
||||||
|
this.progressBar1.Anchor = ((System.Windows.Forms.AnchorStyles)(((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Bottom)
|
||||||
|
| System.Windows.Forms.AnchorStyles.Right)));
|
||||||
|
this.progressBar1.Location = new System.Drawing.Point(714, 0);
|
||||||
|
this.progressBar1.Name = "progressBar1";
|
||||||
|
this.progressBar1.Size = new System.Drawing.Size(186, 26);
|
||||||
|
this.progressBar1.Step = 1;
|
||||||
|
this.progressBar1.TabIndex = 5;
|
||||||
|
//
|
||||||
|
// changesLabel
|
||||||
|
//
|
||||||
|
this.changesLabel.Anchor = System.Windows.Forms.AnchorStyles.Left;
|
||||||
|
this.changesLabel.AutoSize = true;
|
||||||
|
this.changesLabel.Location = new System.Drawing.Point(7, 5);
|
||||||
|
this.changesLabel.Name = "changesLabel";
|
||||||
|
this.changesLabel.Size = new System.Drawing.Size(119, 15);
|
||||||
|
this.changesLabel.TabIndex = 0;
|
||||||
|
this.changesLabel.Text = "No Changes Selected";
|
||||||
|
this.changesLabel.TextAlign = System.Drawing.ContentAlignment.MiddleLeft;
|
||||||
|
this.changesLabel.Click += new System.EventHandler(this.changesLabel_Click);
|
||||||
|
//
|
||||||
// MainForm
|
// MainForm
|
||||||
//
|
//
|
||||||
this.AutoScaleDimensions = new System.Drawing.SizeF(7F, 15F);
|
this.AutoScaleDimensions = new System.Drawing.SizeF(7F, 15F);
|
||||||
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
||||||
this.ClientSize = new System.Drawing.Size(933, 519);
|
this.ClientSize = new System.Drawing.Size(933, 519);
|
||||||
this.Controls.Add(this.splitContainer);
|
this.Controls.Add(this.splitContainer);
|
||||||
|
this.Controls.Add(this.changesPanel);
|
||||||
this.HelpButton = true;
|
this.HelpButton = true;
|
||||||
this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon")));
|
this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon")));
|
||||||
this.MinimumSize = new System.Drawing.Size(631, 269);
|
this.MinimumSize = new System.Drawing.Size(631, 269);
|
||||||
@ -262,11 +317,13 @@
|
|||||||
this.splitContainer.ResumeLayout(false);
|
this.splitContainer.ResumeLayout(false);
|
||||||
this.optionsPanel.ResumeLayout(false);
|
this.optionsPanel.ResumeLayout(false);
|
||||||
this.optionsPanel.PerformLayout();
|
this.optionsPanel.PerformLayout();
|
||||||
|
this.changesPanel.ResumeLayout(false);
|
||||||
|
this.changesPanel.PerformLayout();
|
||||||
this.ResumeLayout(false);
|
this.ResumeLayout(false);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
#endregion
|
||||||
|
|
||||||
private System.Windows.Forms.FlowLayoutPanel sidebarPanel;
|
private System.Windows.Forms.FlowLayoutPanel sidebarPanel;
|
||||||
private System.Windows.Forms.Panel infoPanel;
|
private System.Windows.Forms.Panel infoPanel;
|
||||||
@ -285,6 +342,10 @@
|
|||||||
private System.Windows.Forms.Button action_run;
|
private System.Windows.Forms.Button action_run;
|
||||||
private System.Windows.Forms.Button controls_upload;
|
private System.Windows.Forms.Button controls_upload;
|
||||||
private System.Windows.Forms.OpenFileDialog searchPackageDialog;
|
private System.Windows.Forms.OpenFileDialog searchPackageDialog;
|
||||||
|
private System.Windows.Forms.Panel changesPanel;
|
||||||
|
private System.Windows.Forms.Label changesLabel;
|
||||||
|
private System.Windows.Forms.Button changesButton;
|
||||||
|
private System.Windows.Forms.ProgressBar progressBar1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,33 +1,36 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Diagnostics;
|
using System.Collections.Generic;
|
||||||
using System.Drawing;
|
using System.Drawing;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.IO.Compression;
|
|
||||||
using System.Reflection;
|
|
||||||
using System.Windows.Forms;
|
|
||||||
using UpTool2.DataStructures;
|
|
||||||
using UpTool2.Properties;
|
|
||||||
using UpTool2.Tool;
|
|
||||||
#if DEBUG
|
|
||||||
using System.Threading;
|
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
#endif
|
using System.Reflection;
|
||||||
|
using System.Threading;
|
||||||
|
using System.Windows.Forms;
|
||||||
|
using UpToolLib;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using System.Diagnostics;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
using UpToolLib.v2.TaskQueue;
|
||||||
|
|
||||||
namespace UpTool2
|
namespace UpTool2
|
||||||
{
|
{
|
||||||
public sealed partial class MainForm : Form
|
public sealed partial class MainForm : Form
|
||||||
{
|
{
|
||||||
HelpEventHandler help;
|
private readonly HelpEventHandler _help;
|
||||||
|
private List<AppTask> _tasks;
|
||||||
|
|
||||||
public MainForm()
|
public MainForm()
|
||||||
{
|
{
|
||||||
GlobalVariables.ReloadElements = ReloadElements;
|
|
||||||
InitializeComponent();
|
InitializeComponent();
|
||||||
help = MainForm_HelpRequested;
|
_tasks = new List<AppTask>();
|
||||||
HelpRequested += help;
|
_help = MainForm_HelpRequested;
|
||||||
|
HelpRequested += _help;
|
||||||
filterBox.DataSource = Enum.GetValues(typeof(Status));
|
filterBox.DataSource = Enum.GetValues(typeof(Status));
|
||||||
if (Program.Online)
|
if (Program.Online)
|
||||||
{
|
{
|
||||||
RepoManagement.FetchRepos();
|
Program.SetSplash(8, "Fetching repositories");
|
||||||
|
Program.Lib.V2.RepoManagement.FetchRepos();
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -36,90 +39,67 @@ namespace UpTool2
|
|||||||
filterBox.Enabled = false;
|
filterBox.Enabled = false;
|
||||||
filterBox.SelectedIndex = 2;
|
filterBox.SelectedIndex = 2;
|
||||||
}
|
}
|
||||||
Program.SetSplash(8, "Reloading data");
|
Program.SetSplash(9, "Reloading data");
|
||||||
ReloadElements();
|
ReloadElements();
|
||||||
if (!Directory.Exists(PathTool.appsPath))
|
if (!Directory.Exists(Program.Lib.V1.PathTool.AppsPath))
|
||||||
Directory.CreateDirectory(PathTool.appsPath);
|
Directory.CreateDirectory(Program.Lib.V1.PathTool.AppsPath);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void Action_install_Click(object sender, EventArgs e)
|
private void Action_install_Click(object sender, EventArgs e)
|
||||||
{
|
{
|
||||||
bool trying = true;
|
App tmp = (App) action_install.Tag;
|
||||||
while (trying)
|
if (_tasks.Any(s => s is InstallTask t && t.App == tmp))
|
||||||
{
|
{
|
||||||
#if !DEBUG
|
_tasks = _tasks.Where(s => !(s is InstallTask t) || t.App != tmp).ToList();
|
||||||
try
|
action_install.ResetBackColor();
|
||||||
{
|
|
||||||
#endif
|
|
||||||
AppInstall.Install((App) action_install.Tag);
|
|
||||||
trying = false;
|
|
||||||
#if !DEBUG
|
|
||||||
}
|
|
||||||
catch (Exception e1)
|
|
||||||
{
|
|
||||||
if (!GlobalVariables.RelE)
|
|
||||||
throw;
|
|
||||||
trying = MessageBox.Show(e1.ToString(), "Install failed", MessageBoxButtons.RetryCancel) ==
|
|
||||||
DialogResult.Retry;
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
_tasks.Add(Program.Lib.V2.TaskFactory.CreateInstall(tmp, ReloadElements));
|
||||||
|
action_install.BackColor = Color.Green;
|
||||||
|
}
|
||||||
|
UpdateChangesLabel();
|
||||||
}
|
}
|
||||||
|
|
||||||
private void Action_remove_Click(object sender, EventArgs e)
|
private void Action_remove_Click(object sender, EventArgs e)
|
||||||
{
|
{
|
||||||
try
|
App tmp = (App) action_install.Tag;
|
||||||
|
if (_tasks.Any(s => s is RemoveTask t && t.App == tmp))
|
||||||
{
|
{
|
||||||
string app = ((App) action_remove.Tag).appPath;
|
_tasks = _tasks.Where(s => !(s is RemoveTask t) || t.App != tmp).ToList();
|
||||||
string tmp = PathTool.tempPath;
|
action_remove.ResetBackColor();
|
||||||
if (Directory.Exists(tmp))
|
|
||||||
Directory.Delete(tmp, true);
|
|
||||||
Directory.CreateDirectory(tmp);
|
|
||||||
ZipFile.ExtractToDirectory(Path.Combine(app, "package.zip"), tmp);
|
|
||||||
Process.Start(new ProcessStartInfo
|
|
||||||
{
|
|
||||||
FileName = "cmd.exe",
|
|
||||||
Arguments = $"/C \"{Path.Combine(tmp, "Remove.bat")}\"",
|
|
||||||
WorkingDirectory = Path.Combine(app, "app"),
|
|
||||||
CreateNoWindow = true,
|
|
||||||
WindowStyle = ProcessWindowStyle.Hidden
|
|
||||||
}).WaitForExit();
|
|
||||||
Directory.Delete(tmp, true);
|
|
||||||
Directory.Delete(app, true);
|
|
||||||
if (GlobalVariables.RelE)
|
|
||||||
ReloadElements();
|
|
||||||
}
|
}
|
||||||
catch (Exception e1)
|
else
|
||||||
{
|
{
|
||||||
if (!GlobalVariables.RelE)
|
_tasks.Add(Program.Lib.V2.TaskFactory.CreateRemove(tmp, ReloadElements));
|
||||||
throw;
|
action_remove.BackColor = Color.Green;
|
||||||
MessageBox.Show(e1.ToString(), "Removal failed");
|
|
||||||
}
|
}
|
||||||
|
UpdateChangesLabel();
|
||||||
}
|
}
|
||||||
|
|
||||||
private void controls_upload_Click(object sender, EventArgs e)
|
private void controls_upload_Click(object sender, EventArgs e)
|
||||||
{
|
{
|
||||||
#if !DEBUG
|
if (searchPackageDialog.ShowDialog() != DialogResult.OK)
|
||||||
try
|
return;
|
||||||
|
if (!_tasks.Any(s => s is UploadTask t && t.ZipFile == searchPackageDialog.FileName))
|
||||||
|
_tasks.Add(Program.Lib.V2.TaskFactory.CreateUpload(searchPackageDialog.FileName, AppNameDialog.Show(), ReloadElements));
|
||||||
|
UpdateChangesLabel();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void Action_update_Click(object sender, EventArgs e)
|
||||||
|
{
|
||||||
|
App tmp = (App) action_install.Tag;
|
||||||
|
if (_tasks.Any(s => s is UpdateTask t && t.App == tmp))
|
||||||
{
|
{
|
||||||
#endif
|
_tasks = _tasks.Where(s => !(s is UpdateTask t) || t.App != tmp).ToList();
|
||||||
if (searchPackageDialog.ShowDialog() != DialogResult.OK)
|
action_update.ResetBackColor();
|
||||||
return;
|
|
||||||
Guid id = Guid.NewGuid();
|
|
||||||
while (GlobalVariables.Apps.ContainsKey(id) || Directory.Exists(PathTool.GetAppPath(id)))
|
|
||||||
id = Guid.NewGuid();
|
|
||||||
App appI = new App(AppNameDialog.Show(), "Locally installed package, removal only",
|
|
||||||
GlobalVariables.minimumVer, "", true, "", id, Color.Red, Resources.C_64.ToBitmap(), false, "");
|
|
||||||
AppInstall.InstallZip(searchPackageDialog.FileName, appI);
|
|
||||||
#if !DEBUG
|
|
||||||
}
|
}
|
||||||
catch (Exception e1)
|
else
|
||||||
{
|
{
|
||||||
if (!GlobalVariables.RelE)
|
_tasks.Add(Program.Lib.V2.TaskFactory.CreateUpdate(tmp, ReloadElements));
|
||||||
throw;
|
action_update.BackColor = Color.Green;
|
||||||
MessageBox.Show(e1.ToString(), "Install failed");
|
|
||||||
}
|
}
|
||||||
#endif
|
UpdateChangesLabel();
|
||||||
}
|
}
|
||||||
|
|
||||||
private void ReloadElements()
|
private void ReloadElements()
|
||||||
@ -129,9 +109,9 @@ namespace UpTool2
|
|||||||
ClearSelection();
|
ClearSelection();
|
||||||
infoPanel_Title.Invalidate();
|
infoPanel_Title.Invalidate();
|
||||||
infoPanel_Description.Invalidate();
|
infoPanel_Description.Invalidate();
|
||||||
int F = sidebarPanel.Controls.Count;
|
int f = sidebarPanel.Controls.Count;
|
||||||
for (int i = 0; i < F; i++) sidebarPanel.Controls[0].Dispose();
|
for (int i = 0; i < f; i++) sidebarPanel.Controls[0].Dispose();
|
||||||
GlobalVariables.Apps.Clear();
|
Program.Lib.V1.Apps.Clear();
|
||||||
//add
|
//add
|
||||||
toolTip.SetToolTip(controls_settings, "Settings");
|
toolTip.SetToolTip(controls_settings, "Settings");
|
||||||
toolTip.SetToolTip(controls_reload, "Refresh repositories");
|
toolTip.SetToolTip(controls_reload, "Refresh repositories");
|
||||||
@ -141,83 +121,89 @@ namespace UpTool2
|
|||||||
toolTip.SetToolTip(action_remove, "Remove");
|
toolTip.SetToolTip(action_remove, "Remove");
|
||||||
toolTip.SetToolTip(action_update, "Update");
|
toolTip.SetToolTip(action_update, "Update");
|
||||||
toolTip.SetToolTip(action_run, "Run");
|
toolTip.SetToolTip(action_run, "Run");
|
||||||
RepoManagement.GetReposFromDisk();
|
Program.Lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
int availableUpdates = 0;
|
int availableUpdates = 0;
|
||||||
foreach (App app in GlobalVariables.Apps.Values)
|
foreach (App app in Program.Lib.V1.Apps.Values)
|
||||||
{
|
{
|
||||||
Panel sidebarIcon = new Panel();
|
Panel sidebarIcon = new Panel
|
||||||
sidebarIcon.Tag = app;
|
{
|
||||||
sidebarIcon.BackColor = app.Color;
|
Tag = app,
|
||||||
sidebarIcon.Size = new Size(70, 70);
|
BackColor = app.Color,
|
||||||
sidebarIcon.BackgroundImage = app.Icon;
|
Size = new Size(70, 70),
|
||||||
sidebarIcon.BackgroundImageLayout = ImageLayout.Stretch;
|
BackgroundImage = (Bitmap) app.Icon,
|
||||||
bool updatable = !app.Local && (app.status & Status.Updatable) == Status.Updatable;
|
BackgroundImageLayout = ImageLayout.Stretch
|
||||||
|
};
|
||||||
|
sidebarIcon.Paint += (sender, args) =>
|
||||||
|
{
|
||||||
|
args.Graphics.Clear(sidebarIcon.BackColor);
|
||||||
|
args.Graphics.DrawImage(sidebarIcon.BackgroundImage, args.ClipRectangle,
|
||||||
|
new Rectangle(new Point(0, 0), sidebarIcon.BackgroundImage.Size), GraphicsUnit.Pixel);
|
||||||
|
};
|
||||||
|
bool updateable = !app.Local && app.Status.Contains(Status.Updatable);
|
||||||
sidebarIcon.Click += (sender, e) =>
|
sidebarIcon.Click += (sender, e) =>
|
||||||
{
|
{
|
||||||
infoPanel_Title.Text = app.Name;
|
infoPanel_Title.Text = app.Name;
|
||||||
infoPanel_Title.ForeColor = app.Local ? Color.Red : Color.Black;
|
infoPanel_Title.ForeColor = app.Local ? Color.Red : Color.Black;
|
||||||
infoPanel_Description.Text = app.Description;
|
infoPanel_Description.Text = app.Description;
|
||||||
action_install.Tag = app;
|
action_install.Tag = app;
|
||||||
action_install.Enabled = !(app.Local || Directory.Exists(app.appPath));
|
action_install.Enabled = !(app.Local || Directory.Exists(app.AppPath));
|
||||||
|
if (_tasks.Any(s => s is InstallTask t && t.App == app))
|
||||||
|
action_install.BackColor = Color.Green;
|
||||||
|
else
|
||||||
|
action_install.ResetBackColor();
|
||||||
action_remove.Tag = app;
|
action_remove.Tag = app;
|
||||||
action_remove.Enabled = Directory.Exists(app.appPath);
|
action_remove.Enabled = Directory.Exists(app.AppPath);
|
||||||
|
if (_tasks.Any(s => s is RemoveTask t && t.App == app))
|
||||||
|
action_remove.BackColor = Color.Green;
|
||||||
|
else
|
||||||
|
action_remove.ResetBackColor();
|
||||||
action_update.Tag = app;
|
action_update.Tag = app;
|
||||||
action_update.Enabled = updatable;
|
action_update.Enabled = updateable;
|
||||||
|
if (_tasks.Any(s => s is UpdateTask t && t.App == app))
|
||||||
|
action_update.BackColor = Color.Green;
|
||||||
|
else
|
||||||
|
action_update.ResetBackColor();
|
||||||
action_run.Tag = app;
|
action_run.Tag = app;
|
||||||
action_run.Enabled = (app.status & Status.Installed) == Status.Installed && !app.Local && app.Runnable && Directory.Exists(app.appPath);
|
action_run.Enabled = app.Status.Contains(Status.Installed) && !app.Local &&
|
||||||
|
app.Runnable && Directory.Exists(app.AppPath);
|
||||||
};
|
};
|
||||||
if (updatable)
|
if (updateable)
|
||||||
availableUpdates++;
|
availableUpdates++;
|
||||||
toolTip.SetToolTip(sidebarIcon, app.Name);
|
toolTip.SetToolTip(sidebarIcon, app.Name);
|
||||||
sidebarPanel.Controls.Add(sidebarIcon);
|
sidebarPanel.Controls.Add(sidebarIcon);
|
||||||
}
|
}
|
||||||
UpdateSidebarV(null, null);
|
UpdateSidebarV(null, null);
|
||||||
Text =
|
Text =
|
||||||
$"UpTool2 {(availableUpdates == 0 ? "(All up-to-date)" : $"({availableUpdates.ToString()} Updates)")}";
|
$"UpTool2 {(availableUpdates == 0 ? "(All up-to-date)" : $"({availableUpdates} Updates)")}";
|
||||||
}
|
}
|
||||||
|
|
||||||
private void Action_run_Click(object sender, EventArgs e)
|
private void Action_run_Click(object sender, EventArgs e)
|
||||||
{
|
{
|
||||||
string path = Path.Combine(((App) action_run.Tag).dataPath, ((App) action_run.Tag).MainFile);
|
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
Process.Start(
|
Program.Lib.V1.AppExtras.RunApp((App) action_run.Tag);
|
||||||
new ProcessStartInfo
|
|
||||||
{
|
|
||||||
FileName = path,
|
|
||||||
WorkingDirectory = ((App) action_run.Tag).dataPath
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
catch (Exception e1)
|
catch (Exception e1)
|
||||||
{
|
{
|
||||||
MessageBox.Show(e1
|
MessageBox.Show($"{e1}Failed to start!");
|
||||||
#if DEBUG
|
|
||||||
+ $"{Environment.NewLine}File was: {path}"
|
|
||||||
#endif
|
|
||||||
+ "Failed to start!");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void Action_update_Click(object sender, EventArgs e)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
GlobalVariables.RelE = false;
|
|
||||||
Action_remove_Click(sender, e);
|
|
||||||
Action_install_Click(sender, e);
|
|
||||||
}
|
|
||||||
catch (Exception e1)
|
|
||||||
{
|
|
||||||
MessageBox.Show(e1.ToString(), "Install failed");
|
|
||||||
}
|
|
||||||
ReloadElements();
|
|
||||||
GlobalVariables.RelE = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void Controls_reload_Click(object sender, EventArgs e)
|
private void Controls_reload_Click(object sender, EventArgs e)
|
||||||
{
|
{
|
||||||
RepoManagement.FetchRepos();
|
Enabled = false;
|
||||||
ReloadElements();
|
if (MessageBox.Show("This may take a few minutes. Are you sure?", "", MessageBoxButtons.YesNo) == DialogResult.Yes)
|
||||||
|
{
|
||||||
|
new Thread(() =>
|
||||||
|
{
|
||||||
|
Program.Lib.V2.RepoManagement.FetchRepos();
|
||||||
|
Invoke((Action) (() =>
|
||||||
|
{
|
||||||
|
ReloadElements();
|
||||||
|
Enabled = true;
|
||||||
|
}));
|
||||||
|
}).Start();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private void Controls_settings_Click(object sender, EventArgs e) => new SettingsForms().ShowDialog();
|
private void Controls_settings_Click(object sender, EventArgs e) => new SettingsForms().ShowDialog();
|
||||||
@ -225,24 +211,29 @@ namespace UpTool2
|
|||||||
private void ClearSelection()
|
private void ClearSelection()
|
||||||
{
|
{
|
||||||
action_install.Enabled = false;
|
action_install.Enabled = false;
|
||||||
|
action_install.ResetBackColor();
|
||||||
action_remove.Enabled = false;
|
action_remove.Enabled = false;
|
||||||
|
action_remove.ResetBackColor();
|
||||||
action_update.Enabled = false;
|
action_update.Enabled = false;
|
||||||
|
action_update.ResetBackColor();
|
||||||
action_run.Enabled = false;
|
action_run.Enabled = false;
|
||||||
|
action_run.ResetBackColor();
|
||||||
infoPanel_Title.Text = "";
|
infoPanel_Title.Text = "";
|
||||||
infoPanel_Description.Text = "";
|
infoPanel_Description.Text = "";
|
||||||
}
|
}
|
||||||
|
|
||||||
private void UpdateSidebarV(object sender, EventArgs e)
|
private void UpdateSidebarV(object sender, EventArgs e)
|
||||||
{
|
{
|
||||||
#if DEBUG
|
|
||||||
if (searchBox.Text == "!DEBUG:PRINT!")
|
if (searchBox.Text == "!DEBUG:PRINT!")
|
||||||
{
|
{
|
||||||
searchBox.Text = "!DEBUG:PRINT";
|
searchBox.Text = "!DEBUG:PRINT";
|
||||||
string tmpFile = Path.GetTempFileName();
|
string tmpFile = Path.GetTempFileName();
|
||||||
File.WriteAllText(tmpFile,
|
File.WriteAllText(tmpFile,
|
||||||
string.Join("\r\n\r\n",
|
string.Join("\r\n\r\n",
|
||||||
GlobalVariables.Apps.Values.Select(app => app.ToString()).Concat(new[]
|
Program.Lib.V1.Apps.Values.Select(app => app.ToString()).Concat(new[]
|
||||||
{"Assembly version: " + Assembly.GetExecutingAssembly().GetName().Version}).ToArray()));
|
{
|
||||||
|
$"Assembly version: {Assembly.GetExecutingAssembly().GetName().Version}"
|
||||||
|
}).ToArray()));
|
||||||
new Thread(() =>
|
new Thread(() =>
|
||||||
{
|
{
|
||||||
Process.Start("notepad", tmpFile).WaitForExit();
|
Process.Start("notepad", tmpFile).WaitForExit();
|
||||||
@ -251,31 +242,27 @@ namespace UpTool2
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
#endif
|
App[] apps = Program.Lib.V1.AppExtras.FindApps(searchBox.Text);
|
||||||
Enum.TryParse(filterBox.SelectedValue.ToString(), out Status status);
|
Enum.TryParse(filterBox.SelectedValue.ToString(), out Status status);
|
||||||
for (int i = 0; i < sidebarPanel.Controls.Count; i++)
|
for (int i = 0; i < sidebarPanel.Controls.Count; i++)
|
||||||
{
|
{
|
||||||
Panel sidebarIcon = (Panel) sidebarPanel.Controls[i];
|
Panel sidebarIcon = (Panel) sidebarPanel.Controls[i];
|
||||||
App app = (App) sidebarIcon.Tag;
|
App app = (App) sidebarIcon.Tag;
|
||||||
sidebarIcon.Visible = app.Name.Contains(searchBox.Text) &&
|
sidebarIcon.Visible = apps.Contains(app) && app.Status.Contains(Program.Online ? status : Status.Installed);
|
||||||
((int) app.status & (int) (Program.Online ? status : Status.Installed)) != 0;
|
}
|
||||||
|
ClearSelection();
|
||||||
}
|
}
|
||||||
ClearSelection();
|
|
||||||
#if DEBUG
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void MainForm_Load(object sender, EventArgs e)
|
private void MainForm_Load(object sender, EventArgs e)
|
||||||
{
|
{
|
||||||
if (Program.Splash.IsDisposed)
|
if (Program.Splash.IsDisposed)
|
||||||
{
|
|
||||||
Close();
|
Close();
|
||||||
}
|
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
Program.Splash.Invoke((Action)Program.Splash.Hide);
|
Program.Splash.Invoke((Action) Program.Splash.Hide);
|
||||||
BringToFront();
|
BringToFront();
|
||||||
|
UpdateChangesLabel(false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -294,10 +281,7 @@ namespace UpTool2
|
|||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
if (stream != null)
|
stream?.Close();
|
||||||
{
|
|
||||||
stream.Close();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
int i = BitConverter.ToInt32(buffer, headerOffset);
|
int i = BitConverter.ToInt32(buffer, headerOffset);
|
||||||
@ -308,9 +292,9 @@ namespace UpTool2
|
|||||||
return dt;
|
return dt;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void MainForm_HelpRequested(object sender, HelpEventArgs hlpevent)
|
private void MainForm_HelpRequested(object sender, HelpEventArgs hlpEvent)
|
||||||
{
|
{
|
||||||
HelpRequested -= help;
|
HelpRequested -= _help;
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
DateTime buildTime = GetBuildDateTime(Assembly.GetExecutingAssembly());
|
DateTime buildTime = GetBuildDateTime(Assembly.GetExecutingAssembly());
|
||||||
@ -320,9 +304,44 @@ Build Date: {buildTime:dd.MM.yyyy}", "UpTool2");
|
|||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
HelpRequested += help;
|
HelpRequested += _help;
|
||||||
hlpevent.Handled = true;
|
hlpEvent.Handled = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void changesButton_Click(object sender, EventArgs e)
|
||||||
|
{
|
||||||
|
if (TaskPreview.Show(ref _tasks, true))
|
||||||
|
{
|
||||||
|
progressBar1.Maximum = _tasks.Count;
|
||||||
|
progressBar1.Value = 0;
|
||||||
|
foreach (AppTask task in _tasks)
|
||||||
|
{
|
||||||
|
task.Run();
|
||||||
|
progressBar1.PerformStep();
|
||||||
|
}
|
||||||
|
_tasks.Clear();
|
||||||
|
UpdateChangesLabel();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void changesLabel_Click(object sender, EventArgs e)
|
||||||
|
{
|
||||||
|
TaskPreview.Show(ref _tasks, false);
|
||||||
|
UpdateChangesLabel();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void UpdateChangesLabel(bool showPanel = true)
|
||||||
|
{
|
||||||
|
changesPanel.Visible = showPanel;
|
||||||
|
changesButton.Enabled = _tasks.Count > 0;
|
||||||
|
progressBar1.Maximum = _tasks.Count;
|
||||||
|
changesLabel.Text = _tasks.Count switch
|
||||||
|
{
|
||||||
|
0 => "No Changes Selected",
|
||||||
|
1 => "1 Change Selected",
|
||||||
|
_ => $"{_tasks.Count} Changes Selected"
|
||||||
|
};
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -1,76 +1,69 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Diagnostics;
|
using System.Diagnostics;
|
||||||
using System.Drawing;
|
using System.Drawing;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using System.IO.Compression;
|
using System.IO.Compression;
|
||||||
using System.Linq;
|
|
||||||
using System.Net;
|
|
||||||
using System.Reflection;
|
using System.Reflection;
|
||||||
using System.Runtime.InteropServices;
|
|
||||||
using System.Security.Cryptography;
|
using System.Security.Cryptography;
|
||||||
using System.Threading;
|
|
||||||
using System.Windows.Forms;
|
using System.Windows.Forms;
|
||||||
using System.Xml;
|
using System.Xml;
|
||||||
using System.Xml.Linq;
|
|
||||||
using UpTool2.Tool;
|
using UpTool2.Tool;
|
||||||
|
using UpToolLib;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
|
||||||
namespace UpTool2
|
namespace UpTool2
|
||||||
{
|
{
|
||||||
internal static class Program
|
internal static class Program
|
||||||
{
|
{
|
||||||
public static Form Splash;
|
public static Form? Splash;
|
||||||
private static int SplashProgress;
|
private static int _splashProgress;
|
||||||
private static string SplashMessage;
|
private static string? _splashMessage;
|
||||||
public static bool Online;
|
public static bool Online;
|
||||||
|
public static UpToolLibMain Lib;
|
||||||
|
|
||||||
[STAThread]
|
[STAThread]
|
||||||
private static void Main()
|
private static void Main(string[] args)
|
||||||
{
|
{
|
||||||
Application.EnableVisualStyles();
|
Application.EnableVisualStyles();
|
||||||
Application.SetCompatibleTextRenderingDefault(false);
|
Application.SetCompatibleTextRenderingDefault(false);
|
||||||
BuildSplash();
|
BuildSplash();
|
||||||
new Thread(() => { Splash.ShowDialog(); }).Start();
|
Splash.Show();
|
||||||
using Mutex mutex = new Mutex(false,
|
try
|
||||||
$"Global\\{{{((GuidAttribute) Assembly.GetExecutingAssembly().GetCustomAttributes(typeof(GuidAttribute), false).GetValue(0)).Value}}}",
|
{
|
||||||
out bool _);
|
Lib = new UpToolLibMain(new UtLibFunctions());
|
||||||
bool hasHandle = false;
|
}
|
||||||
|
catch (MutexLockLockedException)
|
||||||
|
{
|
||||||
|
Console.WriteLine("Mutex property of other process, quitting");
|
||||||
|
Process[] processes = Process.GetProcessesByName("UpTool2");
|
||||||
|
if (processes.Length > 0)
|
||||||
|
WindowHelper.BringProcessToFront(Process.GetProcessesByName("UpTool2")[0]);
|
||||||
|
return;
|
||||||
|
}
|
||||||
#if !DEBUG
|
#if !DEBUG
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
#endif
|
#endif
|
||||||
try
|
|
||||||
{
|
|
||||||
hasHandle = mutex.WaitOne(5000, false);
|
|
||||||
if (hasHandle == false)
|
|
||||||
{
|
|
||||||
Console.WriteLine("Mutex property of other process, quitting");
|
|
||||||
Process[] processes = Process.GetProcessesByName("UpTool2");
|
|
||||||
if (processes.Length > 0)
|
|
||||||
WindowHelper.BringProcessToFront(Process.GetProcessesByName("UpTool2")[0]);
|
|
||||||
Environment.Exit(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (AbandonedMutexException)
|
|
||||||
{
|
|
||||||
#if DEBUG
|
|
||||||
Debug.WriteLine("Mutex abandoned");
|
|
||||||
#endif
|
|
||||||
hasHandle = true;
|
|
||||||
}
|
|
||||||
SetSplash(1, "Initializing paths");
|
SetSplash(1, "Initializing paths");
|
||||||
if (!Directory.Exists(PathTool.dir))
|
if (!Directory.Exists(Lib.V1.PathTool.Dir))
|
||||||
Directory.CreateDirectory(PathTool.dir);
|
Directory.CreateDirectory(Lib.V1.PathTool.Dir);
|
||||||
FixXml();
|
FixXml();
|
||||||
SetSplash(2, "Performing checks");
|
SetSplash(2, "Performing checks");
|
||||||
string metaXml = XDocument.Load(PathTool.InfoXml).Element("meta").Element("UpdateSource").Value;
|
try
|
||||||
Online = Ping(metaXml);
|
{
|
||||||
if (Application.ExecutablePath != PathTool.GetRelative("Install", "UpTool2.dll"))
|
Lib.V2.UpdateChecker.Check();
|
||||||
Splash.Invoke((Action)(() => MessageBox.Show(Splash, $"WARNING!{Environment.NewLine}Running from outside the install directory is not recommended!")));
|
Online = true;
|
||||||
if (!Directory.Exists(PathTool.GetRelative("Apps")))
|
}
|
||||||
Directory.CreateDirectory(PathTool.GetRelative("Apps"));
|
catch
|
||||||
|
{
|
||||||
|
Online = false;
|
||||||
|
}
|
||||||
|
if (!Directory.Exists(Lib.V1.PathTool.GetRelative("Apps")))
|
||||||
|
Directory.CreateDirectory(Lib.V1.PathTool.GetRelative("Apps"));
|
||||||
if (!Online)
|
if (!Online)
|
||||||
SetSplash(7, "Opening");
|
SetSplash(7, "Opening");
|
||||||
if (!Online || UpdateCheck(metaXml))
|
if (!Online || UpdateCheck())
|
||||||
Application.Run(new MainForm());
|
Application.Run(new MainForm());
|
||||||
#if !DEBUG
|
#if !DEBUG
|
||||||
}
|
}
|
||||||
@ -78,7 +71,7 @@ namespace UpTool2
|
|||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
Splash.Invoke((Action)Splash.Hide);
|
Splash.Invoke((Action) Splash.Hide);
|
||||||
}
|
}
|
||||||
catch
|
catch
|
||||||
{
|
{
|
||||||
@ -88,8 +81,7 @@ namespace UpTool2
|
|||||||
}
|
}
|
||||||
finally
|
finally
|
||||||
{
|
{
|
||||||
if (hasHandle)
|
Lib.Dispose();
|
||||||
mutex.ReleaseMutex();
|
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
@ -114,52 +106,40 @@ namespace UpTool2
|
|||||||
{
|
{
|
||||||
Graphics g = e.Graphics;
|
Graphics g = e.Graphics;
|
||||||
//Draw background
|
//Draw background
|
||||||
Brush[] brushes = {Brushes.Purple, Brushes.MediumPurple, Brushes.Indigo, Brushes.Fuchsia, Brushes.OrangeRed};
|
Brush[] brushes =
|
||||||
|
{Brushes.Purple, Brushes.MediumPurple, Brushes.Indigo, Brushes.Fuchsia, Brushes.OrangeRed};
|
||||||
const int barWidth = 50;
|
const int barWidth = 50;
|
||||||
const int topOffset = 100;
|
const int topOffset = 100;
|
||||||
for (int i = 0; i < Splash.Width + topOffset; i += barWidth)
|
for (int i = 0; i < Splash.Width + topOffset; i += barWidth)
|
||||||
{
|
g.FillPolygon(brushes[i / barWidth % brushes.Length], new[]
|
||||||
g.FillPolygon(brushes[(i / barWidth) % brushes.Length], new []
|
|
||||||
{
|
{
|
||||||
new PointF(i, 0),
|
new PointF(i, 0),
|
||||||
new PointF(i + barWidth, 0),
|
new PointF(i + barWidth, 0),
|
||||||
new PointF(i, Splash.Height),
|
new PointF(i, Splash.Height),
|
||||||
new PointF(i - topOffset, Splash.Height)
|
new PointF(i - topOffset, Splash.Height)
|
||||||
});
|
});
|
||||||
}
|
|
||||||
//Draw Text: UpTool2 (by JFronny)^
|
//Draw Text: UpTool2 (by JFronny)^
|
||||||
Font font = new Font(FontFamily.GenericSansSerif, 40, FontStyle.Bold);
|
Font font = new Font(FontFamily.GenericSansSerif, 40, FontStyle.Bold);
|
||||||
const string text = "UpTool2";
|
const string text = "UpTool2";
|
||||||
SizeF size = g.MeasureString(text, font);
|
SizeF size = g.MeasureString(text, font);
|
||||||
RectangleF rect = new RectangleF((Splash.Width / 2f) - (size.Width / 2), (Splash.Height / 2f) - (size.Height / 2), size.Width, size.Height);
|
RectangleF rect = new RectangleF(Splash.Width / 2f - size.Width / 2,
|
||||||
|
Splash.Height / 2f - size.Height / 2, size.Width, size.Height);
|
||||||
g.DrawString(text, font, Brushes.White, rect);
|
g.DrawString(text, font, Brushes.White, rect);
|
||||||
Font smallFont = new Font(FontFamily.GenericSansSerif, 10);
|
Font smallFont = new Font(FontFamily.GenericSansSerif, 10);
|
||||||
const string subtitle = "by JFronny";
|
const string subtitle = "by JFronny";
|
||||||
SizeF size2 = g.MeasureString(subtitle, smallFont);
|
SizeF size2 = g.MeasureString(subtitle, smallFont);
|
||||||
g.DrawString(subtitle, smallFont, Brushes.White, new RectangleF(rect.Right - size2.Width, rect.Bottom - size2.Height, size2.Width, size2.Height));
|
g.DrawString(subtitle, smallFont, Brushes.White,
|
||||||
|
new RectangleF(rect.Right - size2.Width, rect.Bottom - size2.Height, size2.Width, size2.Height));
|
||||||
//Draw progress bar
|
//Draw progress bar
|
||||||
Rectangle bar = new Rectangle((3 * Splash.Width) / 8, ((Splash.Height * 3) / 4) - 10, Splash.Width / 4, 20);
|
Rectangle bar = new Rectangle(3 * Splash.Width / 8, Splash.Height * 3 / 4 - 10, Splash.Width / 4,
|
||||||
|
20);
|
||||||
g.FillRectangle(Brushes.Gray, bar);
|
g.FillRectangle(Brushes.Gray, bar);
|
||||||
g.FillRectangle(Brushes.Black, new Rectangle(bar.X, bar.Y, (bar.Width * SplashProgress) / 10, bar.Height));
|
g.FillRectangle(Brushes.Black,
|
||||||
|
new Rectangle(bar.X, bar.Y, bar.Width * _splashProgress / 10, bar.Height));
|
||||||
g.DrawRectangle(Pens.DimGray, bar);
|
g.DrawRectangle(Pens.DimGray, bar);
|
||||||
//g.DrawString(SplashMessage, smallFont, Brushes.White, new PointF(bar.Left, bar.Bottom));
|
//g.DrawString(SplashMessage, smallFont, Brushes.White, new PointF(bar.Left, bar.Bottom));
|
||||||
g.DrawString(SplashMessage, smallFont, Brushes.White, bar, new StringFormat {Alignment = StringAlignment.Near, LineAlignment = StringAlignment.Center});
|
g.DrawString(_splashMessage, smallFont, Brushes.White, bar,
|
||||||
};
|
new StringFormat {Alignment = StringAlignment.Near, LineAlignment = StringAlignment.Center});
|
||||||
int xOff = 0;
|
|
||||||
int yOff = 0;
|
|
||||||
bool moving = false;
|
|
||||||
Splash.MouseDown += (sender, e) =>
|
|
||||||
{
|
|
||||||
moving = true;
|
|
||||||
xOff = e.X;
|
|
||||||
yOff = e.Y;
|
|
||||||
};
|
|
||||||
Splash.MouseUp += (sender, e) => moving = false;
|
|
||||||
Splash.MouseMove += (sender, e) =>
|
|
||||||
{
|
|
||||||
if (!moving) return;
|
|
||||||
Splash.Left = Cursor.Position.X - xOff;
|
|
||||||
Splash.Top = Cursor.Position.Y - yOff;
|
|
||||||
};
|
};
|
||||||
Splash.Load += (sender, e) => Splash.BringToFront();
|
Splash.Load += (sender, e) => Splash.BringToFront();
|
||||||
Splash.FormClosed += (sender, e) => Splash.Dispose();
|
Splash.FormClosed += (sender, e) => Splash.Dispose();
|
||||||
@ -167,9 +147,10 @@ namespace UpTool2
|
|||||||
|
|
||||||
public static void SetSplash(int progress, string status) => Splash.Invoke(new Action(() =>
|
public static void SetSplash(int progress, string status) => Splash.Invoke(new Action(() =>
|
||||||
{
|
{
|
||||||
SplashProgress = progress;
|
Console.WriteLine($"{progress} - {status}");
|
||||||
Console.WriteLine(status);
|
Debug.WriteLine($"{progress} - {status}");
|
||||||
SplashMessage = status;
|
_splashProgress = progress;
|
||||||
|
_splashMessage = status;
|
||||||
Splash.Invoke((Action) Splash.Invalidate);
|
Splash.Invoke((Action) Splash.Invalidate);
|
||||||
}));
|
}));
|
||||||
|
|
||||||
@ -177,59 +158,29 @@ namespace UpTool2
|
|||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
if (!File.Exists(PathTool.InfoXml) || XDocument.Load(PathTool.InfoXml).Element("meta") == null)
|
Lib.V1.XmlTool.FixXml();
|
||||||
new XElement("meta").Save(PathTool.InfoXml);
|
|
||||||
XDocument x = XDocument.Load(PathTool.InfoXml);
|
|
||||||
XElement meta = x.Element("meta");
|
|
||||||
if (meta.Element("UpdateSource") == null)
|
|
||||||
meta.Add(new XElement("UpdateSource"));
|
|
||||||
if (new[]
|
|
||||||
{
|
|
||||||
"",
|
|
||||||
"https://raw.githubusercontent.com/CreepyCrafter24/UpTool2/master/Meta.xml",
|
|
||||||
"https://raw.githubusercontent.com/JFronny/UpTool2/master/Meta.xml",
|
|
||||||
"https://gist.githubusercontent.com/JFronny/f1ccbba3d8a2f5862592bb29fdb612c4/raw/Meta.xml"
|
|
||||||
}
|
|
||||||
.Contains(meta.Element("UpdateSource").Value))
|
|
||||||
meta.Element("UpdateSource").Value =
|
|
||||||
"https://github.com/JFronny/UpTool2/releases/latest/download/meta.xml";
|
|
||||||
if (meta.Element("Repos") == null)
|
|
||||||
meta.Add(new XElement("Repos"));
|
|
||||||
if (meta.Element("Repos").Elements("Repo").Count() == 0)
|
|
||||||
meta.Element("Repos").Add(new XElement("Repo", new XElement("Name", "UpTool2 official Repo"),
|
|
||||||
new XElement("Link",
|
|
||||||
"https://gist.githubusercontent.com/JFronny/f1ccbba3d8a2f5862592bb29fdb612c4/raw/Repo.xml")));
|
|
||||||
meta.Element("Repos").Elements("Repo").Select(s => s.Element("Link"))
|
|
||||||
.Where(s => new[]
|
|
||||||
{
|
|
||||||
null, "https://github.com/JFronny/UpTool2/releases/download/Repo/Repo.xml",
|
|
||||||
"https://raw.githubusercontent.com/JFronny/UpTool2/master/Repo.xml"
|
|
||||||
}.Contains(s.Value))
|
|
||||||
.ToList().ForEach(s =>
|
|
||||||
s.Value =
|
|
||||||
"https://gist.githubusercontent.com/JFronny/f1ccbba3d8a2f5862592bb29fdb612c4/raw/Repo.xml");
|
|
||||||
if (meta.Element("LocalRepo") == null)
|
|
||||||
meta.Add(new XElement("LocalRepo"));
|
|
||||||
x.Save(PathTool.InfoXml);
|
|
||||||
}
|
}
|
||||||
catch (XmlException)
|
catch (XmlException)
|
||||||
{
|
{
|
||||||
if (throwOnError) throw;
|
if (throwOnError) throw;
|
||||||
MessageBox.Show("Something went wrong while trying to parse XML. Retrying...");
|
MessageBox.Show("Something went wrong while trying to parse XML. Retrying...");
|
||||||
File.Delete(PathTool.InfoXml);
|
File.Delete(Lib.V1.PathTool.InfoXml);
|
||||||
FixXml();
|
FixXml();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static bool UpdateCheck(string metaXml)
|
private static bool UpdateCheck()
|
||||||
{
|
{
|
||||||
|
UpdateCheck check = Lib.V2.UpdateChecker.Check();
|
||||||
SetSplash(3, "Comparing online version");
|
SetSplash(3, "Comparing online version");
|
||||||
XElement meta = XDocument.Load(metaXml).Element("meta");
|
if (Assembly.GetExecutingAssembly().GetName().Version >= check.OnlineVersion)
|
||||||
if (Assembly.GetExecutingAssembly().GetName().Version >= Version.Parse(meta.Element("Version").Value))
|
{
|
||||||
|
SetSplash(7, "Opening");
|
||||||
return true;
|
return true;
|
||||||
|
}
|
||||||
byte[] dl;
|
byte[] dl;
|
||||||
SetSplash(4, "Downloading latest");
|
SetSplash(4, "Downloading latest");
|
||||||
using (DownloadDialog dlg = new DownloadDialog(meta.Element("File").Value))
|
using (DownloadDialog dlg = new DownloadDialog(check.Installer.AbsoluteUri))
|
||||||
{
|
{
|
||||||
if (dlg.ShowDialog() != DialogResult.OK)
|
if (dlg.ShowDialog() != DialogResult.OK)
|
||||||
throw new Exception("Failed to update");
|
throw new Exception("Failed to update");
|
||||||
@ -239,45 +190,30 @@ namespace UpTool2
|
|||||||
using (SHA256CryptoServiceProvider sha256 = new SHA256CryptoServiceProvider())
|
using (SHA256CryptoServiceProvider sha256 = new SHA256CryptoServiceProvider())
|
||||||
{
|
{
|
||||||
string pkgHash = BitConverter.ToString(sha256.ComputeHash(dl)).Replace("-", string.Empty).ToUpper();
|
string pkgHash = BitConverter.ToString(sha256.ComputeHash(dl)).Replace("-", string.Empty).ToUpper();
|
||||||
if (pkgHash != meta.Element("Hash").Value.ToUpper())
|
if (pkgHash != check.InstallerHash)
|
||||||
throw new Exception("The hash is not equal to the one stored in the repo:\r\nPackage: " + pkgHash +
|
throw new Exception(
|
||||||
"\r\nOnline: " + meta.Element("Hash").Value.ToUpper());
|
$"The hash is not equal to the one stored in the repo:\r\nPackage: {pkgHash}\r\nOnline: {check.InstallerHash}");
|
||||||
}
|
}
|
||||||
SetSplash(9, "Installing");
|
SetSplash(9, "Installing");
|
||||||
if (Directory.Exists(PathTool.GetRelative("Install", "tmp")))
|
if (Directory.Exists(Lib.V1.PathTool.GetRelative("Install", "tmp")))
|
||||||
Directory.Delete(PathTool.GetRelative("Install", "tmp"), true);
|
Directory.Delete(Lib.V1.PathTool.GetRelative("Install", "tmp"), true);
|
||||||
Directory.CreateDirectory(PathTool.GetRelative("Install", "tmp"));
|
Directory.CreateDirectory(Lib.V1.PathTool.GetRelative("Install", "tmp"));
|
||||||
using (MemoryStream ms = new MemoryStream(dl))
|
using (MemoryStream ms = new MemoryStream(dl))
|
||||||
{
|
{
|
||||||
using ZipArchive ar = new ZipArchive(ms);
|
using ZipArchive ar = new ZipArchive(ms);
|
||||||
ar.ExtractToDirectory(PathTool.GetRelative("Install", "tmp"), true);
|
ar.ExtractToDirectory(Lib.V1.PathTool.GetRelative("Install", "tmp"), true);
|
||||||
}
|
}
|
||||||
Splash.Hide();
|
Splash.Hide();
|
||||||
Process.Start(new ProcessStartInfo
|
Process.Start(new ProcessStartInfo
|
||||||
{
|
{
|
||||||
FileName = "cmd.exe",
|
FileName = Lib.V1.PathTool.GetRelative("Install", "tmp", "Installer.exe"),
|
||||||
Arguments = @"/C timeout /t 2 & xcopy /s /e /y tmp\* .",
|
Arguments = "i -p",
|
||||||
CreateNoWindow = true,
|
CreateNoWindow = true,
|
||||||
WindowStyle = ProcessWindowStyle.Hidden,
|
WindowStyle = ProcessWindowStyle.Hidden,
|
||||||
WorkingDirectory = PathTool.GetRelative("Install")
|
WorkingDirectory = Lib.V1.PathTool.GetRelative("Install")
|
||||||
});
|
});
|
||||||
|
SetSplash(7, "Installing");
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
private static bool Ping(string url)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
HttpWebRequest request = (HttpWebRequest) WebRequest.Create(url);
|
|
||||||
request.Timeout = 3000;
|
|
||||||
request.AllowAutoRedirect = true;
|
|
||||||
using WebResponse response = request.GetResponse();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
catch
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -1,35 +0,0 @@
|
|||||||
using System.Reflection;
|
|
||||||
using System.Runtime.InteropServices;
|
|
||||||
|
|
||||||
// General Information about an assembly is controlled through the following
|
|
||||||
// set of attributes. Change these attribute values to modify the information
|
|
||||||
// associated with an assembly.
|
|
||||||
[assembly: AssemblyTitle("UpTool2")]
|
|
||||||
[assembly: AssemblyDescription("Download and update applications from UpTool repos")]
|
|
||||||
[assembly: AssemblyConfiguration("")]
|
|
||||||
[assembly: AssemblyCompany("JFronny")]
|
|
||||||
[assembly: AssemblyProduct("UpTool2")]
|
|
||||||
[assembly: AssemblyCopyright("Copyright © JFronny 2019")]
|
|
||||||
[assembly: AssemblyTrademark("")]
|
|
||||||
[assembly: AssemblyCulture("")]
|
|
||||||
|
|
||||||
// Setting ComVisible to false makes the types in this assembly not visible
|
|
||||||
// to COM components. If you need to access a type in this assembly from
|
|
||||||
// COM, set the ComVisible attribute to true on that type.
|
|
||||||
[assembly: ComVisible(false)]
|
|
||||||
|
|
||||||
// The following GUID is for the ID of the typelib if this project is exposed to COM
|
|
||||||
[assembly: Guid("c0c1e002-9e13-4e8f-a035-dbdc5128e00e")]
|
|
||||||
|
|
||||||
// Version information for an assembly consists of the following four values:
|
|
||||||
//
|
|
||||||
// Major Version
|
|
||||||
// Minor Version
|
|
||||||
// Build Number
|
|
||||||
// Revision
|
|
||||||
//
|
|
||||||
// You can specify all the values or you can default the Build and Revision Numbers
|
|
||||||
// by using the '*' as shown below:
|
|
||||||
// [assembly: AssemblyVersion("1.0.*")]
|
|
||||||
[assembly: AssemblyVersion("1.0.*")]
|
|
||||||
[assembly: AssemblyFileVersion("1.0.1.0")]
|
|
20
UpTool2/SourcesForm.Designer.cs
generated
20
UpTool2/SourcesForm.Designer.cs
generated
@ -21,20 +21,16 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
#region Windows Form Designer generated code
|
#region Windows Form Designer generated code
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Required method for Designer support - do not modify
|
/// Required method for Designer support - do not modify
|
||||||
/// the contents of this method with the code editor.
|
/// the contents of this method with the code editor.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
private void InitializeComponent()
|
private void InitializeComponent()
|
||||||
{
|
{
|
||||||
System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(SettingsForms));
|
System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(UpTool2.SettingsForms));
|
||||||
this.sourceGrid = new System.Windows.Forms.DataGridView();
|
this.sourceGrid = new System.Windows.Forms.DataGridView();
|
||||||
((System.ComponentModel.ISupportInitialize)(this.sourceGrid)).BeginInit();
|
((System.ComponentModel.ISupportInitialize) (this.sourceGrid)).BeginInit();
|
||||||
this.SuspendLayout();
|
this.SuspendLayout();
|
||||||
//
|
|
||||||
// sourceGrid
|
|
||||||
//
|
|
||||||
this.sourceGrid.BackgroundColor = System.Drawing.Color.White;
|
this.sourceGrid.BackgroundColor = System.Drawing.Color.White;
|
||||||
this.sourceGrid.ColumnHeadersHeightSizeMode = System.Windows.Forms.DataGridViewColumnHeadersHeightSizeMode.AutoSize;
|
this.sourceGrid.ColumnHeadersHeightSizeMode = System.Windows.Forms.DataGridViewColumnHeadersHeightSizeMode.AutoSize;
|
||||||
this.sourceGrid.Dock = System.Windows.Forms.DockStyle.Fill;
|
this.sourceGrid.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||||
@ -44,28 +40,24 @@
|
|||||||
this.sourceGrid.Name = "sourceGrid";
|
this.sourceGrid.Name = "sourceGrid";
|
||||||
this.sourceGrid.Size = new System.Drawing.Size(933, 519);
|
this.sourceGrid.Size = new System.Drawing.Size(933, 519);
|
||||||
this.sourceGrid.TabIndex = 0;
|
this.sourceGrid.TabIndex = 0;
|
||||||
//
|
|
||||||
// SettingsForms
|
|
||||||
//
|
|
||||||
this.AutoScaleDimensions = new System.Drawing.SizeF(7F, 15F);
|
this.AutoScaleDimensions = new System.Drawing.SizeF(7F, 15F);
|
||||||
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
|
||||||
this.ClientSize = new System.Drawing.Size(933, 519);
|
this.ClientSize = new System.Drawing.Size(933, 519);
|
||||||
this.Controls.Add(this.sourceGrid);
|
this.Controls.Add(this.sourceGrid);
|
||||||
this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon")));
|
this.Icon = ((System.Drawing.Icon) (resources.GetObject("$this.Icon")));
|
||||||
this.Name = "SettingsForms";
|
this.Name = "SettingsForms";
|
||||||
this.ShowIcon = false;
|
this.ShowIcon = false;
|
||||||
this.ShowInTaskbar = false;
|
this.ShowInTaskbar = false;
|
||||||
this.Text = "Sources";
|
this.Text = "Sources";
|
||||||
this.TopMost = true;
|
this.TopMost = true;
|
||||||
this.FormClosing += new System.Windows.Forms.FormClosingEventHandler(this.SettingsForms_FormClosing);
|
this.FormClosing += new System.Windows.Forms.FormClosingEventHandler(this.SettingsForms_FormClosing);
|
||||||
((System.ComponentModel.ISupportInitialize)(this.sourceGrid)).EndInit();
|
((System.ComponentModel.ISupportInitialize) (this.sourceGrid)).EndInit();
|
||||||
this.ResumeLayout(false);
|
this.ResumeLayout(false);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#endregion
|
|
||||||
|
|
||||||
private System.Windows.Forms.DataGridView sourceGrid;
|
private System.Windows.Forms.DataGridView sourceGrid;
|
||||||
|
#endregion
|
||||||
|
|
||||||
private System.Windows.Forms.DataGridViewTextBoxColumn sbName;
|
private System.Windows.Forms.DataGridViewTextBoxColumn sbName;
|
||||||
private System.Windows.Forms.DataGridViewTextBoxColumn sbLink;
|
private System.Windows.Forms.DataGridViewTextBoxColumn sbLink;
|
||||||
}
|
}
|
||||||
|
@ -1,34 +1,27 @@
|
|||||||
using System.Windows.Forms;
|
using System.Collections.Generic;
|
||||||
using System.Xml.Linq;
|
using System.Windows.Forms;
|
||||||
using UpTool2.Tool;
|
using UpToolLib.DataStructures;
|
||||||
|
|
||||||
namespace UpTool2
|
namespace UpTool2
|
||||||
{
|
{
|
||||||
public partial class SettingsForms : Form
|
public partial class SettingsForms : Form
|
||||||
{
|
{
|
||||||
private readonly XDocument doc;
|
private readonly List<Repo> _repos = new List<Repo>();
|
||||||
private readonly XElement meta;
|
|
||||||
private readonly XElement repos;
|
|
||||||
|
|
||||||
public SettingsForms()
|
public SettingsForms()
|
||||||
{
|
{
|
||||||
InitializeComponent();
|
InitializeComponent();
|
||||||
Program.FixXml();
|
Program.FixXml();
|
||||||
doc = XDocument.Load(PathTool.InfoXml);
|
_repos.AddRange(Program.Lib.V2.RepoManagement.GetRepos());
|
||||||
meta = doc.Element("meta");
|
sourceGrid.Columns.Clear();
|
||||||
repos = meta.Element("Repos");
|
sourceGrid.Columns.Add("name", "Name");
|
||||||
foreach (XElement repo in repos.Elements("Repo"))
|
sourceGrid.Columns.Add("link", "Link");
|
||||||
sourceGrid.Rows.Add(repo.Element("Name").Value, repo.Element("Link").Value);
|
foreach (Repo repo in _repos)
|
||||||
|
sourceGrid.Rows.Add(repo.Name, repo.Url);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void SettingsForms_FormClosing(object sender, FormClosingEventArgs e)
|
private void SettingsForms_FormClosing(object sender, FormClosingEventArgs e)
|
||||||
{
|
{
|
||||||
repos.RemoveNodes();
|
Program.Lib.V2.RepoManagement.Save(_repos);
|
||||||
for (int y = 0; y < sourceGrid.Rows.Count; y++)
|
|
||||||
if (y + 1 < sourceGrid.Rows.Count)
|
|
||||||
repos.Add(new XElement("Repo", new XElement("Name", (string) sourceGrid.Rows[y].Cells[0].Value),
|
|
||||||
new XElement("Link", (string) sourceGrid.Rows[y].Cells[1].Value)));
|
|
||||||
doc.Save(PathTool.InfoXml);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
32
UpTool2/TaskPreview.cs
Normal file
32
UpTool2/TaskPreview.cs
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Drawing;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Windows.Forms;
|
||||||
|
using UpToolLib.v2.TaskQueue;
|
||||||
|
|
||||||
|
namespace UpTool2
|
||||||
|
{
|
||||||
|
internal static class TaskPreview
|
||||||
|
{
|
||||||
|
public static bool Show(ref List<AppTask> tasks, bool showOk)
|
||||||
|
{
|
||||||
|
bool ok = false;
|
||||||
|
using Form tmp = new Form {Size = new Size(600, 300), MinimumSize = new Size(300, showOk ? 138 : 133)};
|
||||||
|
using CheckedListBox list = new CheckedListBox {Dock = DockStyle.Fill};
|
||||||
|
using Button okButton = new Button {Dock = DockStyle.Bottom, Text = "OK"};
|
||||||
|
list.Items.AddRange(tasks.ToArray());
|
||||||
|
for (int i = 0; i < tasks.Count; i++)
|
||||||
|
list.SetItemChecked(i, true);
|
||||||
|
tmp.Controls.Add(list);
|
||||||
|
okButton.Click += (sender, args) =>
|
||||||
|
{
|
||||||
|
ok = true;
|
||||||
|
tmp.Close();
|
||||||
|
};
|
||||||
|
if (showOk) tmp.Controls.Add(okButton);
|
||||||
|
tmp.ShowDialog();
|
||||||
|
tasks = list.Items.OfType<AppTask>().Where((s, i) => list.GetItemChecked(i)).ToList();
|
||||||
|
return !showOk || ok;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -1,117 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.Diagnostics;
|
|
||||||
using System.IO;
|
|
||||||
using System.IO.Compression;
|
|
||||||
using System.Security.Cryptography;
|
|
||||||
using System.Windows.Forms;
|
|
||||||
using System.Xml.Linq;
|
|
||||||
using UpTool2.DataStructures;
|
|
||||||
|
|
||||||
namespace UpTool2.Tool
|
|
||||||
{
|
|
||||||
internal static class AppInstall
|
|
||||||
{
|
|
||||||
public static void Install(App appI)
|
|
||||||
{
|
|
||||||
string app = "";
|
|
||||||
string tmp = "";
|
|
||||||
#if !DEBUG
|
|
||||||
try
|
|
||||||
{
|
|
||||||
#endif
|
|
||||||
app = appI.appPath;
|
|
||||||
tmp = PathTool.tempPath;
|
|
||||||
if (Directory.Exists(tmp))
|
|
||||||
Directory.Delete(tmp, true);
|
|
||||||
Directory.CreateDirectory(tmp);
|
|
||||||
if (Directory.Exists(app))
|
|
||||||
Directory.Delete(app, true);
|
|
||||||
Directory.CreateDirectory(app);
|
|
||||||
using DownloadDialog dlg = new DownloadDialog(appI.File);
|
|
||||||
if (dlg.ShowDialog() != DialogResult.OK)
|
|
||||||
throw new Exception("Download failed");
|
|
||||||
using (SHA256CryptoServiceProvider sha256 = new SHA256CryptoServiceProvider())
|
|
||||||
{
|
|
||||||
string pkgHash = BitConverter.ToString(sha256.ComputeHash(dlg.Result)).Replace("-", string.Empty)
|
|
||||||
.ToUpper();
|
|
||||||
if (pkgHash != appI.Hash.ToUpper())
|
|
||||||
throw new Exception($@"The hash is not equal to the one stored in the repo:
|
|
||||||
Package: {pkgHash}
|
|
||||||
Online: {appI.Hash.ToUpper()}");
|
|
||||||
}
|
|
||||||
File.WriteAllBytes(Path.Combine(app, "package.zip"), dlg.Result);
|
|
||||||
CompleteInstall(appI);
|
|
||||||
#if !DEBUG
|
|
||||||
}
|
|
||||||
catch
|
|
||||||
{
|
|
||||||
if (Directory.Exists(app))
|
|
||||||
Directory.Delete(app, true);
|
|
||||||
throw;
|
|
||||||
}
|
|
||||||
finally
|
|
||||||
{
|
|
||||||
#endif
|
|
||||||
if (tmp != "" && Directory.Exists(tmp))
|
|
||||||
Directory.Delete(tmp, true);
|
|
||||||
#if !DEBUG
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void InstallZip(string zipPath, App meta)
|
|
||||||
{
|
|
||||||
string app = "";
|
|
||||||
string tmp = "";
|
|
||||||
try
|
|
||||||
{
|
|
||||||
app = meta.appPath;
|
|
||||||
Directory.CreateDirectory(app);
|
|
||||||
tmp = PathTool.tempPath;
|
|
||||||
if (Directory.Exists(tmp))
|
|
||||||
Directory.Delete(tmp, true);
|
|
||||||
Directory.CreateDirectory(tmp);
|
|
||||||
File.Copy(zipPath, Path.Combine(app, "package.zip"));
|
|
||||||
CompleteInstall(meta);
|
|
||||||
}
|
|
||||||
catch
|
|
||||||
{
|
|
||||||
if (Directory.Exists(app))
|
|
||||||
Directory.Delete(app, true);
|
|
||||||
throw;
|
|
||||||
}
|
|
||||||
finally
|
|
||||||
{
|
|
||||||
if (tmp != "" && Directory.Exists(tmp))
|
|
||||||
Directory.Delete(tmp, true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//Use
|
|
||||||
//PowerShell -Command "Add-Type -AssemblyName PresentationFramework;[System.Windows.MessageBox]::Show('Hello World')"
|
|
||||||
//for message boxes
|
|
||||||
private static void CompleteInstall(App app) => CompleteInstall(app.appPath, app.Name, app.Description, app.Version, app.MainFile);
|
|
||||||
|
|
||||||
private static void CompleteInstall(string appPath, string name, string description, Version version, string mainFile)
|
|
||||||
{
|
|
||||||
string tmp = PathTool.tempPath;
|
|
||||||
ZipFile.ExtractToDirectory(Path.Combine(appPath, "package.zip"), tmp);
|
|
||||||
Directory.Move(Path.Combine(tmp, "Data"), Path.Combine(appPath, "app"));
|
|
||||||
XElement el = new XElement("app", new XElement("Name", name), new XElement("Description", description),
|
|
||||||
new XElement("Version", version));
|
|
||||||
if (mainFile != null)
|
|
||||||
el.Add(new XElement(new XElement("MainFile", mainFile)));
|
|
||||||
el.Save(Path.Combine(appPath, "info.xml"));
|
|
||||||
Process.Start(new ProcessStartInfo
|
|
||||||
{
|
|
||||||
FileName = "cmd.exe",
|
|
||||||
Arguments = $"/C \"{Path.Combine(tmp, "Install.bat")}\"",
|
|
||||||
WorkingDirectory = Path.Combine(appPath, "app"),
|
|
||||||
CreateNoWindow = true,
|
|
||||||
WindowStyle = ProcessWindowStyle.Hidden
|
|
||||||
}).WaitForExit();
|
|
||||||
if (GlobalVariables.RelE)
|
|
||||||
GlobalVariables.ReloadElements.Invoke();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,25 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.IO;
|
|
||||||
using System.Linq;
|
|
||||||
|
|
||||||
namespace UpTool2.Tool
|
|
||||||
{
|
|
||||||
internal static class PathTool
|
|
||||||
{
|
|
||||||
public static string dir =>
|
|
||||||
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), "UpTool2");
|
|
||||||
|
|
||||||
public static string tempPath => GetRelative("tmp");
|
|
||||||
public static string appsPath => GetRelative("Apps");
|
|
||||||
public static string InfoXml => GetRelative("info.xml");
|
|
||||||
|
|
||||||
public static string GetRelative(params string[] segments) =>
|
|
||||||
Path.Combine(new[] {dir}.Concat(segments).ToArray());
|
|
||||||
|
|
||||||
public static string GetAppPath(Guid app) => Path.Combine(appsPath, app.ToString());
|
|
||||||
|
|
||||||
public static string GetDataPath(Guid app) => Path.Combine(GetAppPath(app), "app");
|
|
||||||
|
|
||||||
public static string GetInfoPath(Guid app) => Path.Combine(GetAppPath(app), "info.xml");
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,177 +0,0 @@
|
|||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using System.Drawing;
|
|
||||||
using System.Drawing.Drawing2D;
|
|
||||||
using System.Drawing.Imaging;
|
|
||||||
using System.IO;
|
|
||||||
using System.Linq;
|
|
||||||
using System.Net;
|
|
||||||
using System.Windows.Forms;
|
|
||||||
using System.Xml.Linq;
|
|
||||||
using CC_Functions.Misc;
|
|
||||||
using UpTool2.DataStructures;
|
|
||||||
using UpTool2.Properties;
|
|
||||||
|
|
||||||
namespace UpTool2.Tool
|
|
||||||
{
|
|
||||||
internal static class RepoManagement
|
|
||||||
{
|
|
||||||
public static void FetchRepos()
|
|
||||||
{
|
|
||||||
Program.FixXml();
|
|
||||||
XElement meta = XDocument.Load(PathTool.InfoXml).Element("meta");
|
|
||||||
List<XElement> tmpAppsList = new List<XElement>();
|
|
||||||
List<string> repArr = meta.Element("Repos").Elements("Repo").Select(s => s.Element("Link").Value).Distinct()
|
|
||||||
.ToList();
|
|
||||||
using (WebClient client = new WebClient())
|
|
||||||
{
|
|
||||||
int i = 0;
|
|
||||||
while (i < repArr.Count)
|
|
||||||
{
|
|
||||||
#if !DEBUG
|
|
||||||
try
|
|
||||||
{
|
|
||||||
#endif
|
|
||||||
XDocument repo = XDocument.Load(new Uri(repArr[i]).Unshorten().AbsoluteUri);
|
|
||||||
repArr.AddRange(repo.Element("repo").Elements("repolink").Select(s => s.Value)
|
|
||||||
.Where(s => !repArr.Contains(s)));
|
|
||||||
XElement[] tmp_apparray = repo.Element("repo").Elements("app").Where(app =>
|
|
||||||
!tmpAppsList.Any(a => a.Element("ID").Value == app.Element("ID").Value) ||
|
|
||||||
!tmpAppsList
|
|
||||||
.Where(a => a.Element("ID").Value == app.Element("ID").Value).Any(a =>
|
|
||||||
GetVer(a.Element("Version")) >= app.Element("Version").GetVer())).ToArray()
|
|
||||||
.Concat(repo.Element("repo").Elements("applink")
|
|
||||||
.Select(s => XDocument.Load(new Uri(s.Value).Unshorten().AbsoluteUri).Element("app")))
|
|
||||||
.ToArray();
|
|
||||||
for (int i1 = 0; i1 < tmp_apparray.Length; i1++)
|
|
||||||
{
|
|
||||||
XElement app = tmp_apparray[i1];
|
|
||||||
//"Sanity check"
|
|
||||||
Version.Parse(app.Element("Version").Value);
|
|
||||||
Guid.Parse(app.Element("ID").Value);
|
|
||||||
//Create XElement
|
|
||||||
tmpAppsList.Add(new XElement("App",
|
|
||||||
new XElement("Name", app.Element("Name").Value),
|
|
||||||
new XElement("Description", app.Element("Description").Value),
|
|
||||||
new XElement("Version", app.Element("Version").Value),
|
|
||||||
new XElement("ID", app.Element("ID").Value),
|
|
||||||
new XElement("File", app.Element("File").Value),
|
|
||||||
new XElement("Hash", app.Element("Hash").Value)
|
|
||||||
));
|
|
||||||
if (app.Element("MainFile") != null)
|
|
||||||
tmpAppsList.Last().Add(new XElement("MainFile", app.Element("MainFile").Value));
|
|
||||||
if (app.Element("Icon") != null)
|
|
||||||
try
|
|
||||||
{
|
|
||||||
//Scale Image and save as Base64
|
|
||||||
Image src = Image.FromStream(
|
|
||||||
client.OpenRead(new Uri(app.Element("Icon").Value).Unshorten()));
|
|
||||||
Bitmap dest = new Bitmap(70, 70);
|
|
||||||
dest.SetResolution(src.HorizontalResolution, src.VerticalResolution);
|
|
||||||
using (Graphics g = Graphics.FromImage(dest))
|
|
||||||
{
|
|
||||||
g.CompositingMode = CompositingMode.SourceCopy;
|
|
||||||
g.CompositingQuality = CompositingQuality.HighQuality;
|
|
||||||
g.InterpolationMode = InterpolationMode.HighQualityBicubic;
|
|
||||||
g.SmoothingMode = SmoothingMode.HighQuality;
|
|
||||||
g.PixelOffsetMode = PixelOffsetMode.HighQuality;
|
|
||||||
using ImageAttributes wrapMode = new ImageAttributes();
|
|
||||||
wrapMode.SetWrapMode(WrapMode.TileFlipXY);
|
|
||||||
g.DrawImage(src, new Rectangle(0, 0, 70, 70), 0, 0, src.Width, src.Height,
|
|
||||||
GraphicsUnit.Pixel, wrapMode);
|
|
||||||
}
|
|
||||||
using MemoryStream ms = new MemoryStream();
|
|
||||||
dest.Save(ms, ImageFormat.Png);
|
|
||||||
tmpAppsList.Last()
|
|
||||||
.Add(new XElement("Icon", Convert.ToBase64String(ms.ToArray())));
|
|
||||||
}
|
|
||||||
catch
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
if (tmpAppsList.Count(a => a.Element("ID").Value == app.Element("ID").Value) > 1)
|
|
||||||
tmpAppsList.Where(a => a.Element("ID").Value == app.Element("ID").Value).Reverse()
|
|
||||||
.Skip(1)
|
|
||||||
.ToList().ForEach(a => tmpAppsList.Remove(a));
|
|
||||||
}
|
|
||||||
#if !DEBUG
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
MessageBox.Show(e.ToString(), "Failed to load repo: " + repArr[i]);
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
tmpAppsList.Sort((x, y) =>
|
|
||||||
string.Compare(x.Element("Name").Value, y.Element("Name").Value, StringComparison.Ordinal));
|
|
||||||
if (meta.Element("LocalRepo") == null)
|
|
||||||
meta.Add(new XElement("LocalRepo"));
|
|
||||||
XElement repos = meta.Element("LocalRepo");
|
|
||||||
repos.RemoveNodes();
|
|
||||||
tmpAppsList.ForEach(app => repos.Add(app));
|
|
||||||
meta.Save(PathTool.InfoXml);
|
|
||||||
}
|
|
||||||
|
|
||||||
private static Version GetVer(this XElement el) =>
|
|
||||||
int.TryParse(el.Value, out int i) ? new Version(0, 0, 0, i) : Version.Parse(el.Value);
|
|
||||||
|
|
||||||
public static void GetReposFromDisk()
|
|
||||||
{
|
|
||||||
GlobalVariables.Apps.Clear();
|
|
||||||
string xml = PathTool.InfoXml;
|
|
||||||
XDocument.Load(xml).Element("meta").Element("LocalRepo").Elements().ToList().ForEach(app =>
|
|
||||||
{
|
|
||||||
Guid id = Guid.Parse(app.Element("ID").Value);
|
|
||||||
string locInPath = PathTool.GetInfoPath(id);
|
|
||||||
XElement locIn = File.Exists(locInPath) ? XDocument.Load(locInPath).Element("app") : app;
|
|
||||||
if (int.TryParse(app.Element("Version").Value, out _))
|
|
||||||
app.Element("Version").Value = GlobalVariables.minimumVer.ToString();
|
|
||||||
GlobalVariables.Apps.Add(id, new App(
|
|
||||||
locIn.Element("Name").Value,
|
|
||||||
locIn.Element("Description").Value,
|
|
||||||
Version.Parse(app.Element("Version").Value),
|
|
||||||
app.Element("File").Value,
|
|
||||||
false,
|
|
||||||
app.Element("Hash").Value,
|
|
||||||
id,
|
|
||||||
Color.White,
|
|
||||||
app.Element("Icon") == null
|
|
||||||
? Resources.C_64.ToBitmap()
|
|
||||||
: (Bitmap) new ImageConverter().ConvertFrom(
|
|
||||||
Convert.FromBase64String(app.Element("Icon").Value)),
|
|
||||||
locIn.Element("MainFile") != null || app.Element("MainFile") != null,
|
|
||||||
locIn.Element("MainFile") == null
|
|
||||||
? app.Element("MainFile") == null ? "" : app.Element("MainFile").Value
|
|
||||||
: locIn.Element("MainFile").Value
|
|
||||||
));
|
|
||||||
});
|
|
||||||
Directory.GetDirectories(PathTool.appsPath)
|
|
||||||
.Where(s => Guid.TryParse(Path.GetFileName(s), out Guid guid) &&
|
|
||||||
!GlobalVariables.Apps.ContainsKey(guid)).ToList().ForEach(s =>
|
|
||||||
{
|
|
||||||
Guid tmp = Guid.Parse(Path.GetFileName(s));
|
|
||||||
try
|
|
||||||
{
|
|
||||||
XElement data = XDocument.Load(PathTool.GetInfoPath(tmp)).Element("app");
|
|
||||||
GlobalVariables.Apps.Add(tmp,
|
|
||||||
new App("(local) " + data.Element("Name").Value, data.Element("Description").Value,
|
|
||||||
GlobalVariables.minimumVer, "", true, "", tmp, Color.Red, Resources.C_64.ToBitmap(),
|
|
||||||
data.Element("MainFile") != null,
|
|
||||||
data.Element("MainFile") == null ? "" : data.Element("MainFile").Value));
|
|
||||||
}
|
|
||||||
catch (Exception e)
|
|
||||||
{
|
|
||||||
if (MessageBox.Show($@"An error occured while loading this local repo:
|
|
||||||
{e.Message}
|
|
||||||
Do you want to exit? Otherwise the folder will be deleted, possibly causeing problems later.", "",
|
|
||||||
MessageBoxButtons.YesNo) == DialogResult.No)
|
|
||||||
Directory.Delete(PathTool.GetAppPath(tmp), true);
|
|
||||||
else
|
|
||||||
Environment.Exit(0);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
60
UpTool2/UTLibFunctions.cs
Normal file
60
UpTool2/UTLibFunctions.cs
Normal file
@ -0,0 +1,60 @@
|
|||||||
|
using System;
|
||||||
|
using System.Drawing;
|
||||||
|
using System.Drawing.Drawing2D;
|
||||||
|
using System.Drawing.Imaging;
|
||||||
|
using System.IO;
|
||||||
|
using System.Net;
|
||||||
|
using System.Windows.Forms;
|
||||||
|
using UpTool2.Properties;
|
||||||
|
using UpTool2.Tool;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
|
||||||
|
namespace UpTool2
|
||||||
|
{
|
||||||
|
internal class UtLibFunctions : IExternalFunctionality
|
||||||
|
{
|
||||||
|
public Tuple<bool, byte[]> Download(Uri link)
|
||||||
|
{
|
||||||
|
using DownloadDialog dialog = new DownloadDialog(link.AbsoluteUri);
|
||||||
|
bool success = dialog.ShowDialog() == DialogResult.OK;
|
||||||
|
return new Tuple<bool, byte[]>(success, success ? dialog.Result : null);
|
||||||
|
}
|
||||||
|
|
||||||
|
public string FetchImageB64(Uri link)
|
||||||
|
{
|
||||||
|
using WebClient client = new WebClient();
|
||||||
|
Image src = Image.FromStream(
|
||||||
|
client.OpenRead(link));
|
||||||
|
Bitmap dest = new Bitmap(70, 70);
|
||||||
|
dest.SetResolution(src.HorizontalResolution, src.VerticalResolution);
|
||||||
|
using (Graphics g = Graphics.FromImage(dest))
|
||||||
|
{
|
||||||
|
g.CompositingMode = CompositingMode.SourceCopy;
|
||||||
|
g.CompositingQuality = CompositingQuality.HighQuality;
|
||||||
|
g.InterpolationMode = InterpolationMode.HighQualityBicubic;
|
||||||
|
g.SmoothingMode = SmoothingMode.HighQuality;
|
||||||
|
g.PixelOffsetMode = PixelOffsetMode.HighQuality;
|
||||||
|
using ImageAttributes wrapMode = new ImageAttributes();
|
||||||
|
wrapMode.SetWrapMode(WrapMode.TileFlipXY);
|
||||||
|
g.DrawImage(src, new Rectangle(0, 0, 70, 70), 0, 0, src.Width, src.Height,
|
||||||
|
GraphicsUnit.Pixel, wrapMode);
|
||||||
|
}
|
||||||
|
using MemoryStream ms = new MemoryStream();
|
||||||
|
dest.Save(ms, ImageFormat.Png);
|
||||||
|
return Convert.ToBase64String(ms.ToArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool YesNoDialog(string text, bool _) =>
|
||||||
|
MessageBox.Show(text, "", MessageBoxButtons.YesNo) == DialogResult.Yes;
|
||||||
|
|
||||||
|
public void OkDialog(string text) => MessageBox.Show(text);
|
||||||
|
public object GetDefaultIcon() => Resources.C_64.ToBitmap();
|
||||||
|
|
||||||
|
public object ImageFromB64(string b64) =>
|
||||||
|
(Bitmap) new ImageConverter().ConvertFrom(Convert.FromBase64String(b64));
|
||||||
|
|
||||||
|
public void Log(string text)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -1,12 +1,13 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk.WindowsDesktop">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>netcoreapp3.1</TargetFramework>
|
<TargetFramework>net5.0-windows</TargetFramework>
|
||||||
<OutputType>WinExe</OutputType>
|
<OutputType>WinExe</OutputType>
|
||||||
<LangVersion>latest</LangVersion>
|
<LangVersion>8</LangVersion>
|
||||||
<Deterministic>false</Deterministic>
|
<Deterministic>false</Deterministic>
|
||||||
<Nullable>enable</Nullable>
|
<Nullable>enable</Nullable>
|
||||||
<GenerateAssemblyInfo>false</GenerateAssemblyInfo>
|
|
||||||
<UseWindowsForms>true</UseWindowsForms>
|
<UseWindowsForms>true</UseWindowsForms>
|
||||||
|
<Deterministic>false</Deterministic>
|
||||||
|
<AssemblyVersion>1.0.*</AssemblyVersion>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
|
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
|
||||||
<DebugType>none</DebugType>
|
<DebugType>none</DebugType>
|
||||||
@ -19,6 +20,6 @@
|
|||||||
<Service Include="{508349B6-6B84-4DF5-91F0-309BEEBAD82D}" />
|
<Service Include="{508349B6-6B84-4DF5-91F0-309BEEBAD82D}" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<PackageReference Include="CC-Functions.Misc" Version="1.1.7384.27745" />
|
<ProjectReference Include="..\UpToolLib\UpToolLib.csproj" />
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
</Project>
|
</Project>
|
101
UpToolCLI/CacheManagement.cs
Normal file
101
UpToolCLI/CacheManagement.cs
Normal file
@ -0,0 +1,101 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.CommandLine;
|
||||||
|
using System.CommandLine.Invocation;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Reflection;
|
||||||
|
using UpToolLib;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
|
||||||
|
namespace UpToolCLI
|
||||||
|
{
|
||||||
|
public static class CacheManagement
|
||||||
|
{
|
||||||
|
public static void RegisterCommands(RootCommand rootCommand)
|
||||||
|
{
|
||||||
|
rootCommand.AddCommand(new Command("list", "Lists installed packages")
|
||||||
|
{
|
||||||
|
Handler = CommandHandler.Create(List)
|
||||||
|
});
|
||||||
|
|
||||||
|
Command search = new("search", "Search for packages")
|
||||||
|
{
|
||||||
|
new Argument<string>("identifier", "Something to identify the app")
|
||||||
|
};
|
||||||
|
search.Handler = CommandHandler.Create<string>(Search);
|
||||||
|
rootCommand.AddCommand(search);
|
||||||
|
|
||||||
|
Command show = new("show", "Shows package info")
|
||||||
|
{
|
||||||
|
new Argument<string>("identifier", "Something to identify the app")
|
||||||
|
};
|
||||||
|
show.Handler = CommandHandler.Create<string>(Show);
|
||||||
|
rootCommand.AddCommand(show);
|
||||||
|
|
||||||
|
rootCommand.AddCommand(new Command("update", "Updates the cache")
|
||||||
|
{
|
||||||
|
Handler = CommandHandler.Create(Update)
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void List()
|
||||||
|
{
|
||||||
|
Program.Lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
|
Console.WriteLine(Program.Lib.V1.Apps.Where(s => s.Value.Status.Contains(Status.Installed))
|
||||||
|
.ToStringTable(new[]
|
||||||
|
{
|
||||||
|
"Name", "State", "Guid"
|
||||||
|
},
|
||||||
|
u => u.Value.Name,
|
||||||
|
u => u.Value.Local ? "Local" :
|
||||||
|
u.Value.Status.Contains(Status.Updatable) ? "Updatable" : "None",
|
||||||
|
u => u.Key));
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void Search(string identifier)
|
||||||
|
{
|
||||||
|
Program.Lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
|
App[] apps = Program.Lib.V1.AppExtras.FindApps(identifier);
|
||||||
|
Console.WriteLine($"Found {apps.Length} app(s)");
|
||||||
|
if (apps.Length > 0)
|
||||||
|
Console.WriteLine(apps.ToStringTable(new[]
|
||||||
|
{
|
||||||
|
"Name", "Guid"
|
||||||
|
},
|
||||||
|
u => u.Name,
|
||||||
|
u => u.Id));
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void Show(string identifier)
|
||||||
|
{
|
||||||
|
Program.Lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
|
App[] apps = Program.Lib.V1.AppExtras.FindApps(identifier);
|
||||||
|
if (apps.Length == 0)
|
||||||
|
Console.WriteLine("Package not found.");
|
||||||
|
else
|
||||||
|
Console.WriteLine(apps.First());
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void Update()
|
||||||
|
{
|
||||||
|
Console.WriteLine("Fetching Repos...");
|
||||||
|
Program.Lib.V2.RepoManagement.FetchRepos();
|
||||||
|
Program.Lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
|
Console.WriteLine();
|
||||||
|
IEnumerable<App> tmp = Program.Lib.V1.Apps.Where(s =>
|
||||||
|
s.Value.Status.Contains(Status.Updatable)).Select(s => s.Value);
|
||||||
|
IEnumerable<App> apps = tmp as App[] ?? tmp.ToArray();
|
||||||
|
int updatableCount = apps.Count();
|
||||||
|
Console.WriteLine(updatableCount == 0
|
||||||
|
? "All up-to-date"
|
||||||
|
: $@"Found {updatableCount} Updates:
|
||||||
|
{string.Join(Environment.NewLine, apps.Select(s => $"- {s.Name} ({s.Version})"))}");
|
||||||
|
Version vLocal = Assembly.GetExecutingAssembly().GetName().Version;
|
||||||
|
Version vOnline = Program.Lib.V2.UpdateChecker.Check().OnlineVersion;
|
||||||
|
if (vLocal < vOnline)
|
||||||
|
Console.WriteLine($"uptool is outdated ({vLocal} vs {vOnline}), update using \"uptool upgrade-self\"");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
104
UpToolCLI/Other.cs
Normal file
104
UpToolCLI/Other.cs
Normal file
@ -0,0 +1,104 @@
|
|||||||
|
using System;
|
||||||
|
using System.CommandLine;
|
||||||
|
using System.CommandLine.Invocation;
|
||||||
|
using System.Diagnostics;
|
||||||
|
using System.IO;
|
||||||
|
using System.IO.Compression;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Reflection;
|
||||||
|
using System.Security.Cryptography;
|
||||||
|
using UpToolLib;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
using Process = System.Diagnostics.Process;
|
||||||
|
|
||||||
|
namespace UpToolCLI
|
||||||
|
{
|
||||||
|
public class Other
|
||||||
|
{
|
||||||
|
public static void RegisterCommands(RootCommand rootCommand)
|
||||||
|
{
|
||||||
|
Command command = new("upgrade-self", "Upgrades UpToolCLI")
|
||||||
|
{
|
||||||
|
new Option<bool>(new[] {"--force", "-f"}, "Overwrites older files")
|
||||||
|
};
|
||||||
|
command.Handler = CommandHandler.Create<bool>(UpgradeSelf);
|
||||||
|
rootCommand.AddCommand(command);
|
||||||
|
|
||||||
|
Command start = new("start", "Starts an app")
|
||||||
|
{
|
||||||
|
new Argument<string>("identifier", "Something to identify the app"),
|
||||||
|
new Option<string>(new[] {"--arguments", "--args", "-a"}, () => "", "The arguments to run the file with"),
|
||||||
|
new Option<string>(new[] {"--file", "-f"}, () => null, "The file to run instead of the MainFile"),
|
||||||
|
new Option<bool>(new[] {"--waitForExit", "-wait"}, "Waits until the program quits")
|
||||||
|
};
|
||||||
|
start.Handler = CommandHandler.Create<string, string, string, bool>(Start);
|
||||||
|
rootCommand.AddCommand(start);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void UpgradeSelf(bool force)
|
||||||
|
{
|
||||||
|
PathTool pathTool = Program.Lib.V1.PathTool;
|
||||||
|
UpdateCheck updateCheck = Program.Lib.V2.UpdateChecker.Check();
|
||||||
|
if (!force && Assembly.GetExecutingAssembly().GetName().Version >= updateCheck.OnlineVersion)
|
||||||
|
Console.WriteLine("Already up-to-date");
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Console.WriteLine("Downloading latest");
|
||||||
|
(bool success, byte[] dl) = Program.Functions.Download(updateCheck.Installer);
|
||||||
|
if (!success)
|
||||||
|
throw new Exception("Failed to update");
|
||||||
|
Console.WriteLine("Verifying");
|
||||||
|
using (SHA256CryptoServiceProvider sha256 = new())
|
||||||
|
{
|
||||||
|
string pkgHash = BitConverter.ToString(sha256.ComputeHash(dl)).Replace("-", string.Empty).ToUpper();
|
||||||
|
if (pkgHash != updateCheck.InstallerHash)
|
||||||
|
throw new Exception($@"The hash is not equal to the one stored in the repo:
|
||||||
|
Package: {pkgHash}
|
||||||
|
Online: {updateCheck.InstallerHash}");
|
||||||
|
}
|
||||||
|
Console.WriteLine("Installing");
|
||||||
|
if (Directory.Exists(pathTool.GetRelative("Install", "tmp")))
|
||||||
|
Directory.Delete(pathTool.GetRelative("Install", "tmp"), true);
|
||||||
|
Directory.CreateDirectory(pathTool.GetRelative("Install", "tmp"));
|
||||||
|
using (MemoryStream ms = new(dl))
|
||||||
|
{
|
||||||
|
using ZipArchive ar = new(ms);
|
||||||
|
ar.ExtractToDirectory(pathTool.GetRelative("Install", "tmp"), true);
|
||||||
|
}
|
||||||
|
string file = pathTool.GetRelative("Install", "tmp", "Installer.exe");
|
||||||
|
Console.WriteLine($"Starting {file}");
|
||||||
|
Process.Start(new ProcessStartInfo
|
||||||
|
{
|
||||||
|
FileName = file,
|
||||||
|
Arguments = "i",
|
||||||
|
WorkingDirectory = pathTool.GetRelative("Install"),
|
||||||
|
UseShellExecute = false
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void Start(string identifier, string arguments, string file, bool waitForExit)
|
||||||
|
{
|
||||||
|
Program.Lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
|
App[] apps = Program.Lib.V1.AppExtras.FindApps(identifier);
|
||||||
|
if (apps.Length == 0)
|
||||||
|
Console.WriteLine("Package not found.");
|
||||||
|
else
|
||||||
|
{
|
||||||
|
App tmp = apps.First();
|
||||||
|
if (tmp.Runnable)
|
||||||
|
{
|
||||||
|
Console.WriteLine($"Starting {tmp.Name}");
|
||||||
|
Process tmp1 = Program.Lib.V1.AppExtras.RunApp(tmp, file ?? tmp.MainFile, arguments);
|
||||||
|
if (waitForExit)
|
||||||
|
tmp1.WaitForExit();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
Console.WriteLine($"{tmp.Name} is not runnable");
|
||||||
|
}
|
||||||
|
Console.WriteLine("Done!");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
192
UpToolCLI/PackageManagement.cs
Normal file
192
UpToolCLI/PackageManagement.cs
Normal file
@ -0,0 +1,192 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.CommandLine;
|
||||||
|
using System.CommandLine.Invocation;
|
||||||
|
using System.Drawing;
|
||||||
|
using System.IO;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Reflection;
|
||||||
|
using UpToolLib;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
|
||||||
|
namespace UpToolCLI
|
||||||
|
{
|
||||||
|
public static class PackageManagement
|
||||||
|
{
|
||||||
|
public static void RegisterCommands(RootCommand rootCommand)
|
||||||
|
{
|
||||||
|
Command install = new("install", "Install a package")
|
||||||
|
{
|
||||||
|
new Argument<string>("identifier", "Something to identify the app or the file name"),
|
||||||
|
new Option<bool>(new[] {"--force", "-f"}, "Overwrites older files")
|
||||||
|
};
|
||||||
|
install.Handler = CommandHandler.Create<string, bool>(Install);
|
||||||
|
rootCommand.AddCommand(install);
|
||||||
|
|
||||||
|
Command upgrade = new("upgrade", "Upgrade a package")
|
||||||
|
{
|
||||||
|
new Argument<string>("identifier", "Something to identify the app"),
|
||||||
|
new Option<bool>(new[] {"--force", "-f"}, "Overwrites older files")
|
||||||
|
};
|
||||||
|
upgrade.Handler = CommandHandler.Create<string, bool>(Upgrade);
|
||||||
|
rootCommand.AddCommand(upgrade);
|
||||||
|
|
||||||
|
Command reinstall = new("reinstall", "Reinstall a package")
|
||||||
|
{
|
||||||
|
new Argument<string>("identifier", "Something to identify the app"),
|
||||||
|
new Option<bool>(new[] {"--force", "-f"}, "Overwrites older files")
|
||||||
|
};
|
||||||
|
reinstall.Handler = CommandHandler.Create<string, bool>(Reinstall);
|
||||||
|
rootCommand.AddCommand(reinstall);
|
||||||
|
|
||||||
|
Command remove = new("remove", "Remove a package")
|
||||||
|
{
|
||||||
|
new Argument<string>("identifier", "Something to identify the app")
|
||||||
|
};
|
||||||
|
remove.Handler = CommandHandler.Create<string>(Remove);
|
||||||
|
rootCommand.AddCommand(remove);
|
||||||
|
|
||||||
|
Command purge = new("purge", "Completely remove a package")
|
||||||
|
{
|
||||||
|
new Argument<string>("identifier", "Something to identify the app")
|
||||||
|
};
|
||||||
|
purge.Handler = CommandHandler.Create<string>(Purge);
|
||||||
|
rootCommand.AddCommand(purge);
|
||||||
|
|
||||||
|
rootCommand.AddCommand(new Command("dist-upgrade", "Upgrades all packages")
|
||||||
|
{
|
||||||
|
Handler = CommandHandler.Create(DistUpgrade)
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void Install(string identifier, bool force)
|
||||||
|
{
|
||||||
|
Program.Lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
|
App[] apps = Program.Lib.V1.AppExtras.FindApps(identifier);
|
||||||
|
if (apps.Length == 0)
|
||||||
|
{
|
||||||
|
if (File.Exists(identifier))
|
||||||
|
{
|
||||||
|
Console.WriteLine("Name:");
|
||||||
|
string name = Console.ReadLine();
|
||||||
|
Program.Lib.V1.Installer.InstallZip(identifier, Program.Lib.V2.AppFactory.CreateApp(name, "Locally installed package, removal only",
|
||||||
|
UpToolLibV1.MinimumVer, "", true, "",
|
||||||
|
Guid.NewGuid(), Color.Red, "", false, ""), force);
|
||||||
|
Console.WriteLine($"Successfully installed \"{name}\"");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Console.WriteLine("Package not found.");
|
||||||
|
Console.WriteLine(identifier);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
App tmp = apps.First();
|
||||||
|
if (tmp.Status.Contains(Status.Installed))
|
||||||
|
Console.WriteLine("Package is already installed");
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Console.WriteLine($"Installing {tmp.Name}");
|
||||||
|
Program.Lib.V1.Installer.Install(tmp, true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Console.WriteLine("Done!");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void Upgrade(string identifier, bool force)
|
||||||
|
{
|
||||||
|
Program.Lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
|
App[] apps = Program.Lib.V1.AppExtras.FindApps(identifier);
|
||||||
|
if (apps.Length == 0)
|
||||||
|
Console.WriteLine("Package not found.");
|
||||||
|
else
|
||||||
|
{
|
||||||
|
App tmp = apps.First();
|
||||||
|
if (tmp.Status.Contains(Status.Updatable))
|
||||||
|
{
|
||||||
|
Console.WriteLine($"Upgrading {tmp.Name}");
|
||||||
|
Program.Lib.V1.AppExtras.Update(tmp, force);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
Console.WriteLine("Package is up-to-date");
|
||||||
|
}
|
||||||
|
Console.WriteLine("Done!");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void Reinstall(string identifier, bool force)
|
||||||
|
{
|
||||||
|
Program.Lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
|
App[] apps = Program.Lib.V1.AppExtras.FindApps(identifier);
|
||||||
|
if (apps.Length == 0)
|
||||||
|
Console.WriteLine("Package not found.");
|
||||||
|
else
|
||||||
|
{
|
||||||
|
App tmp = apps.First();
|
||||||
|
Console.WriteLine($"Reinstalling {tmp.Name}");
|
||||||
|
Program.Lib.V1.AppExtras.Update(tmp, force);
|
||||||
|
}
|
||||||
|
Console.WriteLine("Done!");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void Remove(string identifier)
|
||||||
|
{
|
||||||
|
Program.Lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
|
App[] apps = Program.Lib.V1.AppExtras.FindApps(identifier);
|
||||||
|
if (apps.Length == 0)
|
||||||
|
Console.WriteLine("Package not found.");
|
||||||
|
else
|
||||||
|
{
|
||||||
|
App tmp = apps.First();
|
||||||
|
if (tmp.Status.Contains(Status.Installed))
|
||||||
|
{
|
||||||
|
Console.WriteLine($"Removing {tmp.Name}");
|
||||||
|
Program.Lib.V1.AppExtras.Remove(tmp, false);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
Console.WriteLine("Package is not installed");
|
||||||
|
}
|
||||||
|
Console.WriteLine("Done!");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void Purge(string identifier)
|
||||||
|
{
|
||||||
|
Program.Lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
|
App[] apps = Program.Lib.V1.AppExtras.FindApps(identifier);
|
||||||
|
if (apps.Length == 0)
|
||||||
|
Console.WriteLine("Package not found.");
|
||||||
|
else
|
||||||
|
{
|
||||||
|
App tmp = apps.First();
|
||||||
|
if (tmp.Status.Contains(Status.Installed))
|
||||||
|
{
|
||||||
|
Console.WriteLine($"Purging {tmp.Name}");
|
||||||
|
Program.Lib.V1.AppExtras.Remove(tmp, true);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
Console.WriteLine("Package is not installed");
|
||||||
|
}
|
||||||
|
Console.WriteLine("Done!");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void DistUpgrade()
|
||||||
|
{
|
||||||
|
Program.Lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
|
foreach (KeyValuePair<Guid, App> app in Program.Lib.V1.Apps.Where(s =>
|
||||||
|
s.Value.Status.Contains(Status.Updatable)))
|
||||||
|
{
|
||||||
|
Console.WriteLine($"Updating {app.Value.Name}");
|
||||||
|
Program.Lib.V1.AppExtras.Update(app.Value, false);
|
||||||
|
}
|
||||||
|
if (Assembly.GetExecutingAssembly().GetName().Version < Program.Lib.V2.UpdateChecker.Check().OnlineVersion)
|
||||||
|
{
|
||||||
|
Console.WriteLine("Updating self");
|
||||||
|
Other.UpgradeSelf(false);
|
||||||
|
}
|
||||||
|
Console.WriteLine("Done!");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
41
UpToolCLI/Program.cs
Normal file
41
UpToolCLI/Program.cs
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
using System;
|
||||||
|
using System.CommandLine;
|
||||||
|
using UpToolLib;
|
||||||
|
|
||||||
|
namespace UpToolCLI
|
||||||
|
{
|
||||||
|
public static class Program
|
||||||
|
{
|
||||||
|
public static readonly UtLibFunctions Functions = new();
|
||||||
|
public static bool Basic;
|
||||||
|
public static UpToolLibMain Lib;
|
||||||
|
|
||||||
|
public static int Main(string[] args)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
Basic = args.Length > 0 && args[0].ToLower() == "--basic";
|
||||||
|
Lib = new UpToolLibMain(Functions);
|
||||||
|
Lib.V1.XmlTool.FixXml();
|
||||||
|
RootCommand rootCommand = new();
|
||||||
|
rootCommand.AddGlobalOption(new Option<bool>("--basic", "Use only basic console functionality. Must be the first parameter in the call"));
|
||||||
|
|
||||||
|
PackageManagement.RegisterCommands(rootCommand);
|
||||||
|
CacheManagement.RegisterCommands(rootCommand);
|
||||||
|
ReposManagement.RegisterCommands(rootCommand);
|
||||||
|
Other.RegisterCommands(rootCommand);
|
||||||
|
|
||||||
|
return rootCommand.InvokeAsync(args).Result;
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
Console.WriteLine($"FAILED: {e}");
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
Lib?.Dispose();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
93
UpToolCLI/ReposManagement.cs
Normal file
93
UpToolCLI/ReposManagement.cs
Normal file
@ -0,0 +1,93 @@
|
|||||||
|
using System;
|
||||||
|
using System.CommandLine;
|
||||||
|
using System.CommandLine.Invocation;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Xml.Linq;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
|
||||||
|
namespace UpToolCLI
|
||||||
|
{
|
||||||
|
public class ReposManagement
|
||||||
|
{
|
||||||
|
private static string InfoXml => Program.Lib.V1.PathTool.InfoXml;
|
||||||
|
public static void RegisterCommands(RootCommand rootCommand)
|
||||||
|
{
|
||||||
|
rootCommand.AddCommand(new Command("list-repo", "Lists current repositories")
|
||||||
|
{
|
||||||
|
Handler = CommandHandler.Create(ListRepo)
|
||||||
|
});
|
||||||
|
|
||||||
|
Command addRepo = new("add-repo", "Adds a repository")
|
||||||
|
{
|
||||||
|
new Argument<string>("name", "The new repositories name"),
|
||||||
|
new Argument<string>("link", "A link to the repositories XML")
|
||||||
|
};
|
||||||
|
addRepo.Handler = CommandHandler.Create<string, string>(AddRepo);
|
||||||
|
rootCommand.AddCommand(addRepo);
|
||||||
|
|
||||||
|
Command removeRepo = new("remove-repo", "Removes a repository")
|
||||||
|
{
|
||||||
|
new Argument<string>("name", "The repositories name")
|
||||||
|
};
|
||||||
|
removeRepo.Handler = CommandHandler.Create<string>(RemoveRepo);
|
||||||
|
rootCommand.AddCommand(removeRepo);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void ListRepo()
|
||||||
|
{
|
||||||
|
XDocument doc = XDocument.Load(InfoXml);
|
||||||
|
XElement repos = doc.Element("meta").Element("Repos");
|
||||||
|
Console.WriteLine("Current repos:");
|
||||||
|
Console.WriteLine(repos.Elements("Repo").ToStringTable(new[]
|
||||||
|
{
|
||||||
|
"Name", "Link"
|
||||||
|
},
|
||||||
|
u => u.Element("Name").Value,
|
||||||
|
u => u.Element("Link").Value));
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void AddRepo(string name, string link)
|
||||||
|
{
|
||||||
|
XDocument doc = XDocument.Load(InfoXml);
|
||||||
|
XElement repos = doc.Element("meta").Element("Repos");
|
||||||
|
repos.Add(new XElement("Repo", new XElement("Name", name),
|
||||||
|
new XElement("Link", link)));
|
||||||
|
doc.Save(InfoXml);
|
||||||
|
Console.WriteLine("Added repo. Remember to update the cache using \"uptool update\"");
|
||||||
|
}
|
||||||
|
|
||||||
|
private static void RemoveRepo(string name)
|
||||||
|
{
|
||||||
|
XDocument doc = XDocument.Load(InfoXml);
|
||||||
|
XElement repos = doc.Element("meta").Element("Repos");
|
||||||
|
XElement[] sRepos = repos.Elements("Repo")
|
||||||
|
.Where(s => s.Element("Name").Value.ToLower().StartsWith(name.ToLower())).ToArray();
|
||||||
|
switch (sRepos.Length)
|
||||||
|
{
|
||||||
|
case 0:
|
||||||
|
Console.WriteLine("No repo was found that matches your input!");
|
||||||
|
return;
|
||||||
|
case 1:
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
Console.WriteLine("Found multiple repos that match your input:");
|
||||||
|
Console.WriteLine(sRepos.ToStringTable(new[]
|
||||||
|
{
|
||||||
|
"Name", "Link"
|
||||||
|
},
|
||||||
|
u => u.Element("Name").Value,
|
||||||
|
u => u.Element("Link").Value));
|
||||||
|
if (!Program.Functions.YesNoDialog("Are you sure you want to delete them all?", false))
|
||||||
|
return;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
foreach (XElement t in sRepos)
|
||||||
|
{
|
||||||
|
Console.WriteLine($"Removing {t.Element("Name").Value}");
|
||||||
|
t.Remove();
|
||||||
|
}
|
||||||
|
doc.Save(InfoXml);
|
||||||
|
Console.WriteLine("Removed repo. Remember to update the cache using \"uptool update\"");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
104
UpToolCLI/TableParser.cs
Normal file
104
UpToolCLI/TableParser.cs
Normal file
@ -0,0 +1,104 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Diagnostics;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Linq.Expressions;
|
||||||
|
using System.Reflection;
|
||||||
|
using System.Text;
|
||||||
|
|
||||||
|
namespace UpToolCLI
|
||||||
|
{
|
||||||
|
public static class TableParser
|
||||||
|
{
|
||||||
|
public static string ToStringTable<T>(this IEnumerable<T> values, string[] columnHeaders,
|
||||||
|
params Func<T, object>[] valueSelectors) => ToStringTable(values.ToArray(), columnHeaders, valueSelectors);
|
||||||
|
|
||||||
|
public static string ToStringTable<T>(this T[] values, string[] columnHeaders,
|
||||||
|
params Func<T, object>[] valueSelectors)
|
||||||
|
{
|
||||||
|
Debug.Assert(columnHeaders.Length == valueSelectors.Length);
|
||||||
|
|
||||||
|
string[,] arrValues = new string[values.Length + 1, valueSelectors.Length];
|
||||||
|
|
||||||
|
// Fill headers
|
||||||
|
for (int colIndex = 0; colIndex < arrValues.GetLength(1); colIndex++)
|
||||||
|
arrValues[0, colIndex] = columnHeaders[colIndex];
|
||||||
|
|
||||||
|
// Fill table rows
|
||||||
|
for (int rowIndex = 1; rowIndex < arrValues.GetLength(0); rowIndex++)
|
||||||
|
for (int colIndex = 0; colIndex < arrValues.GetLength(1); colIndex++)
|
||||||
|
{
|
||||||
|
object value = valueSelectors[colIndex].Invoke(values[rowIndex - 1]);
|
||||||
|
|
||||||
|
arrValues[rowIndex, colIndex] = value != null ? value.ToString() : "null";
|
||||||
|
}
|
||||||
|
|
||||||
|
return ToStringTable(arrValues);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static string ToStringTable(this string[,] arrValues)
|
||||||
|
{
|
||||||
|
int[] maxColumnsWidth = GetMaxColumnsWidth(arrValues);
|
||||||
|
string headerSpliter = new('-', maxColumnsWidth.Sum(i => i + 3) - 1);
|
||||||
|
|
||||||
|
StringBuilder sb = new();
|
||||||
|
for (int rowIndex = 0; rowIndex < arrValues.GetLength(0); rowIndex++)
|
||||||
|
{
|
||||||
|
for (int colIndex = 0; colIndex < arrValues.GetLength(1); colIndex++)
|
||||||
|
{
|
||||||
|
// Print cell
|
||||||
|
string cell = arrValues[rowIndex, colIndex];
|
||||||
|
cell = cell.PadRight(maxColumnsWidth[colIndex]);
|
||||||
|
sb.Append(" | ");
|
||||||
|
sb.Append(cell);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Print end of line
|
||||||
|
sb.Append(" | ");
|
||||||
|
sb.AppendLine();
|
||||||
|
|
||||||
|
// Print splitter
|
||||||
|
if (rowIndex == 0)
|
||||||
|
{
|
||||||
|
sb.AppendFormat(" |{0}| ", headerSpliter);
|
||||||
|
sb.AppendLine();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return sb.ToString();
|
||||||
|
}
|
||||||
|
|
||||||
|
private static int[] GetMaxColumnsWidth(string[,] arrValues)
|
||||||
|
{
|
||||||
|
int[] maxColumnsWidth = new int[arrValues.GetLength(1)];
|
||||||
|
for (int colIndex = 0; colIndex < arrValues.GetLength(1); colIndex++)
|
||||||
|
for (int rowIndex = 0; rowIndex < arrValues.GetLength(0); rowIndex++)
|
||||||
|
{
|
||||||
|
int newLength = arrValues[rowIndex, colIndex].Length;
|
||||||
|
int oldLength = maxColumnsWidth[colIndex];
|
||||||
|
|
||||||
|
if (newLength > oldLength) maxColumnsWidth[colIndex] = newLength;
|
||||||
|
}
|
||||||
|
|
||||||
|
return maxColumnsWidth;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static string ToStringTable<T>(this IEnumerable<T> values,
|
||||||
|
params Expression<Func<T, object>>[] valueSelectors)
|
||||||
|
{
|
||||||
|
string[] headers = valueSelectors.Select(func => GetProperty(func).Name).ToArray();
|
||||||
|
Func<T, object>[] selectors = valueSelectors.Select(exp => exp.Compile()).ToArray();
|
||||||
|
return ToStringTable(values, headers, selectors);
|
||||||
|
}
|
||||||
|
|
||||||
|
private static PropertyInfo GetProperty<T>(Expression<Func<T, object>> expresstion)
|
||||||
|
{
|
||||||
|
if (expresstion.Body is UnaryExpression expression)
|
||||||
|
if (expression.Operand is MemberExpression memberExpression)
|
||||||
|
return memberExpression.Member as PropertyInfo;
|
||||||
|
|
||||||
|
if (expresstion.Body is MemberExpression body) return body.Member as PropertyInfo;
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
117
UpToolCLI/UTLibFunctions.cs
Normal file
117
UpToolCLI/UTLibFunctions.cs
Normal file
@ -0,0 +1,117 @@
|
|||||||
|
using System;
|
||||||
|
using System.IO;
|
||||||
|
using System.Net;
|
||||||
|
using System.Threading;
|
||||||
|
using SixLabors.ImageSharp;
|
||||||
|
using SixLabors.ImageSharp.Processing;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using static UpToolCLI.Program;
|
||||||
|
|
||||||
|
namespace UpToolCLI
|
||||||
|
{
|
||||||
|
public class UtLibFunctions : IExternalFunctionality
|
||||||
|
{
|
||||||
|
public Tuple<bool, byte[]> Download(Uri link)
|
||||||
|
{
|
||||||
|
using WebClient client = new();
|
||||||
|
byte[] result = new byte[0];
|
||||||
|
bool finished = false;
|
||||||
|
bool success = true;
|
||||||
|
client.DownloadDataCompleted += (sender, e) =>
|
||||||
|
{
|
||||||
|
success = !e.Cancelled;
|
||||||
|
if (success)
|
||||||
|
result = e.Result;
|
||||||
|
finished = true;
|
||||||
|
};
|
||||||
|
client.DownloadProgressChanged += (sender, e) =>
|
||||||
|
{
|
||||||
|
if (!Basic)
|
||||||
|
{
|
||||||
|
Console.Write(
|
||||||
|
$"{new string('=', e.ProgressPercentage / 10)}[{e.ProgressPercentage}]{new string('-', 10 - e.ProgressPercentage / 10)}");
|
||||||
|
Console.CursorLeft = 0;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
client.DownloadDataAsync(link);
|
||||||
|
while (!finished)
|
||||||
|
Thread.Sleep(100);
|
||||||
|
return new Tuple<bool, byte[]>(success, result);
|
||||||
|
}
|
||||||
|
|
||||||
|
public string FetchImageB64(Uri link)
|
||||||
|
{
|
||||||
|
using WebClient client = new();
|
||||||
|
using Image image = Image.Load(client.OpenRead(link));
|
||||||
|
image.Mutate(x => x.Resize(70, 70));
|
||||||
|
using MemoryStream ms = new();
|
||||||
|
image.SaveAsPng(ms);
|
||||||
|
return Convert.ToBase64String(ms.ToArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool YesNoDialog(string text, bool defaultVal)
|
||||||
|
{
|
||||||
|
if (Basic)
|
||||||
|
{
|
||||||
|
Console.WriteLine(text);
|
||||||
|
Console.WriteLine($"Selecting: {defaultVal}");
|
||||||
|
return defaultVal;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
bool choosing = true;
|
||||||
|
bool current = defaultVal;
|
||||||
|
Console.WriteLine(text);
|
||||||
|
while (choosing)
|
||||||
|
{
|
||||||
|
Console.CursorLeft = 0;
|
||||||
|
Console.BackgroundColor = current ? ConsoleColor.White : ConsoleColor.Black;
|
||||||
|
Console.ForegroundColor = current ? ConsoleColor.Black : ConsoleColor.White;
|
||||||
|
Console.Write("Yes");
|
||||||
|
Console.ResetColor();
|
||||||
|
Console.Write(" ");
|
||||||
|
Console.BackgroundColor = current ? ConsoleColor.Black : ConsoleColor.White;
|
||||||
|
Console.ForegroundColor = current ? ConsoleColor.White : ConsoleColor.Black;
|
||||||
|
Console.Write("No");
|
||||||
|
Console.ResetColor();
|
||||||
|
switch (Console.ReadKey().Key)
|
||||||
|
{
|
||||||
|
case ConsoleKey.LeftArrow:
|
||||||
|
case ConsoleKey.RightArrow:
|
||||||
|
current = !current;
|
||||||
|
break;
|
||||||
|
case ConsoleKey.Enter:
|
||||||
|
choosing = false;
|
||||||
|
break;
|
||||||
|
case ConsoleKey.Escape:
|
||||||
|
current = defaultVal;
|
||||||
|
choosing = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Console.ResetColor();
|
||||||
|
Console.WriteLine($" Selecting: {current}");
|
||||||
|
return current;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void OkDialog(string text)
|
||||||
|
{
|
||||||
|
if (Basic)
|
||||||
|
Console.WriteLine(text);
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Console.WriteLine(text);
|
||||||
|
Console.BackgroundColor = ConsoleColor.White;
|
||||||
|
Console.Write("OK");
|
||||||
|
Console.ResetColor();
|
||||||
|
Console.ReadKey();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public object GetDefaultIcon() => 0;
|
||||||
|
|
||||||
|
public object ImageFromB64(string b64) => 0;
|
||||||
|
public void Log(string text) => Console.WriteLine(text);
|
||||||
|
}
|
||||||
|
}
|
24
UpToolCLI/UpToolCLI.csproj
Normal file
24
UpToolCLI/UpToolCLI.csproj
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<OutputType>Exe</OutputType>
|
||||||
|
<TargetFramework>net5.0</TargetFramework>
|
||||||
|
<AssemblyName>uptool</AssemblyName>
|
||||||
|
<Deterministic>false</Deterministic>
|
||||||
|
<AssemblyVersion>1.0.*</AssemblyVersion>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<ApplicationIcon>..\UpTool2.ico</ApplicationIcon>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<PackageReference Include="SixLabors.ImageSharp" Version="1.0.2" />
|
||||||
|
<PackageReference Include="System.CommandLine" Version="2.0.0-beta1.20574.7" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<ProjectReference Include="..\UpToolLib\UpToolLib.csproj" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
</Project>
|
17
UpToolEto/UpToolEto.Gtk/Program.cs
Normal file
17
UpToolEto/UpToolEto.Gtk/Program.cs
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
using System;
|
||||||
|
using Eto.Forms;
|
||||||
|
|
||||||
|
namespace UpToolEto.Gtk
|
||||||
|
{
|
||||||
|
class MainClass
|
||||||
|
{
|
||||||
|
[STAThread]
|
||||||
|
public static void Main(string[] args)
|
||||||
|
{
|
||||||
|
new Main(new Application(Eto.Platforms.Gtk), () =>
|
||||||
|
{
|
||||||
|
|
||||||
|
}, args).Entry();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
16
UpToolEto/UpToolEto.Gtk/UpToolEto.Gtk.csproj
Normal file
16
UpToolEto/UpToolEto.Gtk/UpToolEto.Gtk.csproj
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<OutputType>WinExe</OutputType>
|
||||||
|
<TargetFramework>net5.0</TargetFramework>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<ProjectReference Include="..\UpToolEto\UpToolEto.csproj"/>
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<PackageReference Include="Eto.Platform.Gtk" Version="2.5.10"/>
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
</Project>
|
38
UpToolEto/UpToolEto.Wpf/Program.cs
Normal file
38
UpToolEto/UpToolEto.Wpf/Program.cs
Normal file
@ -0,0 +1,38 @@
|
|||||||
|
using System;
|
||||||
|
using Eto.Forms;
|
||||||
|
using System.Diagnostics;
|
||||||
|
using System.Runtime.InteropServices;
|
||||||
|
|
||||||
|
namespace UpToolEto.Wpf
|
||||||
|
{
|
||||||
|
class MainClass
|
||||||
|
{
|
||||||
|
[STAThread]
|
||||||
|
public static void Main(string[] args)
|
||||||
|
{
|
||||||
|
new Main(new Application(Eto.Platforms.Wpf), () =>
|
||||||
|
{
|
||||||
|
Process[] processes = Process.GetProcessesByName("UpTool2");
|
||||||
|
if (processes.Length > 0)
|
||||||
|
BringProcessToFront(processes[0]);
|
||||||
|
}, args).Entry();
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void BringProcessToFront(Process process)
|
||||||
|
{
|
||||||
|
IntPtr handle = process.MainWindowHandle;
|
||||||
|
if (IsIconic(handle))
|
||||||
|
ShowWindow(handle, 9);
|
||||||
|
SetForegroundWindow(handle);
|
||||||
|
}
|
||||||
|
|
||||||
|
[DllImport("User32.dll")]
|
||||||
|
private static extern bool SetForegroundWindow(IntPtr handle);
|
||||||
|
|
||||||
|
[DllImport("User32.dll")]
|
||||||
|
private static extern bool ShowWindow(IntPtr handle, int nCmdShow);
|
||||||
|
|
||||||
|
[DllImport("User32.dll")]
|
||||||
|
private static extern bool IsIconic(IntPtr handle);
|
||||||
|
}
|
||||||
|
}
|
16
UpToolEto/UpToolEto.Wpf/UpToolEto.Wpf.csproj
Normal file
16
UpToolEto/UpToolEto.Wpf/UpToolEto.Wpf.csproj
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<OutputType>WinExe</OutputType>
|
||||||
|
<TargetFramework>net5.0-windows</TargetFramework>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<ProjectReference Include="..\UpToolEto\UpToolEto.csproj"/>
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<PackageReference Include="Eto.Platform.Wpf" Version="2.5.10"/>
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
</Project>
|
65
UpToolEto/UpToolEto/Controls/AppControlButton.cs
Normal file
65
UpToolEto/UpToolEto/Controls/AppControlButton.cs
Normal file
@ -0,0 +1,65 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using Eto.Drawing;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
using UpToolLib.v2.TaskQueue;
|
||||||
|
|
||||||
|
namespace UpToolEto.Controls
|
||||||
|
{
|
||||||
|
public abstract class AppControlButton : Button
|
||||||
|
{
|
||||||
|
public abstract void ReloadState();
|
||||||
|
public abstract void SetApp(App app);
|
||||||
|
public abstract void Clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
public class AppControlButton<T> : AppControlButton where T : KnownAppTask
|
||||||
|
{
|
||||||
|
private readonly IList<AppTask> _tasks;
|
||||||
|
private readonly Func<App, bool> _enabledCheck;
|
||||||
|
private readonly Color _defaultColor;
|
||||||
|
private App _app;
|
||||||
|
|
||||||
|
public AppControlButton(string text, Func<App, Action?, AppTask> factory, IList<AppTask> tasks, Action reloadState, Func<App, bool> enabledCheck)
|
||||||
|
{
|
||||||
|
_tasks = tasks;
|
||||||
|
_enabledCheck = enabledCheck;
|
||||||
|
_defaultColor = BackgroundColor;
|
||||||
|
Text = text;
|
||||||
|
Click += (_, _) =>
|
||||||
|
{
|
||||||
|
bool found = false;
|
||||||
|
for (var i = tasks.ToArray().Length - 1; i >= 0; i--)
|
||||||
|
{
|
||||||
|
if (tasks[i] is T t && t.App == _app)
|
||||||
|
{
|
||||||
|
found = true;
|
||||||
|
tasks.RemoveAt(i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (!found)
|
||||||
|
tasks.Add(factory(_app, ReloadState));
|
||||||
|
reloadState();
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
public override void ReloadState()
|
||||||
|
{
|
||||||
|
Enabled = _enabledCheck(_app);
|
||||||
|
BackgroundColor = _tasks.Any(s => s is T t && t.App == _app) ? Colors.Green : _defaultColor;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override void SetApp(App app)
|
||||||
|
{
|
||||||
|
_app = app;
|
||||||
|
ReloadState();
|
||||||
|
}
|
||||||
|
|
||||||
|
public override void Clear()
|
||||||
|
{
|
||||||
|
Enabled = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
83
UpToolEto/UpToolEto/Controls/AppControls.cs
Normal file
83
UpToolEto/UpToolEto/Controls/AppControls.cs
Normal file
@ -0,0 +1,83 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using Eto.Drawing;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolEto.Forms;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
using UpToolLib.v2.TaskQueue;
|
||||||
|
|
||||||
|
namespace UpToolEto.Controls
|
||||||
|
{
|
||||||
|
public class AppControls : StackLayout
|
||||||
|
{
|
||||||
|
private readonly IList<AppTask> _tasks;
|
||||||
|
private readonly List<AppControlButton> _buttons;
|
||||||
|
private readonly Button _applyButton;
|
||||||
|
public AppControls(TaskFactory factory, IList<AppTask> tasks, IExternalFunctionality platform, Action update)
|
||||||
|
{
|
||||||
|
_tasks = tasks;
|
||||||
|
_buttons = new List<AppControlButton>
|
||||||
|
{
|
||||||
|
new AppControlButton<InstallTask>("Install", factory.CreateInstall, tasks, ReloadState,
|
||||||
|
app => !app.Status.Contains(Status.Installed)),
|
||||||
|
new AppControlButton<UpdateTask>("Update", factory.CreateUpdate, tasks, ReloadState,
|
||||||
|
app => app.Status.Contains(Status.Updatable)),
|
||||||
|
new AppControlButton<RemoveTask>("Remove", factory.CreateRemove, tasks, ReloadState,
|
||||||
|
app => app.Status.Contains(Status.Installed))
|
||||||
|
};
|
||||||
|
_applyButton = new Button((_, _) =>
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
QueueOverview overview = new(tasks);
|
||||||
|
overview.ShowModal();
|
||||||
|
if (!overview.Cancelled)
|
||||||
|
{
|
||||||
|
foreach (AppTask task in overview.TasksResulting)
|
||||||
|
{
|
||||||
|
task.Run();
|
||||||
|
_tasks.RemoveAt(0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
platform.OkDialog("Failed to complete queue:\r\n" + e);
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
ReloadState();
|
||||||
|
update();
|
||||||
|
}
|
||||||
|
})
|
||||||
|
{
|
||||||
|
Text = "Apply",
|
||||||
|
Enabled = false
|
||||||
|
};
|
||||||
|
foreach (AppControlButton button in _buttons) Items.Add(button);
|
||||||
|
Items.Add(new StackLayoutItem(_applyButton, HorizontalAlignment.Right));
|
||||||
|
if (Main.DebugColors)
|
||||||
|
BackgroundColor = Colors.Yellow;
|
||||||
|
Orientation = Orientation.Horizontal;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void SetApp(App app)
|
||||||
|
{
|
||||||
|
foreach (AppControlButton button in _buttons) button.SetApp(app);
|
||||||
|
ReloadState();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Clear()
|
||||||
|
{
|
||||||
|
foreach (AppControlButton button in _buttons) button.Clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void ReloadState()
|
||||||
|
{
|
||||||
|
foreach (AppControlButton button in _buttons) button.ReloadState();
|
||||||
|
_applyButton.Enabled = _tasks.Any();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
58
UpToolEto/UpToolEto/Controls/AppList.cs
Normal file
58
UpToolEto/UpToolEto/Controls/AppList.cs
Normal file
@ -0,0 +1,58 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using Eto.Drawing;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolEto.Forms;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
using UpToolLib.v2.TaskQueue;
|
||||||
|
|
||||||
|
namespace UpToolEto.Controls
|
||||||
|
{
|
||||||
|
public class AppList : StackLayout
|
||||||
|
{
|
||||||
|
private readonly AppExtras _extras;
|
||||||
|
private readonly Action<Guid, App> _itemClickEvent;
|
||||||
|
private readonly StackLayout _layout;
|
||||||
|
private readonly AppListSearchProvider _searchProvider;
|
||||||
|
|
||||||
|
public AppList(AppExtras extras, Action<Guid, App> itemClickEvent, bool online, TaskFactory factory, IList<AppTask> tasks)
|
||||||
|
{
|
||||||
|
_extras = extras;
|
||||||
|
_itemClickEvent = itemClickEvent;
|
||||||
|
_searchProvider = new AppListSearchProvider(online, Update);
|
||||||
|
Items.Add(_searchProvider);
|
||||||
|
_layout = new StackLayout
|
||||||
|
{
|
||||||
|
Padding = 10,
|
||||||
|
Orientation = Orientation.Vertical,
|
||||||
|
Width = 200
|
||||||
|
};
|
||||||
|
Scrollable scrollable = new()
|
||||||
|
{
|
||||||
|
Content = _layout
|
||||||
|
};
|
||||||
|
if (Main.DebugColors)
|
||||||
|
scrollable.BackgroundColor = Colors.YellowGreen;
|
||||||
|
Items.Add(new StackLayoutItem(scrollable, VerticalAlignment.Stretch, true));
|
||||||
|
Orientation = Orientation.Vertical;
|
||||||
|
if (Main.DebugColors)
|
||||||
|
BackgroundColor = Colors.Green;
|
||||||
|
Update();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Update()
|
||||||
|
{
|
||||||
|
_layout.Items.Clear();
|
||||||
|
foreach (App app in _extras.FindApps(_searchProvider.GetSearchTerms()))
|
||||||
|
if (_searchProvider.Matches(app))
|
||||||
|
_layout.Items.Add(new Button((_, _) => _itemClickEvent(app.Id, app))
|
||||||
|
{
|
||||||
|
Text = app.Name,
|
||||||
|
Image = (Icon)app.Icon,
|
||||||
|
ImagePosition = ButtonImagePosition.Left,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
32
UpToolEto/UpToolEto/Controls/AppListSearchProvider.cs
Normal file
32
UpToolEto/UpToolEto/Controls/AppListSearchProvider.cs
Normal file
@ -0,0 +1,32 @@
|
|||||||
|
using System;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
|
||||||
|
namespace UpToolEto.Controls
|
||||||
|
{
|
||||||
|
public class AppListSearchProvider : StackLayout
|
||||||
|
{
|
||||||
|
private readonly bool _online;
|
||||||
|
private readonly TextBox _search;
|
||||||
|
private readonly EnumDropDown<Status> _state;
|
||||||
|
|
||||||
|
public AppListSearchProvider(bool online, Action refresh)
|
||||||
|
{
|
||||||
|
_online = online;
|
||||||
|
_search = new SearchBox();
|
||||||
|
_state = new EnumDropDown<Status>();
|
||||||
|
_state.SelectedValue = online ? Status.NotInstalled : Status.Installed;
|
||||||
|
_state.Enabled = online;
|
||||||
|
_search.TextChanged += (_, _) => refresh();
|
||||||
|
_state.SelectedIndexChanged += (_, _) => refresh();
|
||||||
|
Orientation = Orientation.Vertical;
|
||||||
|
Items.Add(new StackLayoutItem(_search, HorizontalAlignment.Stretch));
|
||||||
|
Items.Add(_state);
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool Matches(App app) => app.Status.Contains(_online ? _state.SelectedValue : Status.Installed);
|
||||||
|
|
||||||
|
public string GetSearchTerms() => _search.Text;
|
||||||
|
}
|
||||||
|
}
|
70
UpToolEto/UpToolEto/Controls/AppPanel.cs
Normal file
70
UpToolEto/UpToolEto/Controls/AppPanel.cs
Normal file
@ -0,0 +1,70 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using Eto.Drawing;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
using UpToolLib.v2.TaskQueue;
|
||||||
|
|
||||||
|
namespace UpToolEto.Controls
|
||||||
|
{
|
||||||
|
public class AppPanel : Panel
|
||||||
|
{
|
||||||
|
private readonly Button _appNameLabel;
|
||||||
|
private readonly Label _appDescriptionLabel;
|
||||||
|
private readonly AppControls _appControls;
|
||||||
|
private App _app;
|
||||||
|
public AppPanel(TaskFactory factory, AppExtras extras, IList<AppTask> tasks, IExternalFunctionality platform, Action updateAppList)
|
||||||
|
{
|
||||||
|
_appDescriptionLabel = new Label();
|
||||||
|
_appNameLabel = new Button((_, _) =>
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
extras.RunApp(_app);
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
platform.OkDialog("Failed to start\r\n" + e);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
_appNameLabel.Font = new Font(_appNameLabel.Font.Family, _appNameLabel.Font.Size * 2);
|
||||||
|
_appControls = new AppControls(factory, tasks, platform, () =>
|
||||||
|
{
|
||||||
|
updateAppList();
|
||||||
|
SetApp(_app);
|
||||||
|
});
|
||||||
|
Content = new StackLayout
|
||||||
|
{
|
||||||
|
Items =
|
||||||
|
{
|
||||||
|
new StackLayoutItem(_appNameLabel, HorizontalAlignment.Center),
|
||||||
|
new StackLayoutItem(_appDescriptionLabel, HorizontalAlignment.Center, true),
|
||||||
|
new StackLayoutItem(_appControls, HorizontalAlignment.Stretch)
|
||||||
|
},
|
||||||
|
Orientation = Orientation.Vertical
|
||||||
|
};
|
||||||
|
if (Main.DebugColors)
|
||||||
|
BackgroundColor = Colors.Red;
|
||||||
|
Clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void SetApp(App app)
|
||||||
|
{
|
||||||
|
_app = app;
|
||||||
|
_appNameLabel.Text = app.Name;
|
||||||
|
_appNameLabel.Enabled = app.Status.Contains(Status.Installed) && app.Runnable;
|
||||||
|
_appDescriptionLabel.Text = app.Description;
|
||||||
|
_appControls.SetApp(app);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Clear()
|
||||||
|
{
|
||||||
|
_appNameLabel.Text = "Welcome to UpTool2";
|
||||||
|
_appNameLabel.Enabled = false;
|
||||||
|
_appDescriptionLabel.Text = "Select an app to get started";
|
||||||
|
_appControls.Clear();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
35
UpToolEto/UpToolEto/Controls/RepoItem.cs
Normal file
35
UpToolEto/UpToolEto/Controls/RepoItem.cs
Normal file
@ -0,0 +1,35 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
|
||||||
|
namespace UpToolEto.Controls
|
||||||
|
{
|
||||||
|
public class RepoItem : StackLayout
|
||||||
|
{
|
||||||
|
public RepoItem(Repo repo, int index, Action update, IList<Repo> repos)
|
||||||
|
{
|
||||||
|
TextBox name = new()
|
||||||
|
{
|
||||||
|
Text = repo.Name
|
||||||
|
};
|
||||||
|
name.TextChanged += (_, _) => repo.Name = name.Text;
|
||||||
|
TextBox link = new()
|
||||||
|
{
|
||||||
|
Text = repo.Url
|
||||||
|
};
|
||||||
|
link.TextChanged += (_, _) => repo.Url = link.Text;
|
||||||
|
Orientation = Orientation.Horizontal;
|
||||||
|
Items.Add(name);
|
||||||
|
Items.Add(new StackLayoutItem(link, HorizontalAlignment.Stretch, true));
|
||||||
|
Items.Add(new Button((_, _) =>
|
||||||
|
{
|
||||||
|
repos.RemoveAt(index);
|
||||||
|
update();
|
||||||
|
})
|
||||||
|
{
|
||||||
|
Text = "-"
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
71
UpToolEto/UpToolEto/Controls/UTMenuBar.cs
Normal file
71
UpToolEto/UpToolEto/Controls/UTMenuBar.cs
Normal file
@ -0,0 +1,71 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolEto.Forms;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
using UpToolLib.v2.TaskQueue;
|
||||||
|
|
||||||
|
namespace UpToolEto.Controls
|
||||||
|
{
|
||||||
|
public class UTMenuBar : MenuBar
|
||||||
|
{
|
||||||
|
public UTMenuBar(MainForm mainForm, RepoManagement repoManagement, TaskFactory factory, IList<AppTask> tasks, AppList appList, IExternalFunctionality platform)
|
||||||
|
{
|
||||||
|
Command reloadRepos = new() {MenuText = "Reload", ToolBarText = "Reload"};
|
||||||
|
reloadRepos.Executed += (_, _) =>
|
||||||
|
{
|
||||||
|
if (platform.YesNoDialog("This may take some time. Are you sure?", true))
|
||||||
|
{
|
||||||
|
repoManagement.FetchRepos();
|
||||||
|
repoManagement.GetReposFromDisk();
|
||||||
|
appList.Update();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
Command editSources = new() {MenuText = "Sources", ToolBarText = "Sources"};
|
||||||
|
editSources.Executed += (_, _) => new RepoForm(repoManagement).ShowModal();
|
||||||
|
|
||||||
|
Command addPackage = new() {MenuText = "Add Package", ToolBarText = "Add Package"};
|
||||||
|
addPackage.Executed += (_, _) =>
|
||||||
|
{
|
||||||
|
OpenFileDialog dialog = new() {MultiSelect = false, CheckFileExists = true, Filters = { new FileFilter("App package", ".zip")}};
|
||||||
|
if (dialog.ShowDialog(mainForm) == DialogResult.Ok)
|
||||||
|
{
|
||||||
|
if (!tasks.Any(s => s is UploadTask t && t.ZipFile == dialog.FileName))
|
||||||
|
{
|
||||||
|
StringDialog sd = new("Package name") {Text = "New package"};
|
||||||
|
sd.ShowModal();
|
||||||
|
tasks.Add(factory.CreateUpload(dialog.FileName, sd.Text));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
Command quitCommand = new() {MenuText = "Quit", Shortcut = Application.Instance.CommonModifier | Keys.Q};
|
||||||
|
quitCommand.Executed += (_, _) => Application.Instance.Quit();
|
||||||
|
|
||||||
|
Command aboutCommand = new() {MenuText = "About Eto..."};
|
||||||
|
aboutCommand.Executed += (_, _) => new AboutDialog().ShowDialog(mainForm);
|
||||||
|
|
||||||
|
Items.Add(new ButtonMenuItem
|
||||||
|
{
|
||||||
|
Text = "&File", Items =
|
||||||
|
{
|
||||||
|
reloadRepos,
|
||||||
|
editSources,
|
||||||
|
addPackage
|
||||||
|
}
|
||||||
|
});
|
||||||
|
// File submenu
|
||||||
|
// new ButtonMenuItem { Text = "&Edit", Items = { /* commands/items */ } },
|
||||||
|
// new ButtonMenuItem { Text = "&View", Items = { /* commands/items */ } },
|
||||||
|
/*ApplicationItems =
|
||||||
|
{
|
||||||
|
// application (OS X) or file menu (others)
|
||||||
|
new ButtonMenuItem {Text = "&Preferences..."},
|
||||||
|
},*/
|
||||||
|
QuitItem = quitCommand;
|
||||||
|
AboutItem = aboutCommand;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
79
UpToolEto/UpToolEto/Forms/DownloadDialog.cs
Normal file
79
UpToolEto/UpToolEto/Forms/DownloadDialog.cs
Normal file
@ -0,0 +1,79 @@
|
|||||||
|
using System;
|
||||||
|
using System.Net;
|
||||||
|
using System.Threading;
|
||||||
|
using Eto.Drawing;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
|
||||||
|
namespace UpToolEto.Forms
|
||||||
|
{
|
||||||
|
public class DownloadDialog : Dialog
|
||||||
|
{
|
||||||
|
private readonly Uri _url;
|
||||||
|
private readonly Application _application;
|
||||||
|
private readonly IExternalFunctionality _platform;
|
||||||
|
public State CurrentState = State.NotStarted;
|
||||||
|
public byte[] Download = new byte[0];
|
||||||
|
private readonly ProgressBar _bar;
|
||||||
|
public DownloadDialog(Uri url, Application application, IExternalFunctionality platform)
|
||||||
|
{
|
||||||
|
_url = url;
|
||||||
|
_application = application;
|
||||||
|
_platform = platform;
|
||||||
|
Title = "Downloader";
|
||||||
|
Resizable = false;
|
||||||
|
Maximizable = false;
|
||||||
|
Minimizable = false;
|
||||||
|
WindowStyle = WindowStyle.Utility;
|
||||||
|
_bar = new();
|
||||||
|
_bar.MaxValue = 100;
|
||||||
|
Content = new StackLayout
|
||||||
|
{
|
||||||
|
Padding = 10,
|
||||||
|
Items =
|
||||||
|
{
|
||||||
|
"Downloading " + url,
|
||||||
|
new StackLayoutItem(_bar, HorizontalAlignment.Stretch, true)
|
||||||
|
}
|
||||||
|
};
|
||||||
|
Size = new Size(700, 400);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void StartDownload()
|
||||||
|
{
|
||||||
|
CurrentState = State.Downloading;
|
||||||
|
new Thread(() =>
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
WebClient client = new();
|
||||||
|
client.DownloadProgressChanged += (_, args) => _application.Invoke(() =>
|
||||||
|
{
|
||||||
|
_bar.Value = args.ProgressPercentage;
|
||||||
|
_application.RunIteration();
|
||||||
|
});
|
||||||
|
client.DownloadDataCompleted += (_, args) =>
|
||||||
|
{
|
||||||
|
CurrentState = State.Success;
|
||||||
|
Download = args.Result;
|
||||||
|
_application.Invoke(Close);
|
||||||
|
};
|
||||||
|
client.DownloadDataAsync(_url, client);
|
||||||
|
}
|
||||||
|
catch
|
||||||
|
{
|
||||||
|
CurrentState = State.Failed;
|
||||||
|
_application.Invoke(Close);
|
||||||
|
}
|
||||||
|
}).Start();
|
||||||
|
}
|
||||||
|
|
||||||
|
public enum State
|
||||||
|
{
|
||||||
|
NotStarted,
|
||||||
|
Downloading,
|
||||||
|
Failed,
|
||||||
|
Success
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
51
UpToolEto/UpToolEto/Forms/InitScreen.cs
Normal file
51
UpToolEto/UpToolEto/Forms/InitScreen.cs
Normal file
@ -0,0 +1,51 @@
|
|||||||
|
using System;
|
||||||
|
using Eto.Drawing;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
|
||||||
|
namespace UpToolEto.Forms
|
||||||
|
{
|
||||||
|
public class InitScreen : Form
|
||||||
|
{
|
||||||
|
private readonly Application _application;
|
||||||
|
private readonly IExternalFunctionality _platform;
|
||||||
|
private readonly Label _lab;
|
||||||
|
public InitScreen(Application application, IExternalFunctionality platform)
|
||||||
|
{
|
||||||
|
_application = application;
|
||||||
|
_platform = platform;
|
||||||
|
Title = "UpTool2 Init";
|
||||||
|
Resizable = false;
|
||||||
|
Maximizable = false;
|
||||||
|
Minimizable = false;
|
||||||
|
WindowStyle = WindowStyle.None;
|
||||||
|
_lab = new Label();
|
||||||
|
Label header = new();
|
||||||
|
header.Font = new Font(header.Font.Family, header.Font.Size * 2);
|
||||||
|
header.Text = "UpTool2";
|
||||||
|
Content = new StackLayout
|
||||||
|
{
|
||||||
|
Padding = 10,
|
||||||
|
Items =
|
||||||
|
{
|
||||||
|
new StackLayoutItem(header, HorizontalAlignment.Center),
|
||||||
|
new StackLayoutItem(_lab, HorizontalAlignment.Center)
|
||||||
|
},
|
||||||
|
VerticalContentAlignment = VerticalAlignment.Center
|
||||||
|
};
|
||||||
|
Shown += (_, _) => Size = new Size(700, 400);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void SetText(string text)
|
||||||
|
{
|
||||||
|
_application.Invoke(() =>
|
||||||
|
{
|
||||||
|
_platform.Log(text);
|
||||||
|
_lab.Text = text;
|
||||||
|
_application.RunIteration();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
public override void Close() => _application.Invoke(() => base.Close());
|
||||||
|
}
|
||||||
|
}
|
37
UpToolEto/UpToolEto/Forms/MainForm.cs
Normal file
37
UpToolEto/UpToolEto/Forms/MainForm.cs
Normal file
@ -0,0 +1,37 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using Eto.Drawing;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolEto.Controls;
|
||||||
|
using UpToolLib;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v2.TaskQueue;
|
||||||
|
|
||||||
|
namespace UpToolEto.Forms
|
||||||
|
{
|
||||||
|
public partial class MainForm : Form
|
||||||
|
{
|
||||||
|
private readonly AppPanel _appPanel;
|
||||||
|
private readonly IList<AppTask> _tasks;
|
||||||
|
public MainForm(InitScreen init, UpToolLibMain lib, IExternalFunctionality platform, bool online)
|
||||||
|
{
|
||||||
|
_tasks = new List<AppTask>();
|
||||||
|
Title = "UpTool2";
|
||||||
|
MinimumSize = new Size(600, 100);
|
||||||
|
AppList appList = new(lib.V1.AppExtras, (_, app) => _appPanel.SetApp(app), online, lib.V2.TaskFactory, _tasks);
|
||||||
|
_appPanel = new AppPanel(lib.V2.TaskFactory, lib.V1.AppExtras, _tasks, platform, appList.Update);
|
||||||
|
|
||||||
|
Content = new StackLayout
|
||||||
|
{
|
||||||
|
Padding = 10,
|
||||||
|
Items =
|
||||||
|
{
|
||||||
|
new StackLayoutItem(appList, VerticalAlignment.Stretch),
|
||||||
|
new StackLayoutItem(_appPanel, VerticalAlignment.Stretch, true)
|
||||||
|
},
|
||||||
|
Orientation = Orientation.Horizontal
|
||||||
|
};
|
||||||
|
Menu = new UTMenuBar(this, lib.V2.RepoManagement, lib.V2.TaskFactory, _tasks, appList, platform);
|
||||||
|
Shown += (_, _) => init.Close();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
46
UpToolEto/UpToolEto/Forms/QueueOverview.cs
Normal file
46
UpToolEto/UpToolEto/Forms/QueueOverview.cs
Normal file
@ -0,0 +1,46 @@
|
|||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolLib.v2.TaskQueue;
|
||||||
|
|
||||||
|
namespace UpToolEto.Forms
|
||||||
|
{
|
||||||
|
public class QueueOverview : Dialog
|
||||||
|
{
|
||||||
|
private readonly IList<AppTask> _tasks;
|
||||||
|
public bool Cancelled;
|
||||||
|
CheckBoxList cbl;
|
||||||
|
public List<AppTask> TasksResulting => cbl.SelectedValues.Select(s => (AppTask) s).ToList();
|
||||||
|
|
||||||
|
public QueueOverview(IList<AppTask> tasks)
|
||||||
|
{
|
||||||
|
_tasks = tasks;
|
||||||
|
StackLayout layout = new();
|
||||||
|
layout.Items.Add(new StackLayoutItem(new StackLayout()
|
||||||
|
{
|
||||||
|
Items =
|
||||||
|
{
|
||||||
|
new StackLayoutItem(new Button((_, _) =>
|
||||||
|
{
|
||||||
|
Cancelled = true;
|
||||||
|
Close();
|
||||||
|
})
|
||||||
|
{
|
||||||
|
Text = "Cancel"
|
||||||
|
}, HorizontalAlignment.Stretch),
|
||||||
|
new StackLayoutItem(new Button((_, _) =>
|
||||||
|
{
|
||||||
|
Close();
|
||||||
|
})
|
||||||
|
{
|
||||||
|
Text = "OK"
|
||||||
|
}, HorizontalAlignment.Stretch)
|
||||||
|
},
|
||||||
|
Orientation = Orientation.Horizontal
|
||||||
|
}, HorizontalAlignment.Stretch));
|
||||||
|
cbl = new CheckBoxList {DataStore = tasks, SelectedValues = tasks};
|
||||||
|
layout.Items.Add(cbl);
|
||||||
|
Content = layout;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
54
UpToolEto/UpToolEto/Forms/RepoForm.cs
Normal file
54
UpToolEto/UpToolEto/Forms/RepoForm.cs
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolEto.Controls;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
|
||||||
|
namespace UpToolEto.Forms
|
||||||
|
{
|
||||||
|
public class RepoForm : Dialog
|
||||||
|
{
|
||||||
|
private readonly RepoManagement _management;
|
||||||
|
private List<Repo> _repos = new();
|
||||||
|
private StackLayout _layout;
|
||||||
|
public RepoForm(RepoManagement management)
|
||||||
|
{
|
||||||
|
_management = management;
|
||||||
|
_repos.AddRange(management.GetRepos());
|
||||||
|
Title = "Sources";
|
||||||
|
_layout = new StackLayout();
|
||||||
|
Content = _layout;
|
||||||
|
Update();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void Update()
|
||||||
|
{
|
||||||
|
_layout.Items.Clear();
|
||||||
|
_layout.Items.Add(new StackLayoutItem(new Button((_, _) =>
|
||||||
|
{
|
||||||
|
_repos.Add(new Repo
|
||||||
|
{
|
||||||
|
Name = "New repo",
|
||||||
|
Url = "https://example.com/repo.xml"
|
||||||
|
});
|
||||||
|
Update();
|
||||||
|
})
|
||||||
|
{
|
||||||
|
Text = "Add",
|
||||||
|
}, HorizontalAlignment.Stretch));
|
||||||
|
StackLayout reposLayout = new();
|
||||||
|
for (int i = 0; i < _repos.Count; i++)
|
||||||
|
reposLayout.Items.Add(new StackLayoutItem(new RepoItem(_repos[i], i, Update, _repos), HorizontalAlignment.Stretch));
|
||||||
|
_layout.Items.Add(new StackLayoutItem(new Scrollable{Content = reposLayout}, HorizontalAlignment.Stretch, true));
|
||||||
|
_layout.Items.Add(new StackLayoutItem(new Button((_, _) =>
|
||||||
|
{
|
||||||
|
_management.Save(_repos);
|
||||||
|
Close();
|
||||||
|
})
|
||||||
|
{
|
||||||
|
Text = "Save"
|
||||||
|
}, HorizontalAlignment.Stretch));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
20
UpToolEto/UpToolEto/Forms/StringDialog.cs
Normal file
20
UpToolEto/UpToolEto/Forms/StringDialog.cs
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
using Eto.Forms;
|
||||||
|
|
||||||
|
namespace UpToolEto.Forms
|
||||||
|
{
|
||||||
|
public class StringDialog : Dialog
|
||||||
|
{
|
||||||
|
private readonly TextBox _tb;
|
||||||
|
public string Text
|
||||||
|
{
|
||||||
|
get => _tb.Text;
|
||||||
|
set => _tb.Text = value;
|
||||||
|
}
|
||||||
|
public StringDialog(string title)
|
||||||
|
{
|
||||||
|
_tb = new TextBox();
|
||||||
|
Content = _tb;
|
||||||
|
Title = title;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
164
UpToolEto/UpToolEto/Main.cs
Normal file
164
UpToolEto/UpToolEto/Main.cs
Normal file
@ -0,0 +1,164 @@
|
|||||||
|
using System;
|
||||||
|
using System.Diagnostics;
|
||||||
|
using System.IO;
|
||||||
|
using System.IO.Compression;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Reflection;
|
||||||
|
using System.Security.Cryptography;
|
||||||
|
using System.Threading;
|
||||||
|
using System.Xml;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolEto.Forms;
|
||||||
|
using UpToolLib;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
|
||||||
|
namespace UpToolEto
|
||||||
|
{
|
||||||
|
public class Main
|
||||||
|
{
|
||||||
|
private readonly IExternalFunctionality _platform;
|
||||||
|
private readonly Application _application;
|
||||||
|
private readonly Action _activityExistsException;
|
||||||
|
private readonly InitScreen _init;
|
||||||
|
private readonly bool _skipFetch;
|
||||||
|
public static bool DebugColors { get; private set; }
|
||||||
|
|
||||||
|
public Main(Application application, Action activityExistsException, string[] args)
|
||||||
|
{
|
||||||
|
_skipFetch = args.Contains("--skip-fetch");
|
||||||
|
DebugColors = args.Contains("--debug-colors");
|
||||||
|
_platform = new UTLibFunctions(application);
|
||||||
|
_application = application;
|
||||||
|
_activityExistsException = activityExistsException;
|
||||||
|
_init = new(application, _platform);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Entry()
|
||||||
|
{
|
||||||
|
new Thread(InitThread).Start();
|
||||||
|
_application.Run(_init);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void InitThread()
|
||||||
|
{
|
||||||
|
UpToolLibMain lib = null;
|
||||||
|
try
|
||||||
|
{
|
||||||
|
lib = new UpToolLibMain(_platform);
|
||||||
|
_init.SetText("Initializing paths");
|
||||||
|
if (!Directory.Exists(lib.V1.PathTool.Dir))
|
||||||
|
Directory.CreateDirectory(lib.V1.PathTool.Dir);
|
||||||
|
FixXml(lib.V1.XmlTool, lib.V1.PathTool);
|
||||||
|
_init.SetText("Performing checks");
|
||||||
|
bool online = false;
|
||||||
|
UpdateCheck updateCheck = null;
|
||||||
|
try
|
||||||
|
{
|
||||||
|
updateCheck = lib.V2.UpdateChecker.Check();
|
||||||
|
online = true;
|
||||||
|
}
|
||||||
|
catch
|
||||||
|
{
|
||||||
|
_platform.Log("Could not perform update check, starting offline");
|
||||||
|
}
|
||||||
|
if (online && UpdateCheck(updateCheck, lib.V1.PathTool, _init))
|
||||||
|
_platform.Log("Quitting");
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (!Directory.Exists(lib.V1.PathTool.GetRelative("Apps")))
|
||||||
|
Directory.CreateDirectory(lib.V1.PathTool.GetRelative("Apps"));
|
||||||
|
if (!_skipFetch && online)
|
||||||
|
{
|
||||||
|
_init.SetText("Fetching repos");
|
||||||
|
lib.V2.RepoManagement.FetchRepos();
|
||||||
|
}
|
||||||
|
lib.V2.RepoManagement.GetReposFromDisk();
|
||||||
|
_init.SetText("Opening");
|
||||||
|
_application.Invoke(() => _application.Run(new MainForm(_init, lib, _platform, online)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (MutexLockLockedException)
|
||||||
|
{
|
||||||
|
_application.Invoke(() =>
|
||||||
|
{
|
||||||
|
_init.Close();
|
||||||
|
_platform.OkDialog("Mutex property of other process, quitting");
|
||||||
|
_activityExistsException();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
lib?.Dispose();
|
||||||
|
_platform.Log(e.ToString());
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
lib?.Dispose();
|
||||||
|
_application.Invoke(() => _application.Quit());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void FixXml(XmlTool xmlTool, PathTool pathTool, bool throwOnError = false)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
xmlTool.FixXml();
|
||||||
|
}
|
||||||
|
catch (XmlException)
|
||||||
|
{
|
||||||
|
if (throwOnError) throw;
|
||||||
|
_platform.OkDialog("Something went wrong while trying to parse XML. Retrying...");
|
||||||
|
File.Delete(pathTool.InfoXml);
|
||||||
|
FixXml(xmlTool, pathTool);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private bool UpdateCheck(UpdateCheck updateCheck, PathTool pathTool, InitScreen init)
|
||||||
|
{
|
||||||
|
init.SetText("Comparing online version");
|
||||||
|
if (Assembly.GetExecutingAssembly().GetName().Version >= updateCheck.OnlineVersion) return false;
|
||||||
|
if (PlatformCheck.IsWindows)
|
||||||
|
{
|
||||||
|
init.SetText("Downloading latest");
|
||||||
|
(bool success, byte[] dl) = _platform.Download(updateCheck.Installer);
|
||||||
|
if (!success)
|
||||||
|
throw new Exception("Failed to update");
|
||||||
|
init.SetText("Verifying");
|
||||||
|
using (SHA256CryptoServiceProvider sha256 = new())
|
||||||
|
{
|
||||||
|
string pkgHash = BitConverter.ToString(sha256.ComputeHash(dl)).Replace("-", string.Empty).ToUpper();
|
||||||
|
if (pkgHash != updateCheck.InstallerHash)
|
||||||
|
throw new Exception(
|
||||||
|
$"The hash is not equal to the one stored in the repo:\r\nPackage: {pkgHash}\r\nOnline: {updateCheck.InstallerHash}");
|
||||||
|
}
|
||||||
|
init.SetText("Installing");
|
||||||
|
if (Directory.Exists(pathTool.GetRelative("Install", "tmp")))
|
||||||
|
Directory.Delete(pathTool.GetRelative("Install", "tmp"), true);
|
||||||
|
Directory.CreateDirectory(pathTool.GetRelative("Install", "tmp"));
|
||||||
|
using (MemoryStream ms = new(dl))
|
||||||
|
{
|
||||||
|
using ZipArchive ar = new(ms);
|
||||||
|
ar.ExtractToDirectory(pathTool.GetRelative("Install", "tmp"), true);
|
||||||
|
}
|
||||||
|
init.Close();
|
||||||
|
Process.Start(new ProcessStartInfo
|
||||||
|
{
|
||||||
|
FileName = pathTool.GetRelative("Install", "tmp", "Installer.exe"),
|
||||||
|
Arguments = "i -p",
|
||||||
|
CreateNoWindow = true,
|
||||||
|
WindowStyle = ProcessWindowStyle.Hidden,
|
||||||
|
WorkingDirectory = pathTool.GetRelative("Install")
|
||||||
|
});
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
_platform.OkDialog("A new version is available. Please install it");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
59
UpToolEto/UpToolEto/UTLibFunctions.cs
Normal file
59
UpToolEto/UpToolEto/UTLibFunctions.cs
Normal file
@ -0,0 +1,59 @@
|
|||||||
|
using System;
|
||||||
|
using System.IO;
|
||||||
|
using System.Net;
|
||||||
|
using System.Threading;
|
||||||
|
using Eto.Drawing;
|
||||||
|
using Eto.Forms;
|
||||||
|
using UpToolEto.Forms;
|
||||||
|
using UpToolLib;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
|
||||||
|
namespace UpToolEto
|
||||||
|
{
|
||||||
|
public class UTLibFunctions : IExternalFunctionality
|
||||||
|
{
|
||||||
|
private readonly Application _application;
|
||||||
|
private const int ImgSize = 32;
|
||||||
|
public Tuple<bool, byte[]> Download(Uri link)
|
||||||
|
{
|
||||||
|
DownloadDialog dlg = new(link, _application, this);
|
||||||
|
_application.AsyncInvoke(() => dlg.ShowModal());
|
||||||
|
dlg.StartDownload();
|
||||||
|
Log("Downloading " + link);
|
||||||
|
while (dlg.CurrentState == DownloadDialog.State.Downloading) Thread.Sleep(20);
|
||||||
|
Log("Download complete");
|
||||||
|
return new Tuple<bool, byte[]>(dlg.CurrentState == DownloadDialog.State.Success, dlg.Download);
|
||||||
|
}
|
||||||
|
|
||||||
|
public string FetchImageB64(Uri link)
|
||||||
|
{
|
||||||
|
using WebClient client = new();
|
||||||
|
using Stream s = client.OpenRead(link);
|
||||||
|
using Bitmap source = new(s);
|
||||||
|
using Icon bmp = source.WithSize(ImgSize, ImgSize);
|
||||||
|
using Bitmap bitmapResized = new(bmp);
|
||||||
|
using MemoryStream ms = new();
|
||||||
|
bitmapResized.Save(ms, ImageFormat.Png);
|
||||||
|
return Convert.ToBase64String(ms.ToArray());
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool YesNoDialog(string text, bool defaultVal) =>
|
||||||
|
_application.Invoke(() => MessageBox.Show(text, MessageBoxButtons.YesNo,
|
||||||
|
defaultButton: defaultVal ? MessageBoxDefaultButton.Yes : MessageBoxDefaultButton.No)) ==
|
||||||
|
DialogResult.Yes;
|
||||||
|
|
||||||
|
public void OkDialog(string text) => _application.Invoke(() => MessageBox.Show(text));
|
||||||
|
|
||||||
|
public object GetDefaultIcon() => Bitmap.FromResource("UpToolLib.C_64.ico", typeof(UpToolLibMain)).WithSize(ImgSize, ImgSize);
|
||||||
|
|
||||||
|
public object ImageFromB64(string b64) => new Bitmap(Convert.FromBase64String(b64)).WithSize(ImgSize, ImgSize);
|
||||||
|
|
||||||
|
public void Log(string text)
|
||||||
|
{
|
||||||
|
Console.WriteLine(text);
|
||||||
|
//TODO implement visual logging
|
||||||
|
}
|
||||||
|
|
||||||
|
public UTLibFunctions(Application application) => _application = application;
|
||||||
|
}
|
||||||
|
}
|
15
UpToolEto/UpToolEto/UpToolEto.csproj
Normal file
15
UpToolEto/UpToolEto/UpToolEto.csproj
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<TargetFramework>net5.0</TargetFramework>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<PackageReference Include="Eto.Forms" Version="2.5.10" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<ProjectReference Include="..\..\UpToolLib\UpToolLib.csproj" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
</Project>
|
BIN
UpToolLib/C_64.ico
Normal file
BIN
UpToolLib/C_64.ico
Normal file
Binary file not shown.
After Width: | Height: | Size: 17 KiB |
15
UpToolLib/DataStructures/IExternalFunctionality.cs
Normal file
15
UpToolLib/DataStructures/IExternalFunctionality.cs
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
using System;
|
||||||
|
|
||||||
|
namespace UpToolLib.DataStructures
|
||||||
|
{
|
||||||
|
public interface IExternalFunctionality
|
||||||
|
{
|
||||||
|
public Tuple<bool, byte[]> Download(Uri link);
|
||||||
|
public string FetchImageB64(Uri link);
|
||||||
|
public bool YesNoDialog(string text, bool defaultVal);
|
||||||
|
public void OkDialog(string text);
|
||||||
|
public object GetDefaultIcon();
|
||||||
|
public object ImageFromB64(string b64);
|
||||||
|
public void Log(string text);
|
||||||
|
}
|
||||||
|
}
|
8
UpToolLib/DataStructures/Repo.cs
Normal file
8
UpToolLib/DataStructures/Repo.cs
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
namespace UpToolLib.DataStructures
|
||||||
|
{
|
||||||
|
public class Repo
|
||||||
|
{
|
||||||
|
public string Name { get; set; }
|
||||||
|
public string Url { get; set; }
|
||||||
|
}
|
||||||
|
}
|
19
UpToolLib/DataStructures/Status.cs
Normal file
19
UpToolLib/DataStructures/Status.cs
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
using System;
|
||||||
|
|
||||||
|
namespace UpToolLib.DataStructures
|
||||||
|
{
|
||||||
|
[Flags]
|
||||||
|
public enum Status
|
||||||
|
{
|
||||||
|
NotInstalled = 1,
|
||||||
|
Updatable = 2,
|
||||||
|
Installed = 4,
|
||||||
|
Local = 8,
|
||||||
|
All = 0
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class StatusExtensions
|
||||||
|
{
|
||||||
|
public static bool Contains(this Status status, Status other) => (status & other) == other;
|
||||||
|
}
|
||||||
|
}
|
8
UpToolLib/MutexLockLockedException.cs
Normal file
8
UpToolLib/MutexLockLockedException.cs
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
using System;
|
||||||
|
|
||||||
|
namespace UpToolLib
|
||||||
|
{
|
||||||
|
public class MutexLockLockedException : Exception
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
16
UpToolLib/UpToolLib.csproj
Normal file
16
UpToolLib/UpToolLib.csproj
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<TargetFramework>net5.0</TargetFramework>
|
||||||
|
<Deterministic>false</Deterministic>
|
||||||
|
<AssemblyVersion>1.0.*</AssemblyVersion>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<Content Remove="C_64.ico" />
|
||||||
|
</ItemGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<EmbeddedResource Include="C_64.ico" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
</Project>
|
38
UpToolLib/UpToolLibMain.cs
Normal file
38
UpToolLib/UpToolLibMain.cs
Normal file
@ -0,0 +1,38 @@
|
|||||||
|
using System;
|
||||||
|
using System.Threading;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
|
||||||
|
namespace UpToolLib
|
||||||
|
{
|
||||||
|
public class UpToolLibMain : IDisposable
|
||||||
|
{
|
||||||
|
private static Mutex _mutex;
|
||||||
|
public UpToolLibMain(IExternalFunctionality platform)
|
||||||
|
{
|
||||||
|
V1 = new UpToolLibV1(platform);
|
||||||
|
V2 = new UpToolLibV2(platform, V1.Installer, V1.AppExtras, V1.PathTool, V1.XmlTool, V1.Apps);
|
||||||
|
_mutex = new Mutex(false,
|
||||||
|
"Global\\{c0c1e002-9e13-4e8f-a035-dbdc5128e00e}",
|
||||||
|
out bool _);
|
||||||
|
try
|
||||||
|
{
|
||||||
|
if (_mutex.WaitOne(5000, false))
|
||||||
|
return;
|
||||||
|
throw new MutexLockLockedException();
|
||||||
|
}
|
||||||
|
catch (AbandonedMutexException)
|
||||||
|
{
|
||||||
|
#if DEBUG
|
||||||
|
_platform.Log("Mutex abandoned");
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public readonly UpToolLibV1 V1;
|
||||||
|
public readonly UpToolLibV2 V2;
|
||||||
|
public void Dispose() => _mutex.ReleaseMutex();
|
||||||
|
~UpToolLibMain() => Dispose();
|
||||||
|
}
|
||||||
|
}
|
23
UpToolLib/v1/PlatformCheck.cs
Normal file
23
UpToolLib/v1/PlatformCheck.cs
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
using System;
|
||||||
|
using System.Linq;
|
||||||
|
|
||||||
|
namespace UpToolLib.v1
|
||||||
|
{
|
||||||
|
public static class PlatformCheck
|
||||||
|
{
|
||||||
|
public static bool IsWindows => new[]
|
||||||
|
{
|
||||||
|
PlatformID.Xbox, PlatformID.Win32S, PlatformID.Win32Windows, PlatformID.Win32NT,
|
||||||
|
PlatformID.WinCE
|
||||||
|
}
|
||||||
|
.Contains(Environment.OSVersion.Platform);
|
||||||
|
|
||||||
|
public static bool IsPosix => !IsWindows;
|
||||||
|
|
||||||
|
public const string Windows = "WINDOWS";
|
||||||
|
public const string Posix = "POSIX";
|
||||||
|
public static string CurrentPlatform =>
|
||||||
|
IsWindows ? Windows :
|
||||||
|
IsPosix ? Posix : throw new Exception("Unexpected PlatformCheck");
|
||||||
|
}
|
||||||
|
}
|
119
UpToolLib/v1/Tool/AppExtras.cs
Normal file
119
UpToolLib/v1/Tool/AppExtras.cs
Normal file
@ -0,0 +1,119 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Diagnostics;
|
||||||
|
using System.IO;
|
||||||
|
using System.IO.Compression;
|
||||||
|
using System.Linq;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
|
||||||
|
namespace UpToolLib.v1.Tool
|
||||||
|
{
|
||||||
|
public class AppExtras
|
||||||
|
{
|
||||||
|
private readonly AppInstall _appInstall;
|
||||||
|
private readonly PathTool _pathTool;
|
||||||
|
private readonly IDictionary<Guid, App> _apps;
|
||||||
|
|
||||||
|
internal AppExtras(AppInstall appInstall, PathTool pathTool, IDictionary<Guid, App> apps)
|
||||||
|
{
|
||||||
|
_appInstall = appInstall;
|
||||||
|
_pathTool = pathTool;
|
||||||
|
_apps = apps;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Process RunApp(App app) => RunApp(app, app.MainFile, "");
|
||||||
|
public Process RunApp(App app, string arguments) => RunApp(app, app.MainFile, arguments);
|
||||||
|
public Process RunApp(App app, string file, string arguments) =>
|
||||||
|
Process.Start(
|
||||||
|
new ProcessStartInfo
|
||||||
|
{
|
||||||
|
FileName = Path.Combine(app.DataPath, file),
|
||||||
|
Arguments = arguments,
|
||||||
|
WorkingDirectory = app.DataPath
|
||||||
|
});
|
||||||
|
|
||||||
|
public void Update(App app, bool overwrite)
|
||||||
|
{
|
||||||
|
Remove(app, overwrite);
|
||||||
|
_appInstall.Install(app, overwrite);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Remove(App app, bool deleteAll)
|
||||||
|
{
|
||||||
|
string tmp = _pathTool.TempPath;
|
||||||
|
if (Directory.Exists(tmp))
|
||||||
|
Directory.Delete(tmp, true);
|
||||||
|
Directory.CreateDirectory(tmp);
|
||||||
|
if (File.Exists(Path.Combine(app.AppPath, "package.zip")))
|
||||||
|
{
|
||||||
|
ZipFile.ExtractToDirectory(Path.Combine(app.AppPath, "package.zip"), tmp);
|
||||||
|
/*Process.Start(new ProcessStartInfo
|
||||||
|
{
|
||||||
|
FileName = "cmd.exe",
|
||||||
|
Arguments = $"/C \"{Path.Combine(tmp, "Remove.bat")}\"",
|
||||||
|
WorkingDirectory = Path.Combine(app.AppPath, "app"),
|
||||||
|
CreateNoWindow = true,
|
||||||
|
WindowStyle = ProcessWindowStyle.Hidden
|
||||||
|
}).WaitForExit();*/
|
||||||
|
int key = PlatformCheck.IsWindows ? 0 :
|
||||||
|
File.Exists(Path.Combine(tmp, "Remove.sh")) ? 1 : 2;
|
||||||
|
ProcessStartInfo prc = new()
|
||||||
|
{
|
||||||
|
FileName = key switch
|
||||||
|
{
|
||||||
|
0 => "cmd.exe",
|
||||||
|
1 => "bash",
|
||||||
|
2 => "wine",
|
||||||
|
_ => throw new Exception()
|
||||||
|
},
|
||||||
|
WorkingDirectory = Path.Combine(app.AppPath, "app"),
|
||||||
|
CreateNoWindow = true,
|
||||||
|
WindowStyle = ProcessWindowStyle.Hidden
|
||||||
|
};
|
||||||
|
foreach (string s in key switch
|
||||||
|
{
|
||||||
|
0 => new[] {"/C", $"{Path.Combine(tmp, "Remove.bat")}"},
|
||||||
|
1 => new[] {Path.Combine(tmp, "Remove.sh")},
|
||||||
|
2 => new[] {"cmd", "/C", $"{Path.Combine(tmp, "Remove.bat")}"},
|
||||||
|
_ => throw new Exception()
|
||||||
|
})
|
||||||
|
prc.ArgumentList.Add(s);
|
||||||
|
Process.Start(prc)?.WaitForExit();
|
||||||
|
if (!deleteAll) CheckDirecory(Path.Combine(tmp, "Data"), app.DataPath);
|
||||||
|
Directory.Delete(tmp, true);
|
||||||
|
}
|
||||||
|
if (File.Exists(app.InfoPath))
|
||||||
|
File.Delete(app.InfoPath);
|
||||||
|
if (File.Exists(Path.Combine(app.AppPath, "package.zip")))
|
||||||
|
File.Delete(Path.Combine(app.AppPath, "package.zip"));
|
||||||
|
if (deleteAll || Directory.Exists(app.DataPath) &&
|
||||||
|
Directory.GetFiles(app.DataPath).Length + Directory.GetDirectories(app.DataPath).Length ==
|
||||||
|
0)
|
||||||
|
Directory.Delete(app.AppPath, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void CheckDirecory(string tmp, string app)
|
||||||
|
{
|
||||||
|
foreach (string file in Directory.GetFiles(tmp))
|
||||||
|
{
|
||||||
|
string tmp1 = Path.Combine(app, Path.GetFileName(file));
|
||||||
|
if (File.Exists(tmp1))
|
||||||
|
File.Delete(tmp1);
|
||||||
|
}
|
||||||
|
foreach (string directory in Directory.GetDirectories(tmp))
|
||||||
|
CheckDirecory(directory, Path.Combine(app, Path.GetFileName(directory)));
|
||||||
|
if (Directory.Exists(app) && Directory.GetFiles(app).Length + Directory.GetDirectories(app).Length == 0)
|
||||||
|
Directory.Delete(app);
|
||||||
|
}
|
||||||
|
|
||||||
|
public App[] FindApps(string identifier)
|
||||||
|
{
|
||||||
|
if (string.IsNullOrWhiteSpace(identifier))
|
||||||
|
return _apps.Values.ToArray();
|
||||||
|
IEnumerable<KeyValuePair<Guid, App>> tmp1 = _apps.Where(s => s.Key.ToString().StartsWith(identifier));
|
||||||
|
tmp1 = tmp1.Concat(_apps.Where(s => s.Value.Name.Contains(identifier)));
|
||||||
|
tmp1 = tmp1.Concat(_apps.Where(s => s.Value.Description.Contains(identifier)));
|
||||||
|
return tmp1.Select(s => s.Value).ToArray();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
201
UpToolLib/v1/Tool/AppInstall.cs
Normal file
201
UpToolLib/v1/Tool/AppInstall.cs
Normal file
@ -0,0 +1,201 @@
|
|||||||
|
using System;
|
||||||
|
using System.Diagnostics;
|
||||||
|
using System.IO;
|
||||||
|
using System.IO.Compression;
|
||||||
|
using System.Security.Cryptography;
|
||||||
|
using System.Xml.Linq;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
|
||||||
|
namespace UpToolLib.v1.Tool
|
||||||
|
{
|
||||||
|
public class AppInstall
|
||||||
|
{
|
||||||
|
private readonly IExternalFunctionality _platform;
|
||||||
|
private readonly PathTool _pathTool;
|
||||||
|
|
||||||
|
internal AppInstall(IExternalFunctionality platform, PathTool pathTool)
|
||||||
|
{
|
||||||
|
_platform = platform;
|
||||||
|
_pathTool = pathTool;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Install an application
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="appI">The app to install</param>
|
||||||
|
/// <param name="force">Set to true to overwrite all old data</param>
|
||||||
|
public void Install(App appI, bool force)
|
||||||
|
{
|
||||||
|
string app = "";
|
||||||
|
string tmp = "";
|
||||||
|
#if !DEBUG
|
||||||
|
try
|
||||||
|
{
|
||||||
|
#endif
|
||||||
|
app = appI.AppPath;
|
||||||
|
tmp = _pathTool.TempPath;
|
||||||
|
if (Directory.Exists(tmp))
|
||||||
|
Directory.Delete(tmp, true);
|
||||||
|
Directory.CreateDirectory(tmp);
|
||||||
|
if (force)
|
||||||
|
{
|
||||||
|
if (Directory.Exists(app))
|
||||||
|
Directory.Delete(app, true);
|
||||||
|
Directory.CreateDirectory(app);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (!Directory.Exists(app))
|
||||||
|
Directory.CreateDirectory(app);
|
||||||
|
}
|
||||||
|
(bool dlSuccess, byte[] dlData) = _platform.Download(new Uri(appI.File));
|
||||||
|
if (!dlSuccess)
|
||||||
|
throw new Exception("Download failed");
|
||||||
|
using (SHA256CryptoServiceProvider sha256 = new())
|
||||||
|
{
|
||||||
|
string pkgHash = BitConverter.ToString(sha256.ComputeHash(dlData)).Replace("-", string.Empty)
|
||||||
|
.ToUpper();
|
||||||
|
if (pkgHash != appI.Hash.ToUpper())
|
||||||
|
throw new Exception($@"The hash is not equal to the one stored in the repo:
|
||||||
|
Package: {pkgHash}
|
||||||
|
Online: {appI.Hash.ToUpper()}");
|
||||||
|
}
|
||||||
|
File.WriteAllBytes(Path.Combine(app, "package.zip"), dlData);
|
||||||
|
CompleteInstall(appI, force);
|
||||||
|
#if !DEBUG
|
||||||
|
}
|
||||||
|
catch
|
||||||
|
{
|
||||||
|
if (Directory.Exists(app))
|
||||||
|
Directory.Delete(app, true);
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
#endif
|
||||||
|
if (tmp != "" && Directory.Exists(tmp))
|
||||||
|
Directory.Delete(tmp, true);
|
||||||
|
#if !DEBUG
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
public void InstallZip(string zipPath, App meta, bool force)
|
||||||
|
{
|
||||||
|
string app = "";
|
||||||
|
string tmp = "";
|
||||||
|
try
|
||||||
|
{
|
||||||
|
app = meta.AppPath;
|
||||||
|
Directory.CreateDirectory(app);
|
||||||
|
tmp = _pathTool.TempPath;
|
||||||
|
if (Directory.Exists(tmp))
|
||||||
|
Directory.Delete(tmp, true);
|
||||||
|
Directory.CreateDirectory(tmp);
|
||||||
|
File.Copy(zipPath, Path.Combine(app, "package.zip"));
|
||||||
|
CompleteInstall(meta, force);
|
||||||
|
}
|
||||||
|
catch
|
||||||
|
{
|
||||||
|
if (Directory.Exists(app))
|
||||||
|
Directory.Delete(app, true);
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
finally
|
||||||
|
{
|
||||||
|
if (tmp != "" && Directory.Exists(tmp))
|
||||||
|
Directory.Delete(tmp, true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//Use
|
||||||
|
//PowerShell -Command "Add-Type -AssemblyName PresentationFramework;[System.Windows.MessageBox]::Show('Hello World')"
|
||||||
|
//for message boxes
|
||||||
|
private void CompleteInstall(App app, bool force) => CompleteInstall(app.AppPath, app.Name,
|
||||||
|
app.Description, app.Version, app.MainFile, force);
|
||||||
|
|
||||||
|
private void CompleteInstall(string appPath, string name, string description, Version version,
|
||||||
|
string mainFile, bool force)
|
||||||
|
{
|
||||||
|
string tmp = _pathTool.TempPath;
|
||||||
|
ZipFile.ExtractToDirectory(Path.Combine(appPath, "package.zip"), tmp);
|
||||||
|
if (force)
|
||||||
|
Directory.Move(Path.Combine(tmp, "Data"), Path.Combine(appPath, "app"));
|
||||||
|
else
|
||||||
|
{
|
||||||
|
CopyAll(Path.Combine(tmp, "Data"), Path.Combine(appPath, "app"));
|
||||||
|
Directory.Delete(Path.Combine(tmp, "Data"), true);
|
||||||
|
}
|
||||||
|
XElement el = new("app", new XElement("Name", name), new XElement("Description", description),
|
||||||
|
new XElement("Version", version));
|
||||||
|
if (mainFile != null)
|
||||||
|
el.Add(new XElement(new XElement("MainFile", mainFile)));
|
||||||
|
el.Save(Path.Combine(appPath, "info.xml"));
|
||||||
|
/*if (new[] { PlatformID.Xbox, PlatformID.Win32S, PlatformID.Win32Windows, PlatformID.Win32NT, PlatformID.WinCE }.Contains(Environment.OSVersion.Platform))
|
||||||
|
Process.Start(new ProcessStartInfo
|
||||||
|
{
|
||||||
|
FileName = "cmd.exe",
|
||||||
|
ArgumentList = {"/C", $"{Path.Combine(tmp, "Install.bat")}"},
|
||||||
|
WorkingDirectory = Path.Combine(appPath, "app"),
|
||||||
|
CreateNoWindow = true,
|
||||||
|
WindowStyle = ProcessWindowStyle.Hidden
|
||||||
|
}).WaitForExit();
|
||||||
|
else if (File.Exists(Path.Combine(tmp, "Install.sh")))
|
||||||
|
Process.Start(new ProcessStartInfo
|
||||||
|
{
|
||||||
|
FileName = "bash",
|
||||||
|
ArgumentList = {Path.Combine(tmp, "Install.sh")},
|
||||||
|
WorkingDirectory = Path.Combine(appPath, "app"),
|
||||||
|
CreateNoWindow = true,
|
||||||
|
WindowStyle = ProcessWindowStyle.Hidden
|
||||||
|
}).WaitForExit();
|
||||||
|
else
|
||||||
|
Process.Start(new ProcessStartInfo
|
||||||
|
{
|
||||||
|
FileName = "wine",
|
||||||
|
ArgumentList = {"cmd", "/C", $"{Path.Combine(tmp, "Install.bat")}"},
|
||||||
|
WorkingDirectory = Path.Combine(appPath, "app"),
|
||||||
|
CreateNoWindow = true,
|
||||||
|
WindowStyle = ProcessWindowStyle.Hidden
|
||||||
|
}).WaitForExit();*/
|
||||||
|
int key = PlatformCheck.IsWindows ? 0 :
|
||||||
|
File.Exists(Path.Combine(tmp, "Install.sh")) ? 1 : 2;
|
||||||
|
ProcessStartInfo prc = new()
|
||||||
|
{
|
||||||
|
FileName = key switch
|
||||||
|
{
|
||||||
|
0 => "cmd.exe",
|
||||||
|
1 => "bash",
|
||||||
|
2 => "wine",
|
||||||
|
_ => throw new Exception()
|
||||||
|
},
|
||||||
|
WorkingDirectory = Path.Combine(appPath, "app"),
|
||||||
|
CreateNoWindow = true,
|
||||||
|
WindowStyle = ProcessWindowStyle.Hidden
|
||||||
|
};
|
||||||
|
foreach (string s in key switch
|
||||||
|
{
|
||||||
|
0 => new[] {"/C", $"{Path.Combine(tmp, "Install.bat")}"},
|
||||||
|
1 => new[] {Path.Combine(tmp, "Install.sh")},
|
||||||
|
2 => new[] {"cmd", "/C", $"{Path.Combine(tmp, "Install.bat")}"},
|
||||||
|
_ => throw new Exception()
|
||||||
|
})
|
||||||
|
prc.ArgumentList.Add(s);
|
||||||
|
Process.Start(prc)?.WaitForExit();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void CopyAll(string source, string target)
|
||||||
|
{
|
||||||
|
if (string.Equals(Path.GetFullPath(source), Path.GetFullPath(target),
|
||||||
|
StringComparison.CurrentCultureIgnoreCase))
|
||||||
|
return;
|
||||||
|
if (!Directory.Exists(target))
|
||||||
|
Directory.CreateDirectory(target);
|
||||||
|
foreach (string file in Directory.GetFiles(source))
|
||||||
|
File.Copy(file, Path.Combine(target, Path.GetFileName(file)), true);
|
||||||
|
foreach (string dir in Directory.GetDirectories(source))
|
||||||
|
CopyAll(dir, Path.Combine(target, Path.GetFileName(dir)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
25
UpToolLib/v1/Tool/PathTool.cs
Normal file
25
UpToolLib/v1/Tool/PathTool.cs
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
using System;
|
||||||
|
using System.IO;
|
||||||
|
using System.Linq;
|
||||||
|
|
||||||
|
namespace UpToolLib.v1.Tool
|
||||||
|
{
|
||||||
|
public class PathTool
|
||||||
|
{
|
||||||
|
public string Dir =>
|
||||||
|
Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData), "UpTool2");
|
||||||
|
|
||||||
|
public string TempPath => GetRelative("tmp");
|
||||||
|
public string AppsPath => GetRelative("Apps");
|
||||||
|
public string InfoXml => GetRelative("info.xml");
|
||||||
|
|
||||||
|
public string GetRelative(params string[] segments) =>
|
||||||
|
Path.Combine(new[] {Dir}.Concat(segments).ToArray());
|
||||||
|
|
||||||
|
public string GetAppPath(Guid app) => Path.Combine(AppsPath, app.ToString());
|
||||||
|
|
||||||
|
public string GetDataPath(Guid app) => Path.Combine(GetAppPath(app), "app");
|
||||||
|
|
||||||
|
public string GetInfoPath(Guid app) => Path.Combine(GetAppPath(app), "info.xml");
|
||||||
|
}
|
||||||
|
}
|
69
UpToolLib/v1/Tool/XmlTool.cs
Normal file
69
UpToolLib/v1/Tool/XmlTool.cs
Normal file
@ -0,0 +1,69 @@
|
|||||||
|
using System.IO;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Xml.Linq;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
|
||||||
|
namespace UpToolLib.v1.Tool
|
||||||
|
{
|
||||||
|
public class XmlTool
|
||||||
|
{
|
||||||
|
private readonly IExternalFunctionality _platform;
|
||||||
|
private readonly PathTool _pathTool;
|
||||||
|
|
||||||
|
internal XmlTool(IExternalFunctionality platform, PathTool pathTool)
|
||||||
|
{
|
||||||
|
_platform = platform;
|
||||||
|
_pathTool = pathTool;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void FixXml()
|
||||||
|
{
|
||||||
|
if (!Directory.Exists(_pathTool.AppsPath))
|
||||||
|
Directory.CreateDirectory(_pathTool.AppsPath);
|
||||||
|
if (!File.Exists(_pathTool.InfoXml) || XDocument.Load(_pathTool.InfoXml).Element("meta") == null)
|
||||||
|
new XElement("meta").Save(_pathTool.InfoXml);
|
||||||
|
XDocument x = XDocument.Load(_pathTool.InfoXml);
|
||||||
|
XElement meta = x.Element("meta");
|
||||||
|
if (meta.Element("UpdateSource") == null)
|
||||||
|
meta.Add(new XElement("UpdateSource"));
|
||||||
|
if (new[]
|
||||||
|
{
|
||||||
|
"",
|
||||||
|
"https://raw.githubusercontent.com/CreepyCrafter24/UpTool2/master/Meta.xml",
|
||||||
|
"https://raw.githubusercontent.com/JFronny/UpTool2/master/Meta.xml",
|
||||||
|
"https://gist.githubusercontent.com/JFronny/f1ccbba3d8a2f5862592bb29fdb612c4/raw/Meta.xml",
|
||||||
|
"https://github.com/JFronny/UpTool2/releases/latest/download/meta.xml",
|
||||||
|
"https://gitlab.com/JFronny/UpTool2/-/jobs/artifacts/master/raw/meta.xml?job=uptool"
|
||||||
|
}
|
||||||
|
.Contains(meta.Element("UpdateSource").Value))
|
||||||
|
meta.Element("UpdateSource").Value =
|
||||||
|
"https://gitlab.com/uptool/UpTool2/-/jobs/artifacts/master/raw/meta.xml?job=uptool";
|
||||||
|
if (meta.Element("Repos") == null)
|
||||||
|
meta.Add(new XElement("Repos"));
|
||||||
|
if (meta.Element("Repos").Elements("Repo").Count() == 0)
|
||||||
|
{
|
||||||
|
if (_platform.YesNoDialog(
|
||||||
|
"No active repository was detected. Add the default repo?", false))
|
||||||
|
{
|
||||||
|
meta.Element("Repos").Add(new XElement("Repo", new XElement("Name", "UpTool2 official Repo"),
|
||||||
|
new XElement("Link",
|
||||||
|
"https://gitlab.com/uptool/UpTool2/-/snippets/1988600/raw/master/Repo.xml")));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
meta.Element("Repos").Elements("Repo").Select(s => s.Element("Link"))
|
||||||
|
.Where(s => new[]
|
||||||
|
{
|
||||||
|
null, "https://github.com/JFronny/UpTool2/releases/download/Repo/Repo.xml",
|
||||||
|
"https://raw.githubusercontent.com/JFronny/UpTool2/master/Repo.xml",
|
||||||
|
"https://gist.githubusercontent.com/JFronny/f1ccbba3d8a2f5862592bb29fdb612c4/raw/Repo.xml",
|
||||||
|
"https://gitlab.com/JFronny/UpTool2/snippets/1988600/raw"
|
||||||
|
}.Contains(s.Value))
|
||||||
|
.ToList().ForEach(s =>
|
||||||
|
s.Value =
|
||||||
|
"https://gitlab.com/uptool/UpTool2/-/snippets/1988600/raw/master/Repo.xml");
|
||||||
|
if (meta.Element("LocalRepo") == null)
|
||||||
|
meta.Add(new XElement("LocalRepo"));
|
||||||
|
x.Save(_pathTool.InfoXml);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
26
UpToolLib/v1/UpToolLibV1.cs
Normal file
26
UpToolLib/v1/UpToolLibV1.cs
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
using UpToolLib.v2;
|
||||||
|
|
||||||
|
namespace UpToolLib.v1
|
||||||
|
{
|
||||||
|
public class UpToolLibV1
|
||||||
|
{
|
||||||
|
internal UpToolLibV1(IExternalFunctionality platform)
|
||||||
|
{
|
||||||
|
PathTool = new PathTool();
|
||||||
|
XmlTool = new XmlTool(platform, PathTool);
|
||||||
|
Installer = new AppInstall(platform, PathTool);
|
||||||
|
AppExtras = new AppExtras(Installer, PathTool, Apps);
|
||||||
|
}
|
||||||
|
public readonly AppExtras AppExtras;
|
||||||
|
public readonly AppInstall Installer;
|
||||||
|
public readonly PathTool PathTool;
|
||||||
|
public readonly XmlTool XmlTool;
|
||||||
|
|
||||||
|
public readonly IDictionary<Guid, App> Apps = new Dictionary<Guid, App>();
|
||||||
|
public static Version MinimumVer => Version.Parse("0.0.0.0");
|
||||||
|
}
|
||||||
|
}
|
@ -3,10 +3,11 @@ using System.Collections.Generic;
|
|||||||
using System.Drawing;
|
using System.Drawing;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Xml.Linq;
|
using System.Xml.Linq;
|
||||||
using UpTool2.Tool;
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
using static System.Environment;
|
using static System.Environment;
|
||||||
|
|
||||||
namespace UpTool2.DataStructures
|
namespace UpToolLib.v2
|
||||||
{
|
{
|
||||||
public struct App : IEquatable<App>
|
public struct App : IEquatable<App>
|
||||||
{
|
{
|
||||||
@ -16,14 +17,15 @@ namespace UpTool2.DataStructures
|
|||||||
public readonly string File;
|
public readonly string File;
|
||||||
public readonly bool Local;
|
public readonly bool Local;
|
||||||
public readonly string Hash;
|
public readonly string Hash;
|
||||||
private Guid _id;
|
public readonly Guid Id;
|
||||||
public Color Color;
|
public Color Color;
|
||||||
public readonly Image Icon;
|
public readonly object Icon;
|
||||||
public readonly bool Runnable;
|
public readonly bool Runnable;
|
||||||
public readonly string MainFile;
|
public readonly string MainFile;
|
||||||
|
private readonly PathTool _pathTool;
|
||||||
|
|
||||||
public App(string name, string description, Version version, string file, bool local, string hash, Guid iD,
|
internal App(string name, string description, Version version, string file, bool local, string hash, Guid iD,
|
||||||
Color color, Image icon, bool runnable, string mainFile)
|
Color color, object icon, bool runnable, string mainFile, PathTool pathTool)
|
||||||
{
|
{
|
||||||
Name = name ?? throw new ArgumentNullException(nameof(name));
|
Name = name ?? throw new ArgumentNullException(nameof(name));
|
||||||
Description = description ?? throw new ArgumentNullException(nameof(description));
|
Description = description ?? throw new ArgumentNullException(nameof(description));
|
||||||
@ -31,20 +33,21 @@ namespace UpTool2.DataStructures
|
|||||||
File = file ?? throw new ArgumentNullException(nameof(file));
|
File = file ?? throw new ArgumentNullException(nameof(file));
|
||||||
Local = local;
|
Local = local;
|
||||||
Hash = hash ?? throw new ArgumentNullException(nameof(hash));
|
Hash = hash ?? throw new ArgumentNullException(nameof(hash));
|
||||||
_id = iD;
|
Id = iD;
|
||||||
Color = color;
|
Color = color;
|
||||||
Icon = icon ?? throw new ArgumentNullException(nameof(icon));
|
Icon = icon ?? throw new ArgumentNullException(nameof(icon));
|
||||||
Runnable = runnable;
|
Runnable = runnable;
|
||||||
MainFile = mainFile ?? throw new ArgumentNullException(nameof(mainFile));
|
MainFile = mainFile ?? throw new ArgumentNullException(nameof(mainFile));
|
||||||
|
_pathTool = pathTool;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Status status
|
public Status Status
|
||||||
{
|
{
|
||||||
get
|
get
|
||||||
{
|
{
|
||||||
if (!System.IO.File.Exists(infoPath))
|
if (!System.IO.File.Exists(InfoPath))
|
||||||
return Status.Not_Installed;
|
return Status.NotInstalled;
|
||||||
if (Version.TryParse(XDocument.Load(infoPath).Element("app").Element("Version").Value,
|
if (Version.TryParse(XDocument.Load(InfoPath).Element("app").Element("Version").Value,
|
||||||
out Version ver) && ver >= Version)
|
out Version ver) && ver >= Version)
|
||||||
return Local ? Status.Installed | Status.Local : Status.Installed;
|
return Local ? Status.Installed | Status.Local : Status.Installed;
|
||||||
return Status.Installed | Status.Updatable;
|
return Status.Installed | Status.Updatable;
|
||||||
@ -53,30 +56,30 @@ namespace UpTool2.DataStructures
|
|||||||
|
|
||||||
public override bool Equals(object obj) => obj is App app && Equals(app);
|
public override bool Equals(object obj) => obj is App app && Equals(app);
|
||||||
|
|
||||||
public bool Equals(App other) => _id.Equals(other._id);
|
public bool Equals(App other) => Id.Equals(other.Id);
|
||||||
|
|
||||||
public override int GetHashCode() => 1213502048 + EqualityComparer<Guid>.Default.GetHashCode(_id);
|
public override int GetHashCode() => 1213502048 + EqualityComparer<Guid>.Default.GetHashCode(Id);
|
||||||
|
|
||||||
public override string ToString() => $@"Name: {Name}
|
public override string ToString() => $@"Name: {Name}
|
||||||
Description:
|
Description:
|
||||||
{string.Join(NewLine, Description.Split('\n').Select(s => { if (s.EndsWith("\r")) s.Remove(s.Length - 1, 1); return "> " + s; }))}
|
{string.Join(NewLine, Description.Split('\n').Select(s => { if (s.EndsWith("\r")) s.Remove(s.Length - 1, 1); return $"> {s}"; }))}
|
||||||
Version: {Version}
|
Version: {Version}
|
||||||
File: {File}
|
File: {File}
|
||||||
Local: {Local.ToString()}
|
Local: {Local}
|
||||||
Hash: {Hash}
|
Hash: {Hash}
|
||||||
ID: {_id.ToString()}
|
ID: {Id}
|
||||||
Color: {Color.ToKnownColor().ToString()}
|
Color: {Color.ToKnownColor()}
|
||||||
Runnable: {Runnable}
|
Runnable: {Runnable}
|
||||||
MainFile: {MainFile}
|
MainFile: {MainFile}
|
||||||
Status: {status.ToString()}
|
Status: {Status}
|
||||||
Object Hash Code: {GetHashCode()}";
|
Object Hash Code: {GetHashCode()}";
|
||||||
|
|
||||||
public static bool operator ==(App left, App right) => left.Equals(right);
|
public static bool operator ==(App left, App right) => left.Equals(right);
|
||||||
|
|
||||||
public static bool operator !=(App left, App right) => !(left == right);
|
public static bool operator !=(App left, App right) => !(left == right);
|
||||||
|
|
||||||
public string appPath => PathTool.GetAppPath(_id);
|
public string AppPath => _pathTool.GetAppPath(Id);
|
||||||
public string dataPath => PathTool.GetDataPath(_id);
|
public string DataPath => _pathTool.GetDataPath(Id);
|
||||||
public string infoPath => PathTool.GetInfoPath(_id);
|
public string InfoPath => _pathTool.GetInfoPath(Id);
|
||||||
}
|
}
|
||||||
}
|
}
|
18
UpToolLib/v2/AppFactory.cs
Normal file
18
UpToolLib/v2/AppFactory.cs
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
using System;
|
||||||
|
using System.Drawing;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
|
||||||
|
namespace UpToolLib.v2
|
||||||
|
{
|
||||||
|
public class AppFactory
|
||||||
|
{
|
||||||
|
private readonly PathTool _pathTool;
|
||||||
|
|
||||||
|
internal AppFactory(PathTool pathTool) => _pathTool = pathTool;
|
||||||
|
|
||||||
|
public App CreateApp(string name, string description, Version version, string file, bool local, string hash,
|
||||||
|
Guid iD, Color color, object icon, bool runnable, string mainFile) =>
|
||||||
|
new(name, description, version, file, local, hash, iD, color, icon, runnable, mainFile, _pathTool);
|
||||||
|
}
|
||||||
|
}
|
219
UpToolLib/v2/RepoManagement.cs
Normal file
219
UpToolLib/v2/RepoManagement.cs
Normal file
@ -0,0 +1,219 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Drawing;
|
||||||
|
using System.IO;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Xml.Linq;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
|
||||||
|
namespace UpToolLib.v2
|
||||||
|
{
|
||||||
|
public class RepoManagement
|
||||||
|
{
|
||||||
|
private readonly IExternalFunctionality _platform;
|
||||||
|
private readonly XmlTool _xmlTool;
|
||||||
|
private readonly PathTool _pathTool;
|
||||||
|
private readonly AppFactory _appFactory;
|
||||||
|
private readonly IDictionary<Guid, App> _apps;
|
||||||
|
|
||||||
|
public RepoManagement(IExternalFunctionality platform, XmlTool xmlTool, PathTool pathTool, AppFactory appFactory, IDictionary<Guid, App> apps)
|
||||||
|
{
|
||||||
|
_platform = platform;
|
||||||
|
_xmlTool = xmlTool;
|
||||||
|
_pathTool = pathTool;
|
||||||
|
_appFactory = appFactory;
|
||||||
|
_apps = apps;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void Save(IEnumerable<Repo> repos)
|
||||||
|
{
|
||||||
|
XDocument doc = XDocument.Load(_pathTool.InfoXml);
|
||||||
|
XElement reposEl = doc.Element("meta").Element("Repos");
|
||||||
|
reposEl.RemoveNodes();
|
||||||
|
foreach (Repo repo in repos)
|
||||||
|
reposEl.Add(new XElement("Repo", new XElement("Name", repo.Name), new XElement("Link", repo.Url)));
|
||||||
|
doc.Save(_pathTool.InfoXml);
|
||||||
|
}
|
||||||
|
|
||||||
|
public IEnumerable<Repo> GetRepos()
|
||||||
|
{
|
||||||
|
_xmlTool.FixXml();
|
||||||
|
XDocument doc = XDocument.Load(_pathTool.InfoXml);
|
||||||
|
XElement reposEl = doc.Element("meta").Element("Repos");
|
||||||
|
List<Repo> repos = new();
|
||||||
|
foreach (XElement repo in reposEl.Elements("Repo"))
|
||||||
|
{
|
||||||
|
repos.Add(new Repo
|
||||||
|
{
|
||||||
|
Name = repo.Element("Name").Value,
|
||||||
|
Url = repo.Element("Link").Value
|
||||||
|
});
|
||||||
|
}
|
||||||
|
return repos.ToArray();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void FetchRepos()
|
||||||
|
{
|
||||||
|
_xmlTool.FixXml();
|
||||||
|
XElement meta = XDocument.Load(_pathTool.InfoXml).Element("meta");
|
||||||
|
List<XElement> tmpAppsList = new();
|
||||||
|
List<string> repArr = meta.Element("Repos").Elements("Repo").Select(s => s.Element("Link").Value).Distinct()
|
||||||
|
.ToList();
|
||||||
|
int i = 0;
|
||||||
|
while (i < repArr.Count)
|
||||||
|
{
|
||||||
|
string status = "Initializing";
|
||||||
|
#if !DEBUG
|
||||||
|
try
|
||||||
|
{
|
||||||
|
#endif
|
||||||
|
_platform.Log($"[{i + 1}] Loading {repArr[i]}");
|
||||||
|
status = $"Loading {repArr[i]}";
|
||||||
|
XDocument repo = XDocument.Load(new Uri(repArr[i]).AbsoluteUri);
|
||||||
|
status = $"Extracting repolinks";
|
||||||
|
repArr.AddRange(repo.Element("repo").Elements("repolink").Select(s => s.Value)
|
||||||
|
.Where(s => !repArr.Contains(s)));
|
||||||
|
status = $"Extracting apps";
|
||||||
|
XElement[] tmpApparray = repo.Element("repo").Elements("app").Where(app =>
|
||||||
|
!tmpAppsList.Any(a => a.Element("ID").Value == app.Element("ID").Value) ||
|
||||||
|
!tmpAppsList
|
||||||
|
.Where(a => a.Element("ID").Value == app.Element("ID").Value).Any(a =>
|
||||||
|
GetVer(a.Element("Version")) >= GetVer(app.Element("Version")))).ToArray()
|
||||||
|
.Concat(repo.Element("repo").Elements("applink")
|
||||||
|
.Select(s =>
|
||||||
|
{
|
||||||
|
_platform.Log($"- Loading {s.Value}");
|
||||||
|
status = $"Fetching app data tag: {s.Value}";
|
||||||
|
XElement ret = XDocument.Load(new Uri(s.Value).AbsoluteUri)
|
||||||
|
.Element("app");
|
||||||
|
return ret;
|
||||||
|
}))
|
||||||
|
.ToArray();
|
||||||
|
status = $"Creating app cache";
|
||||||
|
foreach (XElement app in tmpApparray)
|
||||||
|
{
|
||||||
|
//"Sanity check"
|
||||||
|
Version.Parse(app.Element("Version").Value);
|
||||||
|
Guid.Parse(app.Element("ID").Value);
|
||||||
|
//Create XElement
|
||||||
|
tmpAppsList.Add(new XElement("App",
|
||||||
|
new XElement("Name", app.Element("Name").Value),
|
||||||
|
new XElement("Description", app.Element("Description").Value),
|
||||||
|
new XElement("Version", app.Element("Version").Value),
|
||||||
|
new XElement("ID", app.Element("ID").Value),
|
||||||
|
new XElement("File", new Uri(app.Element("File").Value).ToString()),
|
||||||
|
new XElement("Hash", app.Element("Hash").Value)
|
||||||
|
));
|
||||||
|
if (app.Element("MainFile") != null)
|
||||||
|
tmpAppsList.Last().Add(new XElement("MainFile", app.Element("MainFile").Value));
|
||||||
|
if (app.Element("Icon") != null)
|
||||||
|
try
|
||||||
|
{
|
||||||
|
tmpAppsList.Last()
|
||||||
|
.Add(new XElement("Icon",
|
||||||
|
_platform.FetchImageB64(new Uri(app.Element("Icon").Value))));
|
||||||
|
}
|
||||||
|
catch
|
||||||
|
{
|
||||||
|
// ignored
|
||||||
|
}
|
||||||
|
tmpAppsList.Last().Add(new XElement("Platform",
|
||||||
|
app.Element("Platform") == null ||
|
||||||
|
!new[] {PlatformCheck.Posix, PlatformCheck.Windows}.Contains(app.Element("Platform")
|
||||||
|
.Value)
|
||||||
|
? PlatformCheck.CurrentPlatform
|
||||||
|
: app.Element("Platform").Value));
|
||||||
|
XElement app1 = app;
|
||||||
|
if (tmpAppsList.Count(a => a.Element("ID").Value == app1.Element("ID").Value) > 1)
|
||||||
|
tmpAppsList.Where(a => a.Element("ID").Value == app.Element("ID").Value).Reverse()
|
||||||
|
.Skip(1)
|
||||||
|
.ToList().ForEach(a => tmpAppsList.Remove(a));
|
||||||
|
}
|
||||||
|
#if !DEBUG
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
_platform.OkDialog(
|
||||||
|
$"Failed to load repo: {repArr[i]}{Environment.NewLine}Last status was: {status}{Environment.NewLine}{e}");
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
tmpAppsList.Sort((x, y) =>
|
||||||
|
string.Compare(x.Element("Name").Value, y.Element("Name").Value, StringComparison.Ordinal));
|
||||||
|
if (meta.Element("LocalRepo") == null)
|
||||||
|
meta.Add(new XElement("LocalRepo"));
|
||||||
|
XElement repos = meta.Element("LocalRepo");
|
||||||
|
repos.RemoveNodes();
|
||||||
|
tmpAppsList.ForEach(app => repos.Add(app));
|
||||||
|
meta.Save(_pathTool.InfoXml);
|
||||||
|
}
|
||||||
|
|
||||||
|
private Version GetVer(XElement el) =>
|
||||||
|
int.TryParse(el.Value, out int i) ? new Version(0, 0, 0, i) : Version.Parse(el.Value);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Load the repository cache
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="errorHandler">Function to call on an exception, will ask the user whether he wants to quit</param>
|
||||||
|
public void GetReposFromDisk()
|
||||||
|
{
|
||||||
|
_apps.Clear();
|
||||||
|
string xml = _pathTool.InfoXml;
|
||||||
|
XDocument.Load(xml).Element("meta").Element("LocalRepo").Elements().ToList().ForEach(app =>
|
||||||
|
{
|
||||||
|
if (app.Element("Platform").Value != PlatformCheck.CurrentPlatform) return;
|
||||||
|
Guid id = Guid.Parse(app.Element("ID").Value);
|
||||||
|
string locInPath = _pathTool.GetInfoPath(id);
|
||||||
|
XElement locIn = File.Exists(locInPath) ? XDocument.Load(locInPath).Element("app") : app;
|
||||||
|
if (int.TryParse(app.Element("Version").Value, out _))
|
||||||
|
app.Element("Version").Value = UpToolLibV1.MinimumVer.ToString();
|
||||||
|
_apps.Add(id, _appFactory.CreateApp(
|
||||||
|
locIn.Element("Name").Value,
|
||||||
|
locIn.Element("Description").Value,
|
||||||
|
Version.Parse(app.Element("Version").Value),
|
||||||
|
app.Element("File").Value,
|
||||||
|
false,
|
||||||
|
app.Element("Hash").Value,
|
||||||
|
id,
|
||||||
|
Color.White,
|
||||||
|
app.Element("Icon") == null
|
||||||
|
? _platform.GetDefaultIcon()
|
||||||
|
: _platform.ImageFromB64(app.Element("Icon").Value),
|
||||||
|
locIn.Element("MainFile") != null || app.Element("MainFile") != null,
|
||||||
|
locIn.Element("MainFile") == null
|
||||||
|
? app.Element("MainFile") == null ? "" : app.Element("MainFile").Value
|
||||||
|
: locIn.Element("MainFile").Value
|
||||||
|
));
|
||||||
|
});
|
||||||
|
Directory.GetDirectories(_pathTool.AppsPath)
|
||||||
|
.Where(s => Guid.TryParse(Path.GetFileName(s), out Guid guid) &&
|
||||||
|
!_apps.ContainsKey(guid)).ToList().ForEach(s =>
|
||||||
|
{
|
||||||
|
Guid tmp = Guid.Parse(Path.GetFileName(s));
|
||||||
|
try
|
||||||
|
{
|
||||||
|
XElement data = XDocument.Load(_pathTool.GetInfoPath(tmp)).Element("app");
|
||||||
|
_apps.Add(tmp,
|
||||||
|
_appFactory.CreateApp($"(local) {data.Element("Name").Value}", data.Element("Description").Value,
|
||||||
|
UpToolLibV1.MinimumVer, "", true, "", tmp, Color.Red,
|
||||||
|
_platform.GetDefaultIcon(),
|
||||||
|
data.Element("MainFile") != null,
|
||||||
|
data.Element("MainFile") == null ? "" : data.Element("MainFile").Value));
|
||||||
|
}
|
||||||
|
catch (Exception e)
|
||||||
|
{
|
||||||
|
if (_platform.YesNoDialog(
|
||||||
|
$@"An error occured while loading this local repo:
|
||||||
|
{e.Message}
|
||||||
|
Do you want to exit? Otherwise the folder will be deleted, possibly causeing problems later.", false))
|
||||||
|
Environment.Exit(0);
|
||||||
|
else
|
||||||
|
Directory.Delete(_pathTool.GetAppPath(tmp), true);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
13
UpToolLib/v2/TaskQueue/AppTask.cs
Normal file
13
UpToolLib/v2/TaskQueue/AppTask.cs
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
using UpToolLib.DataStructures;
|
||||||
|
|
||||||
|
namespace UpToolLib.v2.TaskQueue
|
||||||
|
{
|
||||||
|
public abstract class AppTask
|
||||||
|
{
|
||||||
|
public abstract void Run();
|
||||||
|
|
||||||
|
public AppTask(IExternalFunctionality platform) => Platform = platform;
|
||||||
|
|
||||||
|
protected IExternalFunctionality Platform { get; }
|
||||||
|
}
|
||||||
|
}
|
43
UpToolLib/v2/TaskQueue/InstallTask.cs
Normal file
43
UpToolLib/v2/TaskQueue/InstallTask.cs
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
using System;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
|
||||||
|
namespace UpToolLib.v2.TaskQueue
|
||||||
|
{
|
||||||
|
public class InstallTask : KnownAppTask
|
||||||
|
{
|
||||||
|
private readonly AppInstall _installer;
|
||||||
|
private readonly Action? _postInstall;
|
||||||
|
|
||||||
|
internal InstallTask(IExternalFunctionality platform, AppInstall installer, App app, Action? postInstall) : base(platform)
|
||||||
|
{
|
||||||
|
App = app;
|
||||||
|
_installer = installer;
|
||||||
|
_postInstall = postInstall;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override App App { get; }
|
||||||
|
|
||||||
|
public override void Run()
|
||||||
|
{
|
||||||
|
bool trying = true;
|
||||||
|
while (trying)
|
||||||
|
{
|
||||||
|
#if !DEBUG
|
||||||
|
try
|
||||||
|
{
|
||||||
|
#endif
|
||||||
|
_installer.Install(App, true);
|
||||||
|
_postInstall?.Invoke();
|
||||||
|
trying = false;
|
||||||
|
#if !DEBUG
|
||||||
|
}
|
||||||
|
catch (Exception e1)
|
||||||
|
{
|
||||||
|
trying = Platform.YesNoDialog("Install failed. Retry?\r\nException=" + e1, true);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
25
UpToolLib/v2/TaskQueue/KnownAppTask.cs
Normal file
25
UpToolLib/v2/TaskQueue/KnownAppTask.cs
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
using UpToolLib.DataStructures;
|
||||||
|
|
||||||
|
namespace UpToolLib.v2.TaskQueue
|
||||||
|
{
|
||||||
|
public abstract class KnownAppTask : AppTask
|
||||||
|
{
|
||||||
|
public abstract App App { get; }
|
||||||
|
|
||||||
|
public override string ToString() => $"{TrimEnd(GetType().Name, "Task")} {App.Name}";
|
||||||
|
|
||||||
|
private static string TrimEnd(string target, string trimString)
|
||||||
|
{
|
||||||
|
if (string.IsNullOrEmpty(trimString)) return target;
|
||||||
|
|
||||||
|
string result = target;
|
||||||
|
while (result.EndsWith(trimString)) result = result.Substring(0, result.Length - trimString.Length);
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected KnownAppTask(IExternalFunctionality platform) : base(platform)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
38
UpToolLib/v2/TaskQueue/RemoveTask.cs
Normal file
38
UpToolLib/v2/TaskQueue/RemoveTask.cs
Normal file
@ -0,0 +1,38 @@
|
|||||||
|
using System;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
|
||||||
|
namespace UpToolLib.v2.TaskQueue
|
||||||
|
{
|
||||||
|
public class RemoveTask : KnownAppTask
|
||||||
|
{
|
||||||
|
private readonly AppExtras _extras;
|
||||||
|
private readonly Action? _postInstall;
|
||||||
|
|
||||||
|
internal RemoveTask(IExternalFunctionality platform, AppExtras extras, App app, Action? postInstall) : base(platform)
|
||||||
|
{
|
||||||
|
App = app;
|
||||||
|
_extras = extras;
|
||||||
|
_postInstall = postInstall;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override App App { get; }
|
||||||
|
|
||||||
|
public override void Run()
|
||||||
|
{
|
||||||
|
#if !DEBUG
|
||||||
|
try
|
||||||
|
{
|
||||||
|
#endif
|
||||||
|
_extras.Remove(App, true);
|
||||||
|
_postInstall?.Invoke();
|
||||||
|
#if !DEBUG
|
||||||
|
}
|
||||||
|
catch (Exception e1)
|
||||||
|
{
|
||||||
|
Platform.OkDialog("Removal failed.\r\nException=" + e1);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
35
UpToolLib/v2/TaskQueue/TaskFactory.cs
Normal file
35
UpToolLib/v2/TaskQueue/TaskFactory.cs
Normal file
@ -0,0 +1,35 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
|
||||||
|
namespace UpToolLib.v2.TaskQueue
|
||||||
|
{
|
||||||
|
public class TaskFactory
|
||||||
|
{
|
||||||
|
private IExternalFunctionality _platform;
|
||||||
|
private readonly AppInstall _installer;
|
||||||
|
private readonly AppExtras _extras;
|
||||||
|
private readonly PathTool _pathTool;
|
||||||
|
private readonly AppFactory _appFactory;
|
||||||
|
private readonly IDictionary<Guid, App> _apps;
|
||||||
|
|
||||||
|
internal TaskFactory(IExternalFunctionality platform, AppInstall installer, AppExtras extras, PathTool pathTool, AppFactory appFactory, IDictionary<Guid, App> apps)
|
||||||
|
{
|
||||||
|
_platform = platform;
|
||||||
|
_installer = installer;
|
||||||
|
_extras = extras;
|
||||||
|
_pathTool = pathTool;
|
||||||
|
_appFactory = appFactory;
|
||||||
|
_apps = apps;
|
||||||
|
}
|
||||||
|
|
||||||
|
public KnownAppTask CreateInstall(App app, Action? postInstall = null) => new InstallTask(_platform, _installer, app, postInstall);
|
||||||
|
|
||||||
|
public KnownAppTask CreateRemove(App app, Action? postInstall = null) => new RemoveTask(_platform, _extras, app, postInstall);
|
||||||
|
|
||||||
|
public KnownAppTask CreateUpdate(App app, Action? postInstall = null) => new UpdateTask(_platform, _extras, app, postInstall);
|
||||||
|
|
||||||
|
public AppTask CreateUpload(string zipFile, string name, Action? postInstall = null) => new UploadTask(_platform, _installer, _appFactory, _pathTool, _apps, zipFile, name, postInstall);
|
||||||
|
}
|
||||||
|
}
|
38
UpToolLib/v2/TaskQueue/UpdateTask.cs
Normal file
38
UpToolLib/v2/TaskQueue/UpdateTask.cs
Normal file
@ -0,0 +1,38 @@
|
|||||||
|
using System;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
|
||||||
|
namespace UpToolLib.v2.TaskQueue
|
||||||
|
{
|
||||||
|
public class UpdateTask : KnownAppTask
|
||||||
|
{
|
||||||
|
private readonly AppExtras _extras;
|
||||||
|
private readonly Action? _postInstall;
|
||||||
|
|
||||||
|
internal UpdateTask(IExternalFunctionality platform, AppExtras extras, App app, Action? postInstall) : base(platform)
|
||||||
|
{
|
||||||
|
App = app;
|
||||||
|
_extras = extras;
|
||||||
|
_postInstall = postInstall;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override App App { get; }
|
||||||
|
|
||||||
|
public override void Run()
|
||||||
|
{
|
||||||
|
#if !DEBUG
|
||||||
|
try
|
||||||
|
{
|
||||||
|
#endif
|
||||||
|
_extras.Update(App, false);
|
||||||
|
_postInstall?.Invoke();
|
||||||
|
#if !DEBUG
|
||||||
|
}
|
||||||
|
catch (Exception e1)
|
||||||
|
{
|
||||||
|
Platform.OkDialog("Update failed.\r\nException=" + e1);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
56
UpToolLib/v2/TaskQueue/UploadTask.cs
Normal file
56
UpToolLib/v2/TaskQueue/UploadTask.cs
Normal file
@ -0,0 +1,56 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Drawing;
|
||||||
|
using System.IO;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
|
||||||
|
namespace UpToolLib.v2.TaskQueue
|
||||||
|
{
|
||||||
|
public class UploadTask : AppTask
|
||||||
|
{
|
||||||
|
private readonly string _name;
|
||||||
|
private readonly Action? _postInstall;
|
||||||
|
private readonly AppInstall _installer;
|
||||||
|
private readonly AppFactory _appFactory;
|
||||||
|
private readonly PathTool _pathTool;
|
||||||
|
private readonly IDictionary<Guid, App> _apps;
|
||||||
|
public readonly string ZipFile;
|
||||||
|
|
||||||
|
internal UploadTask(IExternalFunctionality platform, AppInstall installer, AppFactory appFactory, PathTool pathTool, IDictionary<Guid, App> apps, string zipFile, string name, Action? postInstall) : base(platform)
|
||||||
|
{
|
||||||
|
_installer = installer;
|
||||||
|
_appFactory = appFactory;
|
||||||
|
_pathTool = pathTool;
|
||||||
|
_apps = apps;
|
||||||
|
ZipFile = zipFile;
|
||||||
|
_name = name;
|
||||||
|
_postInstall = postInstall;
|
||||||
|
}
|
||||||
|
|
||||||
|
public override void Run()
|
||||||
|
{
|
||||||
|
#if !DEBUG
|
||||||
|
try
|
||||||
|
{
|
||||||
|
#endif
|
||||||
|
Guid id = Guid.NewGuid();
|
||||||
|
while (_apps.ContainsKey(id) || Directory.Exists(_pathTool.GetAppPath(id)))
|
||||||
|
id = Guid.NewGuid();
|
||||||
|
App appI = _appFactory.CreateApp(_name, "Locally installed package, removal only",
|
||||||
|
UpToolLibV1.MinimumVer, "", true, "", id, Color.Red, Platform.GetDefaultIcon(), false, "");
|
||||||
|
_installer.InstallZip(ZipFile, appI, true);
|
||||||
|
_postInstall?.Invoke();
|
||||||
|
#if !DEBUG
|
||||||
|
}
|
||||||
|
catch (Exception e1)
|
||||||
|
{
|
||||||
|
Platform.OkDialog("Upload failed.\r\nException=" + e1);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
public override string ToString() => $"Install local {Path.GetFileName(ZipFile)}";
|
||||||
|
}
|
||||||
|
}
|
24
UpToolLib/v2/UpToolLibV2.cs
Normal file
24
UpToolLib/v2/UpToolLibV2.cs
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using UpToolLib.DataStructures;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
using UpToolLib.v2.TaskQueue;
|
||||||
|
|
||||||
|
namespace UpToolLib.v2
|
||||||
|
{
|
||||||
|
public class UpToolLibV2
|
||||||
|
{
|
||||||
|
internal UpToolLibV2(IExternalFunctionality platform, AppInstall install, AppExtras extras, PathTool pathTool, XmlTool xmlTool, IDictionary<Guid, App> apps)
|
||||||
|
{
|
||||||
|
AppFactory = new AppFactory(pathTool);
|
||||||
|
UpdateChecker = new UpdateChecker(pathTool);
|
||||||
|
TaskFactory = new TaskFactory(platform, install, extras, pathTool, AppFactory, apps);
|
||||||
|
RepoManagement = new RepoManagement(platform, xmlTool, pathTool, AppFactory, apps);
|
||||||
|
}
|
||||||
|
|
||||||
|
public readonly UpdateChecker UpdateChecker;
|
||||||
|
public readonly TaskFactory TaskFactory;
|
||||||
|
public readonly AppFactory AppFactory;
|
||||||
|
public readonly RepoManagement RepoManagement;
|
||||||
|
}
|
||||||
|
}
|
23
UpToolLib/v2/UpdateCheck.cs
Normal file
23
UpToolLib/v2/UpdateCheck.cs
Normal file
@ -0,0 +1,23 @@
|
|||||||
|
using System;
|
||||||
|
using System.Xml.Linq;
|
||||||
|
|
||||||
|
namespace UpToolLib.v2
|
||||||
|
{
|
||||||
|
public class UpdateCheck
|
||||||
|
{
|
||||||
|
public readonly Version OnlineVersion;
|
||||||
|
public readonly Uri Installer;
|
||||||
|
public readonly string InstallerHash;
|
||||||
|
public readonly Uri App;
|
||||||
|
public readonly string AppHash;
|
||||||
|
|
||||||
|
public UpdateCheck(XElement meta)
|
||||||
|
{
|
||||||
|
OnlineVersion = Version.Parse(meta.Element("Version").Value);
|
||||||
|
Installer = new Uri(meta.Element("Installer").Value);
|
||||||
|
InstallerHash = meta.Element("InstallerHash").Value.ToUpper();
|
||||||
|
App = new Uri(meta.Element("File").Value);
|
||||||
|
AppHash = meta.Element("Hash").Value.ToUpper();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
13
UpToolLib/v2/UpdateChecker.cs
Normal file
13
UpToolLib/v2/UpdateChecker.cs
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
using System.Xml.Linq;
|
||||||
|
using UpToolLib.v1.Tool;
|
||||||
|
|
||||||
|
namespace UpToolLib.v2
|
||||||
|
{
|
||||||
|
public class UpdateChecker
|
||||||
|
{
|
||||||
|
private readonly PathTool _pathTool;
|
||||||
|
public UpdateCheck Check() => Check(XDocument.Load(_pathTool.InfoXml).Element("meta").Element("UpdateSource").Value);
|
||||||
|
public UpdateCheck Check(string source) => new(XDocument.Load(source).Element("meta"));
|
||||||
|
internal UpdateChecker(PathTool pathTool) => _pathTool = pathTool;
|
||||||
|
}
|
||||||
|
}
|
13
renovate.json
Normal file
13
renovate.json
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
{
|
||||||
|
"extends": [
|
||||||
|
"config:base"
|
||||||
|
],
|
||||||
|
"hostRules": [
|
||||||
|
{
|
||||||
|
"domainName": "github.com",
|
||||||
|
"encrypted": {
|
||||||
|
"token": "o53wjvsApqgx2krTKwD5LBnbmtK7gZ4zgAYsFIxLxf3blIMY2y9tUpsVNo4thY/kTA1tDOvIiP9PNdJV/DRYqvMDQMxvKiGHE1eSrpmrICRaq4Bhdc9/QZotkliqcziynLV0vD+xXZ7tyXKhR+nZijp4K1H2euCAv8vCVAUrpXIlBf/gmHvfEjmTDKUqJTEAvzre7H7l3C7SmQ2VwyE6gEFD91K9jGbgfI6MIgjx3i3O4fxM/JLXmUR19mGVK//Hpc1GXyVePB1sdzYhsyMU/3hzR3d/lJLOrHhr40WO1vNf3aB0WVDqqsl+XwoFxBxFqhSPTVHkEsylD+l+d8fsXA=="
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
Reference in New Issue
Block a user