From da92026e3bba783dad0897e246d90fe77323bca9 Mon Sep 17 00:00:00 2001 From: Cody Tolene Date: Fri, 29 Jul 2022 14:27:47 -0500 Subject: [PATCH 01/10] Pre-render content in model before display to speed things up. Also add loading template --- package-lock.json | 2 +- package.json | 2 +- src/app/public/ngx-gist-content.pipe.ts | 10 --- src/app/public/ngx-gist-file-filter.pipe.ts | 28 +++++-- src/app/public/ngx-gist.component.ts | 59 ++++++-------- src/app/public/ngx-gist.model.ts | 88 +++++++++++++++------ src/app/public/ngx-gist.module.ts | 3 +- src/app/public/ngx-gist.service.ts | 4 +- 8 files changed, 114 insertions(+), 82 deletions(-) delete mode 100644 src/app/public/ngx-gist-content.pipe.ts diff --git a/package-lock.json b/package-lock.json index 6c82d78..96c1246 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,6 +1,6 @@ { "name": "@proangular/ngx-gist", - "version": "1.0.2", + "version": "1.0.3", "lockfileVersion": 2, "requires": true, "packages": { diff --git a/package.json b/package.json index c8cf039..857ac77 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "@proangular/ngx-gist", - "version": "1.0.2", + "version": "1.0.3", "description": "An Angular Material and HighlighJs styled display box for GitHub gist and local code snippets.", "author": "Pro Angular ", "homepage": "https://www.proangular.com", diff --git a/src/app/public/ngx-gist-content.pipe.ts b/src/app/public/ngx-gist-content.pipe.ts deleted file mode 100644 index a752dfb..0000000 --- a/src/app/public/ngx-gist-content.pipe.ts +++ /dev/null @@ -1,10 +0,0 @@ -import { NgxGist } from './ngx-gist.model'; -import { Pipe, PipeTransform } from '@angular/core'; - -@Pipe({ name: 'gistContent' }) -export class GistContentPipe implements PipeTransform { - public transform(value: NgxGist, key: string): string { - const file = value.files[key]; - return file.content; - } -} diff --git a/src/app/public/ngx-gist-file-filter.pipe.ts b/src/app/public/ngx-gist-file-filter.pipe.ts index c246558..a4b6637 100644 --- a/src/app/public/ngx-gist-file-filter.pipe.ts +++ b/src/app/public/ngx-gist-file-filter.pipe.ts @@ -1,22 +1,34 @@ import { NgxGist } from './ngx-gist.model'; import { Pipe, PipeTransform } from '@angular/core'; +import { isStringArray } from './ngx-gist.utilities'; +import { isNonEmptyString } from 'dist/npm'; @Pipe({ name: 'gistFileFilter' }) export class GistFileFilterPipe implements PipeTransform { public transform( - files: NgxGist['files'] | null, - displayOnlyFileName?: string | null, - ): NgxGist['files'] { + files: NgxGist['highlightedFiles'] | null, + displayOnlyFileNames?: string | readonly string[] | null, + ): NgxGist['highlightedFiles'] { if (!files) { - return {}; + return []; } - if (!displayOnlyFileName) { + if (!displayOnlyFileNames || displayOnlyFileNames === '') { return files; } - return { - [displayOnlyFileName]: files[displayOnlyFileName], - }; + if (isNonEmptyString(displayOnlyFileNames)) { + return ( + files.filter(({ filename }) => displayOnlyFileNames === filename) ?? [] + ); + } + + if (isStringArray(displayOnlyFileNames)) { + return files.filter(({ filename }) => + displayOnlyFileNames.includes(filename), + ); + } + + return files; } } diff --git a/src/app/public/ngx-gist.component.ts b/src/app/public/ngx-gist.component.ts index 0f1e3a8..2b54137 100644 --- a/src/app/public/ngx-gist.component.ts +++ b/src/app/public/ngx-gist.component.ts @@ -2,8 +2,8 @@ import { NgxGistService } from './ngx-gist.service'; import { isNonEmptyValue } from './ngx-gist.utilities'; import { NgxGist } from './ngx-gist.model'; import { Component, Inject, Input, OnInit } from '@angular/core'; -import { Language, default as hljs } from 'highlight.js'; -import { filter, firstValueFrom, ReplaySubject } from 'rxjs'; +import { Language } from 'highlight.js'; +import { BehaviorSubject, filter, firstValueFrom, ReplaySubject } from 'rxjs'; import { UntilDestroy, untilDestroyed } from '@ngneat/until-destroy'; import { DOCUMENT } from '@angular/common'; @@ -12,18 +12,16 @@ import { DOCUMENT } from '@angular/common'; selector: 'ngx-gist', template: ` - - +
-            
+            
           
@@ -36,6 +34,7 @@ import { DOCUMENT } from '@angular/common'; link Open Gist on GitHub + Loading Code Snippet...
`, styleUrls: ['./ngx-gist.component.scss'], @@ -66,12 +65,13 @@ export class NgxGistComponent implements OnInit { * * Default: `undefined` */ - @Input() public gist?: NgxGist; - // We want reactive behavior for `gistId` so we can update gists asynchronously - private readonly gistIdSubject = new ReplaySubject< - NgxGistComponent['gistId'] - >(1); - public readonly gistIdChanges = this.gistIdSubject.asObservable(); + @Input() public set gist(value: NgxGist | undefined) { + this.gistSubject.next(value); + } + private readonly gistSubject = new BehaviorSubject( + undefined, + ); + public readonly gistChanges = this.gistSubject.asObservable(); /** * Provide the GitHub gist id to be fetched and loaded. This can be found in * URL of the gists you create. For example the id `TH1515th31DT0C0PY` in: @@ -82,6 +82,11 @@ export class NgxGistComponent implements OnInit { @Input() public set gistId(value: string) { this.gistIdSubject.next(value); } + // We want reactive behavior for `gistId` so we can update gists asynchronously + private readonly gistIdSubject = new ReplaySubject< + NgxGistComponent['gistId'] + >(1); + public readonly gistIdChanges = this.gistIdSubject.asObservable(); /** * When defined, override automatic language detection [and styling] and * treat all gists as this lanuage. @@ -137,31 +142,17 @@ export class NgxGistComponent implements OnInit { }); } - // TODO: Work on speeding this call up. Or possibly pre-render instead. - public getHighlightJsContent(value: string): string { - const userSpecifiedLanguage = this.languageName; - if (userSpecifiedLanguage) { - return hljs.highlight(value, { language: userSpecifiedLanguage }).value; - } - - return hljs.highlightAuto(value).value; - } - private async fetchAndSetGist(gistId: string): Promise { - // Use the initial gist model as a fallback for a failed fetch. This - // enables us to have a fallback gist snippet should we be offline or - // the data is unavailable for some reason. - const initialGist = this.gist ? { ...this.gist } : undefined; - // Fetch and hydrate model or fallback to initial gist. - this.gist = - (await firstValueFrom(this.ngxGistService.get(gistId))) ?? initialGist; + const fetcheGist = + (await firstValueFrom(this.ngxGistService.get(gistId))) ?? undefined; + this.gist = fetcheGist; - if (this.useCache && this.gist) { + if (this.useCache && fetcheGist) { // Set value in cache for reuse saving on the amount of HTTP requests. // Set refresh time to be a hard coded 24 hours. This was once configurable // but I decided against it for simplicities sake on ease of use. - this.ngxGistService.setToCache(this.gist, 1440); + this.ngxGistService.setToCache(fetcheGist, 1440); } } diff --git a/src/app/public/ngx-gist.model.ts b/src/app/public/ngx-gist.model.ts index 40e290f..f65b7b5 100644 --- a/src/app/public/ngx-gist.model.ts +++ b/src/app/public/ngx-gist.model.ts @@ -5,9 +5,10 @@ import { isNonEmptyString, parsedJsonFromStringCodec, } from './ngx-gist.utilities'; +import { default as hljs } from 'highlight.js'; export class NgxGist implements Gist { - public constructor(args: Gist) { + public constructor(args: Gist & Pick) { this.comments = args.comments; this.comments_url = args.comments_url; this.commits_url = args.commits_url; @@ -28,8 +29,23 @@ export class NgxGist implements Gist { this.updated_at = new Date(args.updated_at); this.url = args.url; this.user = args.user; + + // Additional properties + this.languageOverride = args.languageOverride; + const highlightedFiles: NgxGist['highlightedFiles'] = []; + for (const key in this.files) { + if (this.files[key]) { + const file = this.files[key]; + highlightedFiles.push({ + ...file, + highlightedContent: getHighlightedContent(file.content), + }); + } + } + this.highlightedFiles = highlightedFiles; } + /** Core gist properties */ /* eslint-disable @typescript-eslint/naming-convention */ public readonly comments: number; public readonly comments_url: string; @@ -53,23 +69,36 @@ export class NgxGist implements Gist { public readonly user?: unknown; /* eslint-enable @typescript-eslint/naming-convention */ + /** Additional properties */ + public readonly highlightedFiles: Array< + io.TypeOf & HighlightedContent + >; + public readonly languageOverride?: string; + /** * Create a local, static gist object. Do not use this for fetched data. * Used for creating and displaying local code samples. * + * Use `deserialize` sibling function for remote "unknown" responses. + * * @param args Minimally necessary paramaters for displaying local code. * @returns A 'partial' model in which unnecessary fields are dummny data. */ public static create( - args: Pick, + args: Pick & + Pick, ): NgxGist { return new NgxGist({ - comments: 0, - comments_url: '', - commits_url: '', + // Properties with settable values. These are the mimimum values needed + // for displaying non "remote". created_at: new Date(args.created_at), description: args.description, files: args.files, + languageOverride: args.languageOverride, + // Empty properties that aren't needed for displaying non "remote" gists + comments: 0, + comments_url: '', + commits_url: '', forks: [], forks_url: '', git_pull_url: '', @@ -88,7 +117,7 @@ export class NgxGist implements Gist { } /** - * Deserialize and decode fetched/unkown data into the full model. + * Deserialize and decode fetched/unknown data into the full model. * * @param value Unknown value, but expects a full model either by object or JSON string. * @returns Either the full model or null if deserialization fails. @@ -102,15 +131,30 @@ export class NgxGist implements Gist { ? decodeValueElseNull(gistFromJsonStringCodec)(value) : null); return decoded - ? { + ? new NgxGist({ ...decoded, created_at: new Date(decoded.created_at), updated_at: new Date(decoded.updated_at), - } + }) : null; } } +interface HighlightedContent { + highlightedContent: string; +} + +function getHighlightedContent( + baseContent: string, + languageOverride?: string, +): string { + if (languageOverride) { + return hljs.highlight(baseContent, { language: languageOverride }).value; + } + + return hljs.highlightAuto(baseContent).value; +} + const gitHubUserCodec = io.readonly( io.type({ avatar_url: io.string, @@ -155,21 +199,17 @@ const gistHistoryCodec = io.readonly( 'GistHistory', ); -const gistFilesCodec = io.readonly( - io.record( - io.string, - io.type({ - content: io.string, - filename: io.string, - language: io.string, - raw_url: io.string, - size: io.number, - truncated: io.boolean, - type: io.string, - }), - ), - 'GistFiles', -); +const gistFilesContent = io.type({ + content: io.string, + filename: io.string, + language: io.string, + raw_url: io.string, + size: io.number, + truncated: io.boolean, + type: io.string, +}); + +const gistFilesCodec = io.record(io.string, gistFilesContent); export const gistCodec = io.readonly( io.intersection([ @@ -207,7 +247,7 @@ const gistFromJsonStringCodec = parsedJsonFromStringCodec.pipe( ); /** - * Official Gist objecio. + * Official Gist object * https://docs.github.com/en/rest/gists */ type Gist = io.TypeOf; diff --git a/src/app/public/ngx-gist.module.ts b/src/app/public/ngx-gist.module.ts index 5ba1f08..5b61bd3 100644 --- a/src/app/public/ngx-gist.module.ts +++ b/src/app/public/ngx-gist.module.ts @@ -4,12 +4,11 @@ import { NgxGistComponent } from './ngx-gist.component'; import { NgxGistService } from './ngx-gist.service'; import { MatCardModule } from '@angular/material/card'; import { MatTabsModule } from '@angular/material/tabs'; -import { GistContentPipe } from './ngx-gist-content.pipe'; import { GistFileFilterPipe } from './ngx-gist-file-filter.pipe'; import { MatIconModule } from '@angular/material/icon'; @NgModule({ - declarations: [NgxGistComponent, GistContentPipe, GistFileFilterPipe], + declarations: [NgxGistComponent, GistFileFilterPipe], imports: [ // Needs to be imported at root. // BrowserAnimationsModule, diff --git a/src/app/public/ngx-gist.service.ts b/src/app/public/ngx-gist.service.ts index d58722b..5b325c1 100644 --- a/src/app/public/ngx-gist.service.ts +++ b/src/app/public/ngx-gist.service.ts @@ -61,11 +61,11 @@ export class NgxGistService { const gist = storedGist.value; // All is good, return unexpired gist - return { + return new NgxGist({ ...gist, created_at: new Date(gist.created_at), updated_at: new Date(gist.updated_at), - }; + }); } public setToCache(gist: NgxGist, expiresInMin?: number): void { From 6021761ed4f24b71a3c9818dd9ac25e7c7bc037a Mon Sep 17 00:00:00 2001 From: Cody Tolene Date: Fri, 29 Jul 2022 16:02:00 -0500 Subject: [PATCH 02/10] Wrap up additional features --- README.md | 2 +- src/app/app.component.ts | 79 ++++++++++++++++++--- src/app/public/ngx-gist-file-filter.pipe.ts | 2 + src/app/public/ngx-gist.component.ts | 50 ++++++++----- src/app/public/ngx-gist.model.ts | 36 +++++++--- 5 files changed, 131 insertions(+), 38 deletions(-) diff --git a/README.md b/README.md index e7ae1b5..bb2b486 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@

- +

diff --git a/src/app/app.component.ts b/src/app/app.component.ts index e80236b..831cb83 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -1,3 +1,4 @@ +import { NgxGist } from './public/ngx-gist.model'; import { Component } from '@angular/core'; @Component({ @@ -9,26 +10,82 @@ import { Component } from '@angular/core';

Examples of displaying local and GitHub gists and code snippets.

- + +
+ +

FETCHED GIST (AUTO CACHED FOR 24 HOURS)

- + +

FETCHED GIST (FORCED NO CACHE)

- + +

DISPLAYING ONE SPECIFIC FILE

+

Display only one specific file when your gist has many.

- - `, - styles: [], + styles: [ + ` + h2 { + margin-top: 2rem; + } + h3 { + margin-bottom: 3rem; + } + `, + ], }) -export class AppComponent {} +export class AppComponent { + public readonly localGistObject = NgxGist.create({ + // Required + files: [ + { + content: getTimeSnippet, + filename: 'get-time.ts', + }, + { + content: printHelloWorldSnippet, + filename: 'print-hello-world.js', + }, + ], + // Optional + created_at: undefined, + languageOverride: undefined, + }); +} + +const getTimeSnippet = ` +function getTime(): number { + return new Date().getTime(); +} +`.trimStart(); + +const printHelloWorldSnippet = ` +function printHelloWorld() { + console.log('Hello world!'); +} +`.trimStart(); diff --git a/src/app/public/ngx-gist-file-filter.pipe.ts b/src/app/public/ngx-gist-file-filter.pipe.ts index a4b6637..7efa9a4 100644 --- a/src/app/public/ngx-gist-file-filter.pipe.ts +++ b/src/app/public/ngx-gist-file-filter.pipe.ts @@ -13,6 +13,8 @@ export class GistFileFilterPipe implements PipeTransform { return []; } + console.log(displayOnlyFileNames); + if (!displayOnlyFileNames || displayOnlyFileNames === '') { return files; } diff --git a/src/app/public/ngx-gist.component.ts b/src/app/public/ngx-gist.component.ts index 2b54137..32dbe05 100644 --- a/src/app/public/ngx-gist.component.ts +++ b/src/app/public/ngx-gist.component.ts @@ -16,7 +16,7 @@ import { DOCUMENT } from '@angular/common'; @@ -25,16 +25,18 @@ import { DOCUMENT } from '@angular/common'; - + +
link Open Gist on GitHub - Loading Code Snippet... + + Loading Code Snippet... `, styleUrls: ['./ngx-gist.component.scss'], @@ -50,13 +52,23 @@ export class NgxGistComponent implements OnInit { private htmlLinkElement: HTMLLinkElement | null = null; /** - * Display in the DOM only the selected filename from the gists files array. - * - * TODO: Make this possible for string array input. + * Display in the DOM only the selected filename(s) from the gists files array. * * Default: `undefined` + * + * Example: `'my-styles.scss'` or `'super-feature.ts'` + * + * Tip: Can be either a string or string array. File names much match exactly, + * be sure to remove any leading or trailing whitespace in the provided strings. + */ + @Input() public displayOnlyFileNames?: string | readonly string[]; + /** + * Optionally hide the gist link which opens the gist on GitHub. The gist links + * automatically dispaly for remote gists, but can be hidden with this feature. + * + * Default: `false` */ - @Input() public displayOnlyFileName?: string; + @Input() public hideGistLink = false; /** * Provide a static gist model here directly which will be displayed if * no `gistId` is provided for remote fetching. Also this model will be @@ -77,12 +89,13 @@ export class NgxGistComponent implements OnInit { * URL of the gists you create. For example the id `TH1515th31DT0C0PY` in: * https://gist.github.com/FakeUserName/TH1515th31DT0C0PY * - * Alternatively, provide a value directly in the sibling input `gist`. + * Default: `undefined` + * + * Tip: Alternatively, provide a value directly in the sibling input `gist`. */ @Input() public set gistId(value: string) { this.gistIdSubject.next(value); } - // We want reactive behavior for `gistId` so we can update gists asynchronously private readonly gistIdSubject = new ReplaySubject< NgxGistComponent['gistId'] >(1); @@ -91,22 +104,23 @@ export class NgxGistComponent implements OnInit { * When defined, override automatic language detection [and styling] and * treat all gists as this lanuage. * - * See supported languages here: - * https://github.com/highlightjs/highlight.js/blob/main/SUPPORTED_LANGUAGES.md - * * Default: `undefined` + * + * Tip: See supported language strings here: + * https://github.com/highlightjs/highlight.js/blob/main/SUPPORTED_LANGUAGES.md */ @Input() public languageName?: Language['name']; /** * Define a material core theme to apply. Ideally, you should already have * your global material theme set at the root of your project so try to - * avoid using this if possible. Note: These are also loaded from a CDN. + * avoid using this if possible. * - * See theming Angular Material: https://material.angular.io/guide/theming - * - * CDN used: `https://unpkg.com` + * Note: These are loaded from the CDN: `https://unpkg.com` * * Default: `undefined` + * + * Tip: See theming Angular Material: https://material.angular.io/guide/theming + * if you need help applying a global material theme. */ @Input() public materialTheme: | 'deeppurple-amber' @@ -117,7 +131,7 @@ export class NgxGistComponent implements OnInit { /** * Cache the GitHub gist request in local memory for 24 hours. GitHub has a * request limit, so this helps in reducing bandwidth. Loads previously - * fetched gist content from the users machine. + * fetched gist content from the users machine on refresh and page re-visits. * * Default: `true` */ diff --git a/src/app/public/ngx-gist.model.ts b/src/app/public/ngx-gist.model.ts index f65b7b5..f072d94 100644 --- a/src/app/public/ngx-gist.model.ts +++ b/src/app/public/ngx-gist.model.ts @@ -70,9 +70,7 @@ export class NgxGist implements Gist { /* eslint-enable @typescript-eslint/naming-convention */ /** Additional properties */ - public readonly highlightedFiles: Array< - io.TypeOf & HighlightedContent - >; + public readonly highlightedFiles: HighlightedFiles; public readonly languageOverride?: string; /** @@ -85,15 +83,32 @@ export class NgxGist implements Gist { * @returns A 'partial' model in which unnecessary fields are dummny data. */ public static create( - args: Pick & - Pick, + args: { files: Files } & Partial> & // Required // Optional + Pick, // Optional ): NgxGist { + const files: NgxGist['files'] = args.files.reduce((prev, curr) => { + const file: GistFilesContent = { + // Passed in values, use these. + content: curr.content, + filename: curr.filename, + // Leave these empty, not needed for a local, static model. + language: '', + raw_url: '', + size: 0, + truncated: false, + type: '', + }; + return { + ...prev, + [curr.filename]: file, + }; + }, {}); return new NgxGist({ // Properties with settable values. These are the mimimum values needed // for displaying non "remote". - created_at: new Date(args.created_at), - description: args.description, - files: args.files, + created_at: args.created_at ? new Date(args.created_at) : new Date(), + description: args.description ?? '', + files, languageOverride: args.languageOverride, // Empty properties that aren't needed for displaying non "remote" gists comments: 0, @@ -140,6 +155,10 @@ export class NgxGist implements Gist { } } +type Files = Array>; + +type HighlightedFiles = Array; + interface HighlightedContent { highlightedContent: string; } @@ -208,6 +227,7 @@ const gistFilesContent = io.type({ truncated: io.boolean, type: io.string, }); +type GistFilesContent = io.TypeOf; const gistFilesCodec = io.record(io.string, gistFilesContent); From 2fc669028984e9ac88d241dce303fb67468438d1 Mon Sep 17 00:00:00 2001 From: Cody Tolene Date: Fri, 29 Jul 2022 22:10:54 -0500 Subject: [PATCH 03/10] Add line numbers --- package-lock.json | 15 ++++- package.json | 1 + src/app/app.component.ts | 20 ++++++ src/app/public/ngx-gist-file-filter.pipe.ts | 2 - .../public/ngx-gist-line-numbers.service.ts | 61 +++++++++++++++++++ src/app/public/ngx-gist-theme.service.ts | 37 +++++++++++ src/app/public/ngx-gist.component.ts | 60 ++++++++++++------ src/app/public/ngx-gist.model.ts | 12 +++- src/app/public/ngx-gist.module.ts | 4 +- 9 files changed, 186 insertions(+), 26 deletions(-) create mode 100644 src/app/public/ngx-gist-line-numbers.service.ts create mode 100644 src/app/public/ngx-gist-theme.service.ts diff --git a/package-lock.json b/package-lock.json index 96c1246..1cc5c40 100644 --- a/package-lock.json +++ b/package-lock.json @@ -6,7 +6,7 @@ "packages": { "": { "name": "@proangular/ngx-gist", - "version": "1.0.0", + "version": "1.0.3", "hasInstallScript": true, "license": "MIT", "devDependencies": { @@ -63,6 +63,7 @@ "@angular/platform-browser": ">=12 <15", "@ngneat/until-destroy": "^9.2.1", "highlight.js": "^11.6.0", + "highlightjs-line-numbers.js": "^2.8.0", "io-ts": "^2.2.17", "io-ts-types": "^0.5.16" } @@ -8054,6 +8055,12 @@ "node": ">=12.0.0" } }, + "node_modules/highlightjs-line-numbers.js": { + "version": "2.8.0", + "resolved": "https://registry.npmjs.org/highlightjs-line-numbers.js/-/highlightjs-line-numbers.js-2.8.0.tgz", + "integrity": "sha512-TEf1gw0c8mb8nan0QwliqS7obT4cpUd9hzsGzsZLweteNnWea/VIqy5/aQqsa5wnz9lnvmtAkS1ZtDTjB/goYQ==", + "peer": true + }, "node_modules/hosted-git-info": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.0.0.tgz", @@ -20939,6 +20946,12 @@ "integrity": "sha512-ig1eqDzJaB0pqEvlPVIpSSyMaO92bH1N2rJpLMN/nX396wTpDA4Eq0uK+7I/2XG17pFaaKE0kjV/XPeGt7Evjw==", "peer": true }, + "highlightjs-line-numbers.js": { + "version": "2.8.0", + "resolved": "https://registry.npmjs.org/highlightjs-line-numbers.js/-/highlightjs-line-numbers.js-2.8.0.tgz", + "integrity": "sha512-TEf1gw0c8mb8nan0QwliqS7obT4cpUd9hzsGzsZLweteNnWea/VIqy5/aQqsa5wnz9lnvmtAkS1ZtDTjB/goYQ==", + "peer": true + }, "hosted-git-info": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-5.0.0.tgz", diff --git a/package.json b/package.json index 857ac77..8ea4629 100644 --- a/package.json +++ b/package.json @@ -32,6 +32,7 @@ "@angular/platform-browser": ">=12 <15", "@ngneat/until-destroy": "^9.2.1", "highlight.js": "^11.6.0", + "highlightjs-line-numbers.js": "^2.8.0", "io-ts": "^2.2.17", "io-ts-types": "^0.5.16" }, diff --git a/src/app/app.component.ts b/src/app/app.component.ts index 831cb83..dc144a9 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -14,9 +14,20 @@ import { Component } from '@angular/core';

FETCHED GIST (AUTO CACHED FOR 24 HOURS)

+

+ ngx-gist will fetch the gist once and store it locally for 24 hours. In + that timeframe if the user returns or visits another page where this + gist was previously loaded, it will reload the content without having to + reach out to GitHub again. +

FETCHED GIST (FORCED NO CACHE)

+

+ Force no cache. This will force ngx-gist to retrieve the content live + from GitHub every time this content loads. This is disabled by default, + but could be useful if your gists change frequently. +

+ +

HIDING LINE NUMBERS

+

+ Line numbers are enabled by default, but you can turn them off like so. +

+ `, diff --git a/src/app/public/ngx-gist-file-filter.pipe.ts b/src/app/public/ngx-gist-file-filter.pipe.ts index 7efa9a4..a4b6637 100644 --- a/src/app/public/ngx-gist-file-filter.pipe.ts +++ b/src/app/public/ngx-gist-file-filter.pipe.ts @@ -13,8 +13,6 @@ export class GistFileFilterPipe implements PipeTransform { return []; } - console.log(displayOnlyFileNames); - if (!displayOnlyFileNames || displayOnlyFileNames === '') { return files; } diff --git a/src/app/public/ngx-gist-line-numbers.service.ts b/src/app/public/ngx-gist-line-numbers.service.ts new file mode 100644 index 0000000..0eb2453 --- /dev/null +++ b/src/app/public/ngx-gist-line-numbers.service.ts @@ -0,0 +1,61 @@ +import { DOCUMENT } from '@angular/common'; +import { Inject, Injectable } from '@angular/core'; +import hljs, { HLJSApi } from 'highlight.js'; +import { filter, map, Observable, firstValueFrom, from } from 'rxjs'; + +@Injectable({ providedIn: 'root' }) // Must be a singleton +export class NgxGistLineNumbersService { + public constructor(@Inject(DOCUMENT) private readonly document: Document) {} + private isLoaded = false; + + public async load(): Promise { + if (this.isLoaded) { + return; + } + + try { + if (this.document.defaultView) { + // Ensure hljs is available before we load the dependant library + // `highlightjs-line-numbers.js` dynamically as a js import. + this.document.defaultView.hljs = hljs; + } else { + throw new Error( + `Unable to access default view to apply "highlight.js" package.`, + ); + } + + firstValueFrom(this.loadHljsLineNumbersLibrary()).then(() => { + // The library `highlightjs-line-numbers.js` adds new functions to the + // `highlight.js` scope on load, so we should now be able to call it + // without failure. + // eslint-disable-next-line @typescript-eslint/no-non-null-assertion + this.document.defaultView?.hljs?.initLineNumbersOnLoad!(); + }); + } catch (e: unknown) { + console.log(e); + } finally { + this.isLoaded = true; + } + } + + /* eslint-disable @typescript-eslint/no-explicit-any */ + private loadHljsLineNumbersLibrary(): Observable { + return from(import('highlightjs-line-numbers.js' as any)).pipe( + filter((module: any) => !!module && !!module.default), + map((module: any) => module.default), + ); + } + /* eslint-enable @typescript-eslint/no-explicit-any */ +} + +declare global { + interface Window { + hljs?: HLJSApi & { + /* eslint-disable @typescript-eslint/no-explicit-any */ + initLineNumbersOnLoad?: (options?: any) => void; + lineNumbersBlock?: (value: Element, options?: any) => void; + lineNumbersValue?: (value: string, options?: any) => string; + /* eslint-enable @typescript-eslint/no-explicit-any */ + }; + } +} diff --git a/src/app/public/ngx-gist-theme.service.ts b/src/app/public/ngx-gist-theme.service.ts new file mode 100644 index 0000000..3f3b1a3 --- /dev/null +++ b/src/app/public/ngx-gist-theme.service.ts @@ -0,0 +1,37 @@ +import { Inject, Injectable } from '@angular/core'; +import { DOCUMENT } from '@angular/common'; + +@Injectable({ providedIn: 'root' }) // Must be a singleton +export class NgxGistThemeService { + public constructor(@Inject(DOCUMENT) private readonly document: Document) {} + + private importElMaterialTheme: HTMLLinkElement | null = null; + + public setTheme(materialPrebuiltTheme: MaterialPrebuiltTheme): void { + const themeId = 'material-theme-import'; + const currentEl = this.document.getElementById(themeId); + + if (currentEl) { + this.document.removeChild(currentEl); + } + + if (this.importElMaterialTheme) { + this.document.removeChild(this.importElMaterialTheme); + } + + this.importElMaterialTheme = this.document.createElement('link'); + this.importElMaterialTheme.href = `https://unpkg.com/@angular/material@14.1.0/prebuilt-themes/${materialPrebuiltTheme}.css`; + this.importElMaterialTheme.media = 'screen,print'; + this.importElMaterialTheme.rel = 'stylesheet'; + this.importElMaterialTheme.type = 'text/css'; + this.importElMaterialTheme.id = themeId; + + this.document.head.appendChild(this.importElMaterialTheme); + } +} + +export type MaterialPrebuiltTheme = + | 'deeppurple-amber' + | 'indigo-pink' + | 'pink-bluegrey' + | 'purple-green'; diff --git a/src/app/public/ngx-gist.component.ts b/src/app/public/ngx-gist.component.ts index 32dbe05..0e06e5e 100644 --- a/src/app/public/ngx-gist.component.ts +++ b/src/app/public/ngx-gist.component.ts @@ -6,6 +6,12 @@ import { Language } from 'highlight.js'; import { BehaviorSubject, filter, firstValueFrom, ReplaySubject } from 'rxjs'; import { UntilDestroy, untilDestroyed } from '@ngneat/until-destroy'; import { DOCUMENT } from '@angular/common'; +import { NgxGistLineNumbersService } from './ngx-gist-line-numbers.service'; +import { DomSanitizer, SafeHtml } from '@angular/platform-browser'; +import { + MaterialPrebuiltTheme, + NgxGistThemeService, +} from './ngx-gist-theme.service'; @UntilDestroy() @Component({ @@ -21,7 +27,13 @@ import { DOCUMENT } from '@angular/common'; [label]="file.filename" >
-            
+            
+            
+              Error loading code...
+            
           
@@ -43,14 +55,12 @@ import { DOCUMENT } from '@angular/common'; }) export class NgxGistComponent implements OnInit { public constructor( - @Inject(DOCUMENT) - private readonly document: Document, + @Inject(DOCUMENT) private readonly document: Document, + private readonly domSanitizer: DomSanitizer, private readonly ngxGistService: NgxGistService, + private readonly ngxGistLineNumbersService: NgxGistLineNumbersService, + private readonly ngxGistThemeService: NgxGistThemeService, ) {} - - public codeSnippet: string | null = null; - private htmlLinkElement: HTMLLinkElement | null = null; - /** * Display in the DOM only the selected filename(s) from the gists files array. * @@ -122,12 +132,13 @@ export class NgxGistComponent implements OnInit { * Tip: See theming Angular Material: https://material.angular.io/guide/theming * if you need help applying a global material theme. */ - @Input() public materialTheme: - | 'deeppurple-amber' - | 'indigo-pink' - | 'pink-bluegrey' - | 'purple-green' - | undefined = undefined; + @Input() public materialTheme: MaterialPrebuiltTheme | undefined = undefined; + /** + * Display or hide the line numbers in your gist code snippets. + * + * Default: `true` + */ + @Input() public showLineNumbers = true; /** * Cache the GitHub gist request in local memory for 24 hours. GitHub has a * request limit, so this helps in reducing bandwidth. Loads previously @@ -140,6 +151,10 @@ export class NgxGistComponent implements OnInit { public async ngOnInit(): Promise { this.setTheme(); + if (this.showLineNumbers) { + await this.ngxGistLineNumbersService.load(); + } + this.gistIdChanges .pipe(filter(isNonEmptyValue), untilDestroyed(this)) .subscribe(async (gistId) => { @@ -174,12 +189,19 @@ export class NgxGistComponent implements OnInit { if (!this.materialTheme) { return; } + this.ngxGistThemeService.setTheme(this.materialTheme); + } - this.htmlLinkElement = this.document.createElement('link'); - this.htmlLinkElement.href = `https://unpkg.com/@angular/material@14.1.0/prebuilt-themes/${this.materialTheme}.css`; - this.htmlLinkElement.media = 'screen,print'; - this.htmlLinkElement.rel = 'stylesheet'; - this.htmlLinkElement.type = 'text/css'; - this.document.head.appendChild(this.htmlLinkElement); + public applyLineNumbers(highlightedConent: string): SafeHtml | null { + if ( + this.showLineNumbers && + this.document.defaultView?.hljs && + typeof this.document.defaultView.hljs.lineNumbersValue === 'function' + ) { + return this.domSanitizer.bypassSecurityTrustHtml( + this.document.defaultView.hljs.lineNumbersValue(highlightedConent), + ); + } + return highlightedConent; } } diff --git a/src/app/public/ngx-gist.model.ts b/src/app/public/ngx-gist.model.ts index f072d94..a6033e9 100644 --- a/src/app/public/ngx-gist.model.ts +++ b/src/app/public/ngx-gist.model.ts @@ -5,7 +5,7 @@ import { isNonEmptyString, parsedJsonFromStringCodec, } from './ngx-gist.utilities'; -import { default as hljs } from 'highlight.js'; +import hljs from 'highlight.js'; export class NgxGist implements Gist { public constructor(args: Gist & Pick) { @@ -167,11 +167,17 @@ function getHighlightedContent( baseContent: string, languageOverride?: string, ): string { + let highlighted = baseContent; + if (languageOverride) { - return hljs.highlight(baseContent, { language: languageOverride }).value; + highlighted = hljs.highlight(baseContent, { + language: languageOverride, + }).value; + } else { + highlighted = hljs.highlightAuto(baseContent).value; } - return hljs.highlightAuto(baseContent).value; + return highlighted; } const gitHubUserCodec = io.readonly( diff --git a/src/app/public/ngx-gist.module.ts b/src/app/public/ngx-gist.module.ts index 5b61bd3..ee63c07 100644 --- a/src/app/public/ngx-gist.module.ts +++ b/src/app/public/ngx-gist.module.ts @@ -6,6 +6,8 @@ import { MatCardModule } from '@angular/material/card'; import { MatTabsModule } from '@angular/material/tabs'; import { GistFileFilterPipe } from './ngx-gist-file-filter.pipe'; import { MatIconModule } from '@angular/material/icon'; +import { NgxGistLineNumbersService } from './ngx-gist-line-numbers.service'; +import { NgxGistThemeService } from './ngx-gist-theme.service'; @NgModule({ declarations: [NgxGistComponent, GistFileFilterPipe], @@ -20,6 +22,6 @@ import { MatIconModule } from '@angular/material/icon'; MatTabsModule, ], exports: [NgxGistComponent], - providers: [NgxGistService], + providers: [NgxGistLineNumbersService, NgxGistService, NgxGistThemeService], }) export class NgxGistModule {} From 81147b3c03e39af6a188ecbe866b6e2306039f52 Mon Sep 17 00:00:00 2001 From: Cody Tolene Date: Fri, 29 Jul 2022 22:19:21 -0500 Subject: [PATCH 04/10] Tweak line number service --- src/app/public/ngx-gist-line-numbers.service.ts | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/src/app/public/ngx-gist-line-numbers.service.ts b/src/app/public/ngx-gist-line-numbers.service.ts index 0eb2453..1c3835f 100644 --- a/src/app/public/ngx-gist-line-numbers.service.ts +++ b/src/app/public/ngx-gist-line-numbers.service.ts @@ -9,7 +9,11 @@ export class NgxGistLineNumbersService { private isLoaded = false; public async load(): Promise { - if (this.isLoaded) { + if ( + this.isLoaded || + typeof this.document.defaultView?.hljs?.initLineNumbersOnLoad === + 'function' + ) { return; } @@ -24,7 +28,7 @@ export class NgxGistLineNumbersService { ); } - firstValueFrom(this.loadHljsLineNumbersLibrary()).then(() => { + await firstValueFrom(this.loadHljsLineNumbersLibrary()).then(() => { // The library `highlightjs-line-numbers.js` adds new functions to the // `highlight.js` scope on load, so we should now be able to call it // without failure. From 7296333c342d3b2b7242d611728c1f9d4f2dec21 Mon Sep 17 00:00:00 2001 From: Cody Tolene Date: Fri, 29 Jul 2022 22:40:19 -0500 Subject: [PATCH 05/10] Fix up incorrect import on build fail --- src/app/public/ngx-gist-file-filter.pipe.ts | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/app/public/ngx-gist-file-filter.pipe.ts b/src/app/public/ngx-gist-file-filter.pipe.ts index a4b6637..a9fe88e 100644 --- a/src/app/public/ngx-gist-file-filter.pipe.ts +++ b/src/app/public/ngx-gist-file-filter.pipe.ts @@ -1,7 +1,6 @@ import { NgxGist } from './ngx-gist.model'; import { Pipe, PipeTransform } from '@angular/core'; -import { isStringArray } from './ngx-gist.utilities'; -import { isNonEmptyString } from 'dist/npm'; +import { isNonEmptyString, isStringArray } from './ngx-gist.utilities'; @Pipe({ name: 'gistFileFilter' }) export class GistFileFilterPipe implements PipeTransform { From 5efa79be46d0be929cb16eaea957980619fd75a8 Mon Sep 17 00:00:00 2001 From: Cody Tolene Date: Sat, 30 Jul 2022 00:01:13 -0500 Subject: [PATCH 06/10] Update layout and documentation --- README.md | 147 ++++++++++++++++++++++++++- src/app/app.component.ts | 6 +- src/app/app.module.ts | 4 + src/app/layout/body.component.ts | 1 + src/app/layout/header.component.ts | 52 ++++++++-- src/app/public/ngx-gist.component.ts | 6 +- src/assets/images/git-hub.svg | 35 +++++++ src/styles.scss | 1 + 8 files changed, 238 insertions(+), 14 deletions(-) create mode 100644 src/assets/images/git-hub.svg diff --git a/README.md b/README.md index bb2b486..9f06dbd 100644 --- a/README.md +++ b/README.md @@ -5,7 +5,7 @@

Pro Angular - : GitHub gist Code Snippet Display + : GitHub gist Code Snippet Tabs

@@ -17,8 +17,149 @@ # Description -An Angular Material and HighlighJs styled display box for GitHub gist and local code snippets. +An Angular Material and HighlighJs styled display box for GitHub gist and local code snippets. All files from the remote/local gist are displayed in separate tabs for users to easily navigate. Many optional features and themes are available. Enjoy! # Demo -TODO: Further documentation. +TODO: Add demo here. + +# Requirements + +This project uses Angular Material tabs so an Angular Material must be installed and available along with a theme. You can define a theme if you use this application outside of Angular using the public API `materialTheme` (see below for more information). See other peer dependancies in the package description. + +# Installation + +```bash +ng add @proangular/ngx-gist@latest +``` +or +```bash +npm install @proangular/ngx-gist --save +``` + +Import `NgxGistModule` where needed +```diff +... ++ import { NgxGistModule } from '@proangular/ngx-gist'; +... + +@NgModule({ + imports: [ + ... ++ NgxGistModule + ], + ... +}) +export class AppModule { } +``` + +# Usage + +### Default - fetched gist (auto cached for 24 hours) + +ngx-gist will fetch the gist once and store it locally for 24 hours. In that timeframe, if the user returns or visits another page where this gist was previously loaded, it will reload the content without having to reach out to GitHub again. +```html + +``` + +### Fetched gist (forced no cache) + +Force no cache. This will force ngx-gist to retrieve the content live from GitHub every time this content loads. This is disabled by default, but could be useful if your gists change frequently. +```html + +``` + +### Displaying one specific file + +Display only one specific file when your gist has many. +```html + +``` + +### Displaying multiple, specific files + +Display only one specific file when your gist has many. +```html + +``` + +### Displaying a basic code snippet (without a remote gist) + +These are not fetched from GitHub and are brought in elsewhere from your application (seperate HTTP request, or statically for example). With this method you can display code snippets without having to create a remote gist. Also, please notice here that no "Open Gist on GitHub" link is displayed here. +```html + +``` + +### Hiding line numbers + +Line numbers are enabled by default, but you can turn them off like so. +```html + +``` + +# Component API + +| Input Name | Input Typing | Default Value | Description | +| ------------------------ | ---------------------------------------- | ------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | +| **displayOnlyFileNames** | string \| readonly string[] \| undefined | `undefined` | Display in the DOM only the selected filename(s) from the gists files array. Can be either a string or string array. File names much match exactly, be sure to remove any leading or trailing whitespace in the provided strings. | +| **hideGistLink** | bool | `false` | Optionally hide the gist link which opens the gist on GitHub. The gist links automatically dispaly for remote gists, but can be hidden with this feature. | +| **gist** | NgxGist \| undefined | `undefined` | Provide a static gist model here directly which will be displayed if no `gistId` is provided for remote fetching. Also this model will be displayed should a fetch fail when retrieving `gistId`, or overwritten once the pertaining `gistId` data is fetched. | +| **gistId** | string | `undefined` | Provide the GitHub gist id to be fetched and loaded. This can be found in URL of the gists you create. For example the id `TH1515th31DT0C0PY` in: https://gist.github.com/FakeUserName/TH1515th31DT0C0PY. Alternatively, provide a value directly in the sibling input `gist`. | +| **languageName** | string \| undefined | `undefined` | When defined, override automatic language detection [and styling] and treat all gists as this lanuage. See supported language strings here: https://github.com/highlightjs/highlight.js/blob/main/SUPPORTED_LANGUAGES.md | +| **materialTheme** | MaterialPrebuiltTheme \| undefined | `undefined` | Define a material core theme to apply. Ideally, you should already have your global material theme set at the root of your project so try to avoid using this if possible. Note: These are loaded from the CDN: `https://unpkg.com` | +| **showLineNumbers** | bool | `true` | Display or hide the line numbers in your gist code snippets. | +| **useCache** | bool | `true` | Cache the GitHub gist request in local memory for 24 hours. GitHub has a request limit, so this helps in reducing bandwidth. Loads previously fetched gist content from the users machine on refresh and page re-visits. | + +# Compatibility + +| Angular version | @proangular/ngx-gist | Install | +| --------------- | -------------------------- | ------------------------------------ | +| v14 | v1.x.x | `ng add @proangular/ngx-gist@latest` | +| v13 | v1.x.x | `ng add @proangular/ngx-gist@latest` | +| v12 | v1.x.x | `ng add @proangular/ngx-gist@latest` | + +# Development + +Please submit all issues, and feature requests here: [https://github.com/ProAngular/ngx-gist/issues](https://github.com/ProAngular/ngx-gist/issues) + +Contribution: + +1. Clone the repo and create a new branch: + * `git clone https://github.com/ProAngular/ngx-gist.git` + * `git checkout -b username/feature-or-bug-description` +2. Bump up the version of package in `package.json` and `package-lock.json`, commit all changes, push. + * `git add -A` + * `git commit -m "My commit message"` + * `git push origin username/feature-or-bug-description` +3. Submit code in published PR for review and approval. Add a good description and link any possible user stories or bugs. + * [Create a new pull request](https://github.com/ProAngular/ngx-gist/compare). +4. Allow CI actions to completely run and verify files. +5. Add/ping reviewers and await approval. + +Thank you for any and all contributions! + +# Donation + +As a husband and father of four children, your donations mean the world to me! Any donations are greatly appreciated and keep me going! +* [https://www.paypal.me/CodyTolene](https://www.paypal.me/CodyTolene) +* [https://github.com/sponsors/ProAngular](https://github.com/sponsors/ProAngular) + +# License + +Copyright © 2022 [Cody Tolene](https://www.CodyTolene.com) + +All content is licensed under the [MIT license]. + +[mit license]: LICENSE diff --git a/src/app/app.component.ts b/src/app/app.component.ts index dc144a9..cd575d4 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -16,7 +16,7 @@ import { Component } from '@angular/core';

FETCHED GIST (AUTO CACHED FOR 24 HOURS)

ngx-gist will fetch the gist once and store it locally for 24 hours. In - that timeframe if the user returns or visits another page where this + that timeframe, if the user returns or visits another page where this gist was previously loaded, it will reload the content without having to reach out to GitHub again.

@@ -50,8 +50,8 @@ import { Component } from '@angular/core';

DISPLAYING A BASIC CODE SNIPPET (WITHOUT A REMOTE GIST)

These are not fetched from GitHub and are brought in elsewhere from your - application (seperate HTTP request, or statically for example). With - this method you can display code snippets without having to create a + application (separate HTTP request, or statically, for example). With + this method, you can display code snippets without having to create a remote gist. Also, please notice here that no "Open Gist on GitHub" link is displayed here.

diff --git a/src/app/app.module.ts b/src/app/app.module.ts index 927aac8..2833956 100644 --- a/src/app/app.module.ts +++ b/src/app/app.module.ts @@ -5,6 +5,8 @@ import { NgxGistModule } from './public/ngx-gist.module'; import { BodyComponent, FooterComponent, HeaderComponent } from './layout'; import { HttpClientModule } from '@angular/common/http'; import { BrowserAnimationsModule } from '@angular/platform-browser/animations'; +import { MatToolbarModule } from '@angular/material/toolbar'; +import { MatButtonModule } from '@angular/material/button'; @NgModule({ declarations: [AppComponent, BodyComponent, FooterComponent, HeaderComponent], @@ -12,6 +14,8 @@ import { BrowserAnimationsModule } from '@angular/platform-browser/animations'; BrowserAnimationsModule, BrowserModule, HttpClientModule, + MatButtonModule, + MatToolbarModule, NgxGistModule, ], providers: [], diff --git a/src/app/layout/body.component.ts b/src/app/layout/body.component.ts index d2890d3..41c5f07 100644 --- a/src/app/layout/body.component.ts +++ b/src/app/layout/body.component.ts @@ -12,6 +12,7 @@ import { Component } from '@angular/core'; section { padding: 1rem; min-height: 90vh; + margin-top: 64px; } `, ], diff --git a/src/app/layout/header.component.ts b/src/app/layout/header.component.ts index 42f1791..184a661 100644 --- a/src/app/layout/header.component.ts +++ b/src/app/layout/header.component.ts @@ -3,17 +3,55 @@ import { Component } from '@angular/core'; @Component({ selector: 'ngx-header', template: ` -
- - - -
+ + + + + + `, styles: [ ` - header { + :host, + mat-toolbar { + position: fixed; background-color: #1775d1; - padding: 0.5rem 1rem; + padding: 0; + z-index: 1000; + width: 100%; + height: 64px; + top: 0; + } + a.logo, + img.git-hub { + height: 40px; + } + .github-link-container { + display: flex; + justify-content: flex-end; + align-items: center; + width: 100%; + min-width: 6.5rem; + height: 100%; + margin-right: 1rem; + position: relative; + margin: 0; + + > a { + background-color: transparent; + border: none; + cursor: pointer; + } } `, ], diff --git a/src/app/public/ngx-gist.component.ts b/src/app/public/ngx-gist.component.ts index 0e06e5e..f7c3f2e 100644 --- a/src/app/public/ngx-gist.component.ts +++ b/src/app/public/ngx-gist.component.ts @@ -61,6 +61,10 @@ export class NgxGistComponent implements OnInit { private readonly ngxGistLineNumbersService: NgxGistLineNumbersService, private readonly ngxGistThemeService: NgxGistThemeService, ) {} + + // TODO: Apply HighlightJs code theme. + // @Input() public codeTheme?: unknown; + /** * Display in the DOM only the selected filename(s) from the gists files array. * @@ -132,7 +136,7 @@ export class NgxGistComponent implements OnInit { * Tip: See theming Angular Material: https://material.angular.io/guide/theming * if you need help applying a global material theme. */ - @Input() public materialTheme: MaterialPrebuiltTheme | undefined = undefined; + @Input() public materialTheme?: MaterialPrebuiltTheme; /** * Display or hide the line numbers in your gist code snippets. * diff --git a/src/assets/images/git-hub.svg b/src/assets/images/git-hub.svg new file mode 100644 index 0000000..232e834 --- /dev/null +++ b/src/assets/images/git-hub.svg @@ -0,0 +1,35 @@ + + + + GitHub Icon + + + diff --git a/src/styles.scss b/src/styles.scss index 3542910..906298e 100644 --- a/src/styles.scss +++ b/src/styles.scss @@ -15,4 +15,5 @@ body { padding: 0; margin: 0; + background-color: #faf9f6; } From 2e95c8918385b92f7dda9e5c60b304e6369863fb Mon Sep 17 00:00:00 2001 From: Cody Tolene Date: Sat, 30 Jul 2022 00:05:08 -0500 Subject: [PATCH 07/10] Readme update --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 9f06dbd..26a0898 100644 --- a/README.md +++ b/README.md @@ -14,6 +14,8 @@ [![Join the chat at https://gitter.im/ProAngular/community](https://badges.gitter.im/ProAngular/lobby.svg)](https://gitter.im/ProAngular/community) [![Verify and Deploy to GitHub Packages](https://github.com/ProAngular/ngx-gist/actions/workflows/on-merge-main-deploy-gpr.yml/badge.svg)](https://github.com/ProAngular/ngx-gist/actions/workflows/on-merge-main-deploy-gpr.yml) [![Verify and Deploy to npmjs](https://github.com/ProAngular/ngx-gist/actions/workflows/on-merge-main-deploy-npmjs.yml/badge.svg)](https://github.com/ProAngular/ngx-gist/actions/workflows/on-merge-main-deploy-npmjs.yml) +[![npm bundle size (minified + gzip)](https://img.shields.io/bundlephobia/minzip/@ProAngular/ngx-gist.svg)](https://bundlephobia.com/result?p=@ProAngular/ngx-gist) +[![License](https://img.shields.io/npm/l/express.svg?maxAge=2592000)](/LICENSE) # Description From c526de4851f6b10d7fcb2edcdbf804e12ec1baae Mon Sep 17 00:00:00 2001 From: Cody Tolene Date: Sat, 30 Jul 2022 00:09:11 -0500 Subject: [PATCH 08/10] Readme update --- README.md | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 26a0898..28caa11 100644 --- a/README.md +++ b/README.md @@ -13,8 +13,9 @@ [![NPM Downloads](https://img.shields.io/amo/dw/@proangular%252Fngx-gist.svg)](https://www.npmjs.com/@proangular/ngx-gist) [![Join the chat at https://gitter.im/ProAngular/community](https://badges.gitter.im/ProAngular/lobby.svg)](https://gitter.im/ProAngular/community) [![Verify and Deploy to GitHub Packages](https://github.com/ProAngular/ngx-gist/actions/workflows/on-merge-main-deploy-gpr.yml/badge.svg)](https://github.com/ProAngular/ngx-gist/actions/workflows/on-merge-main-deploy-gpr.yml) +[![Monthly Downloads](https://img.shields.io/npm/dm/@ProAngular/ngx-gist.svg)](https://www.npmjs.com/package/@proangular/ngx-gist) [![Verify and Deploy to npmjs](https://github.com/ProAngular/ngx-gist/actions/workflows/on-merge-main-deploy-npmjs.yml/badge.svg)](https://github.com/ProAngular/ngx-gist/actions/workflows/on-merge-main-deploy-npmjs.yml) -[![npm bundle size (minified + gzip)](https://img.shields.io/bundlephobia/minzip/@ProAngular/ngx-gist.svg)](https://bundlephobia.com/result?p=@ProAngular/ngx-gist) +[![npm bundle size (minified + gzip)](https://img.shields.io/bundlephobia/minzip/ProAngular/ngx-gist.svg)](https://bundlephobia.com/result?p=ProAngular/ngx-gist) [![License](https://img.shields.io/npm/l/express.svg?maxAge=2592000)](/LICENSE) # Description From a9f9eda8d139d58fe79db8dac8e903d689ae893e Mon Sep 17 00:00:00 2001 From: Cody Tolene Date: Sat, 30 Jul 2022 00:11:18 -0500 Subject: [PATCH 09/10] Readme update --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 28caa11..fa1f2f4 100644 --- a/README.md +++ b/README.md @@ -13,8 +13,8 @@ [![NPM Downloads](https://img.shields.io/amo/dw/@proangular%252Fngx-gist.svg)](https://www.npmjs.com/@proangular/ngx-gist) [![Join the chat at https://gitter.im/ProAngular/community](https://badges.gitter.im/ProAngular/lobby.svg)](https://gitter.im/ProAngular/community) [![Verify and Deploy to GitHub Packages](https://github.com/ProAngular/ngx-gist/actions/workflows/on-merge-main-deploy-gpr.yml/badge.svg)](https://github.com/ProAngular/ngx-gist/actions/workflows/on-merge-main-deploy-gpr.yml) -[![Monthly Downloads](https://img.shields.io/npm/dm/@ProAngular/ngx-gist.svg)](https://www.npmjs.com/package/@proangular/ngx-gist) [![Verify and Deploy to npmjs](https://github.com/ProAngular/ngx-gist/actions/workflows/on-merge-main-deploy-npmjs.yml/badge.svg)](https://github.com/ProAngular/ngx-gist/actions/workflows/on-merge-main-deploy-npmjs.yml) +[![Monthly Downloads](https://img.shields.io/npm/dm/@ProAngular/ngx-gist.svg)](https://www.npmjs.com/package/@proangular/ngx-gist) [![npm bundle size (minified + gzip)](https://img.shields.io/bundlephobia/minzip/ProAngular/ngx-gist.svg)](https://bundlephobia.com/result?p=ProAngular/ngx-gist) [![License](https://img.shields.io/npm/l/express.svg?maxAge=2592000)](/LICENSE) From b2eb5ae24ede0e05215757f68f4b1310124ecfba Mon Sep 17 00:00:00 2001 From: Cody Tolene Date: Sat, 30 Jul 2022 00:12:23 -0500 Subject: [PATCH 10/10] Update package export --- src/app/public/public.ts | 4 ---- 1 file changed, 4 deletions(-) diff --git a/src/app/public/public.ts b/src/app/public/public.ts index 9616528..3081920 100644 --- a/src/app/public/public.ts +++ b/src/app/public/public.ts @@ -1,9 +1,5 @@ /** Public API Exports for Node Package */ -export * from './ngx-gist-content.pipe'; -export * from './ngx-gist-file-filter.pipe'; export * from './ngx-gist.component'; export * from './ngx-gist.model'; export * from './ngx-gist.module'; -export * from './ngx-gist.service'; -export * from './ngx-gist.utilities';