Skip to content

Commit

Permalink
Merge pull request #13 from NicolasConstant/develop
Browse files Browse the repository at this point in the history
0.5.0 PR
  • Loading branch information
NicolasConstant authored Jun 4, 2021
2 parents 47455f8 + 19cfe4b commit df0bbb3
Show file tree
Hide file tree
Showing 34 changed files with 907 additions and 121 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/windows.yml
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ jobs:
build:
strategy:
matrix:
node-version: [10.13.0, 12.x, 14.x, 15.x]
node-version: [14.x]

# The type of runner that the job will run on
runs-on: windows-latest
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "msfs-community-downloader",
"version": "0.4.0",
"version": "0.5.0",
"description": "MSFS addin downloader client",
"homepage": "https://github.com/nicolasconstant/msfs-community-downloader",
"author": {
Expand Down
7 changes: 7 additions & 0 deletions src/app/app.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,12 @@ import { SettingsModule } from './settings/settings.module';

import { AppComponent } from './app.component';
import { FontAwesomeModule } from '@fortawesome/angular-fontawesome';
import { ImportModule } from './import/import.module';

// import { AddPackageComponent } from './import/add-package.component';
// import { CreatePackageComponent } from './import/create-package/create-package.component';
// import { ImportPackageComponent } from './import/import-package/import-package.component';
// import { ExportPackageComponent } from './import/export-package/export-package.component';

// AoT requires an exported function for factories
export function HttpLoaderFactory(http: HttpClient): TranslateHttpLoader {
Expand All @@ -31,6 +37,7 @@ export function HttpLoaderFactory(http: HttpClient): TranslateHttpLoader {
CoreModule,
SharedModule,
HomeModule,
ImportModule,
SettingsModule,
AppRoutingModule,
FontAwesomeModule,
Expand Down
118 changes: 97 additions & 21 deletions src/app/core/services/domain.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,7 @@ import { SettingsService } from './settings.service';
@Injectable({
providedIn: 'root'
})
export class DomainService {

export class DomainService {
private packages: Package[];
private downloadSub: Subscription;
private downloadUpdateSub: Subscription;
Expand All @@ -25,7 +24,7 @@ export class DomainService {
private githubService: GithubService,
private downloaderService: DownloaderService,
private extractorService: ExtractorService,
private settingsService: SettingsService
private settingsService: SettingsService
) {
this.downloadSub = downloaderService.fileDownloaded.subscribe(r => {
if (r) {
Expand Down Expand Up @@ -53,7 +52,11 @@ export class DomainService {
let pipeline: Promise<any> = Promise.resolve(true);
packages.forEach(x => {
pipeline = pipeline.then(() => {
return this.analysePackage(x);
return this.analysePackage(x)
.catch(err => {
console.error(err);
x.state = InstallStatusEnum.error;
});
});
});
return pipeline;
Expand All @@ -65,26 +68,37 @@ export class DomainService {

return Promise.all([localPromise, githubPromise])
.then(result => {
p.localVersion = result[0].version;
p.availableVersion = result[1].availableVersion;
p.assetDownloadUrl = result[1].downloadUrl;
p.state = this.getState(p, result[0], result[1]);
p.publishedAt = result[1].publishedAt;
const local = result[0];
const remote = result [1];

if(local){
p.localVersion = local.version;
}

if(remote) {
p.availableVersion = remote.availableVersion;
p.assetDownloadUrl = remote.downloadUrl;
p.publishedAt = remote.publishedAt;
}

p.state = this.getState(p, local, remote);
});
}

private getState(p: Package, local: LocalState, info: PackageInfo): InstallStatusEnum {
if (p.state === InstallStatusEnum.downloading) return InstallStatusEnum.downloading;
if (p.state === InstallStatusEnum.extracting) return InstallStatusEnum.extracting;
if (p.state === InstallStatusEnum.installing) return InstallStatusEnum.installing;
if (p.state === InstallStatusEnum.installing) return InstallStatusEnum.installing;

if (local.untrackedFolderFound) return InstallStatusEnum.untrackedPackageFound;
if (!local.folderFound) return InstallStatusEnum.notFound;
if (local.version && info.availableVersion) {
if (local && local.untrackedFolderFound) return InstallStatusEnum.untrackedPackageFound;
if (local && !local.folderFound) return InstallStatusEnum.notFound;
if (local && local.version && info && info.availableVersion) {
if (local.version === info.availableVersion) return InstallStatusEnum.installed;
if (local.version !== info.availableVersion) return InstallStatusEnum.updateAvailable;
}
return InstallStatusEnum.notFound;

if (p.state === InstallStatusEnum.error) return InstallStatusEnum.error;
return InstallStatusEnum.unknown;
}

private processDownloadedFile(r: FileDownloadInfo): void {
Expand Down Expand Up @@ -143,16 +157,78 @@ export class DomainService {
this.app.tick();
}

getPackages(): Promise<Package[]> {
getPackages(): Package[] {
if (this.packages) {
return Promise.resolve(this.packages);
return this.packages;
}

return this.packageService.getPackages()
.then(p => {
this.packages = p;
return p;
});
this.packages = this.packageService.getPackages();
return this.packages;
}

addCustomPackage(p: Package): void {
if(!this.packages) {
this.getPackages();
}

this.packages.forEach(x => x.isSelected = false);

const settings = this.settingsService.getSettings();
settings.customPackages.push(p);
this.settingsService.saveSettings(settings);

this.packages.unshift(p);
p.state = InstallStatusEnum.unknown;
p.isCustomPackage = true;
p.isSelected = true;
this.analysePackage(p);
}

updateCustomPackage(p: Package): void {
if(!p) return;

const settings = this.settingsService.getSettings();
const toUpdate = settings.customPackages.find(x => x.id === p.id);

toUpdate.id = p.id;
toUpdate.name = p.name;
toUpdate.description = p.description;
toUpdate.summary = p.summary;
toUpdate.githubOwner = p.githubOwner;
toUpdate.githubRepo = p.githubRepo;
toUpdate.assetName = p.assetName;
toUpdate.isPrerelease = p.isPrerelease;
toUpdate.folderName = p.folderName;
toUpdate.illustration = p.illustration;
toUpdate.webpageUrl = p.webpageUrl;
toUpdate.versionPatternToRemove = p.versionPatternToRemove;

this.settingsService.saveSettings(settings);

const localToUpdate = this.packages.find(x => x.id === p.id);

localToUpdate.id = p.id;
localToUpdate.name = p.name;
localToUpdate.description = p.description;
localToUpdate.summary = p.summary;
localToUpdate.githubOwner = p.githubOwner;
localToUpdate.githubRepo = p.githubRepo;
localToUpdate.assetName = p.assetName;
localToUpdate.isPrerelease = p.isPrerelease;
localToUpdate.folderName = p.folderName;
localToUpdate.illustration = p.illustration;
localToUpdate.webpageUrl = p.webpageUrl;
localToUpdate.versionPatternToRemove = p.versionPatternToRemove;
}

removeCustomPackage(p: Package): void {
if(!p) return;

const settings = this.settingsService.getSettings();
settings.customPackages = settings.customPackages.filter(x => x.id !== p.id);
this.settingsService.saveSettings(settings);

this.packages = this.packages.filter(x => x.id !== p.id);
}

install(p: Package): void {
Expand Down
12 changes: 10 additions & 2 deletions src/app/core/services/github.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,14 +11,17 @@ export class GithubService {
constructor(private http: HttpClient) { }

retrievePackageInfo(p: Package): Promise<PackageInfo> {
const route = `https://api.github.com/repos/${p.githubOwner}/${p.githubRepo}/releases`;
const route = `https://api.github.com/repos/${p.githubOwner}/${p.githubRepo}/releases?per_page=100`;
return this.http.get<GithubRelease[]>(route).toPromise()
.then((rel: GithubRelease[]) => {
const lastRelease = rel
.sort((a, b) => {
return new Date(b.published_at).getTime() - new Date(a.published_at).getTime();
})
.find(x => this.isCandidate(x, p));

if(!lastRelease) return null;

const asset = lastRelease.assets.find(y => y.name.includes(p.assetName));

let downloadUrl = lastRelease.zipball_url;
Expand All @@ -32,8 +35,13 @@ export class GithubService {
}

private isCandidate(rel: GithubRelease, p: Package): boolean {
let keepPrerelease = false;
if(p.isPrerelease) {
keepPrerelease = true;
}

return rel.draft === false
&& rel.prerelease === false
&& rel.prerelease === keepPrerelease
&& (!p.assetName || rel.assets.findIndex(y => y.name.includes(p.assetName)) !== -1);
}
}
Expand Down
102 changes: 47 additions & 55 deletions src/app/core/services/packages.service.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,15 @@
import { Injectable } from '@angular/core';
import { SettingsService } from './settings.service';

@Injectable({
providedIn: 'root'
})
export class PackagesService {
constructor() { }
constructor(
private settingsService: SettingsService
) { }

getPackages(): Promise<Package[]> {
getPackages(): Package[] {
const wtcj4 = new Package();
wtcj4.id = "wt-cj4";
wtcj4.name = "WT CJ4";
Expand All @@ -19,7 +22,7 @@ export class PackagesService {
wtcj4.versionPatternToRemove = "cj4-";
wtcj4.state = InstallStatusEnum.unknown;
wtcj4.summary = "OPEN BETA<br/>Performance and avionics improvements for the Citation CJ4";
wtcj4.webpageUrl = "https://www.workingtitle.aero/packages/cj4/";
wtcj4.webpageUrl = "https://www.workingtitle.aero/packages/cj4/";

const wtg1000 = new Package();
wtg1000.id = "wt-g1000";
Expand Down Expand Up @@ -49,6 +52,21 @@ export class PackagesService {
wtg3000.summary = "Fixes and enhancements for the stock G3000 avionics package";
wtg3000.webpageUrl = "https://www.workingtitle.aero/packages/g3000/";

const wtg3x = new Package();
wtg3x.id = "wt-g3x";
wtg3x.name = "WT G3X";
wtg3x.description = "Working Title G3X Touch";
wtg3x.githubOwner = "Working-Title-MSFS-Mods";
wtg3x.githubRepo = "fspackages";
wtg3x.illustration = "assets/illustrations/g3x.jpg";
wtg3x.folderName = "workingtitle-gx";
wtg3x.assetName = "workingtitle-gx-v";
wtg3x.versionPatternToRemove = "gx-";
wtg3x.state = InstallStatusEnum.unknown;
wtg3x.summary = "This is an early release of what is intended to eventually be the reworking of several of the smaller Garmin units in the game.<br/><br/>At the moment the only thing that has been updated is the G3X Touch, but future modifications to the non-touch G3X, and to the touch-based Aera which uses much of the same code, are possible.";
wtg3x.webpageUrl = "https://www.workingtitle.aero/packages/g3x/";
wtg3x.isPrerelease = true;

const a32nx = new Package();
a32nx.id = "a32nx";
a32nx.name = "FBW A32NX";
Expand All @@ -62,17 +80,6 @@ export class PackagesService {
a32nx.summary = "The A32NX Project is a community-driven open source project to create a free Airbus A320neo in Microsoft Flight Simulator that is as close to reality as possible.<br/><br/>The following aircraft configuration is currently simulated:<br/><br/>Model&emsp;&emsp;A320-251N<br/>Engine&emsp;&emsp;CFM LEAP 1A-26<br/>FMGS&emsp;&emsp;Honeywell Pegasus II<br/>FWC Std.&emsp;&emsp;H2F9C<br/><br/>Please note that this configuration may change in the future as the A32NX project evolves and changes.";
a32nx.webpageUrl = "https://flybywiresim.com/";

// const wtg3x = new Package();
// wtg3x.id = "wt-g3x";
// wtg3x.name = "WT G3X";
// wtg3x.description = "Working Title G3X Touch";
// wtg3x.githubOwner = "Working-Title-MSFS-Mods";
// wtg3x.githubRepo = "fspackages";
// wtg3x.illustration = "assets/illustrations/aa.jpg";
// wtg3x.folderName = "workingtitle-g3000";
// wtg3x.assetName = "workingtitle-g3000-v";
// wtg3x.state = InstallStatusEnum.unknown;

const b787xe = new Package();
b787xe.id = "b787xe";
b787xe.name = "HD B78XH";
Expand Down Expand Up @@ -133,47 +140,29 @@ export class PackagesService {
jplc152.assetName = "jplogistics-c152-";
jplc152.state = InstallStatusEnum.unknown;
jplc152.summary = "A MSFS Addon to improve the Cessna C152 ";

const pms50gns530 = new Package();
pms50gns530.id = "pms50gns530";
pms50gns530.name = "PMS50 GNS530";
pms50gns530.description = "Pimarc PMS50 GNS530";
pms50gns530.githubOwner = "pimarc";
pms50gns530.githubRepo = "pms50-gns530";
pms50gns530.illustration = "assets/illustrations/pms50gns530.jpg";
pms50gns530.folderName = "pms50-gns530";
pms50gns530.assetName = "pms50-gns530.zip";
pms50gns530.state = InstallStatusEnum.unknown;
pms50gns530.summary = "This package is an enhancement of the built-in GNS530 GPS. The goal is to offer an instrument that comes as close as possible to the original.";

return Promise.resolve([wtcj4, wtg1000, wtg3000, a32nx, b787xe, salty747, aa, tfg36p, jplc152]);

// new Package();
// "aa-liv",
// "AA Liveries",
// "Azghar Airline Liveries",
// InstallStatusEnum.installed,
// null,
// "1.0.0",
// "dites33",
// "aa",
// null,
// "url",
// "assets/illustrations/aa.jpg",
// true
// ),
// new Package(
// "wt-cj4",
// "WT CJ4",
// "Working Title CJ4",
// InstallStatusEnum.notFound,
// null,
// "1.0.0",
// "url",
// "assets/illustrations/aa.jpg",
// false
// ),
// new Package(
// "aa-liv-3",
// "AA Liveries",
// "Azghar Airline Liveries",
// InstallStatusEnum.updateAvailable,
// null,
// "1.0.0",
// "url",
// "assets/illustrations/aa.jpg",
// false
// )

// ]);
const packages = [wtcj4, wtg1000, wtg3000, wtg3x, a32nx, b787xe, salty747, aa, tfg36p, jplc152, pms50gns530];
const customPackages = this.settingsService.getSettings().customPackages;

for (const p of customPackages) {
p.isCustomPackage = true;
p.state = InstallStatusEnum.unknown;
packages.unshift(p);
}

return packages;
}
}

Expand All @@ -189,6 +178,7 @@ export class Package {
public githubOwner: string;
public githubRepo: string;
public assetName: string;
public isPrerelease: boolean;
public versionPatternToRemove: string;
public folderName: string;
public assetDownloadUrl: string;
Expand All @@ -201,7 +191,9 @@ export class Package {

public summary: string;
public webpageUrl: string;
public oldFolderNames: string[]; //TODO
public oldFolderNames: string[];

public isCustomPackage: boolean;
}

export enum InstallStatusEnum {
Expand Down
Loading

0 comments on commit df0bbb3

Please sign in to comment.