Compare commits
86 Commits
Author | SHA1 | Date |
---|---|---|
|
b3228f8805 | |
|
c8d0437e4b | |
|
66b3a74d72 | |
|
14a72ac7af | |
|
273b416216 | |
|
e0a31d84a6 | |
|
3a012ae76b | |
|
9a5264be85 | |
|
11ec464c07 | |
|
4b9981691e | |
|
c45120f0bf | |
|
4518c8d951 | |
|
0880de93c4 | |
|
2e06007622 | |
|
4115e3ee4b | |
|
5f8728f78f | |
|
d8fc7d06a3 | |
|
7980719b9a | |
|
4497bf7ce7 | |
|
71b337ce7d | |
|
a322b74e3a | |
|
8e87a1691b | |
|
d35ebcf80f | |
|
7bd0c946b8 | |
|
1a7beaec5c | |
|
9c3d5d82ed | |
|
6f12da98eb | |
|
4b30fc615c | |
|
295aef9ac1 | |
|
edb998ef7c | |
|
e03411ec7f | |
|
a704e32a87 | |
|
7a41cfb111 | |
|
36967355d0 | |
|
8d8f156bb1 | |
|
026a663e2b | |
|
e87635eeff | |
|
98548be2a1 | |
|
37060f2a5f | |
|
28f89c6b09 | |
|
91c9fdca31 | |
|
ca758ddd28 | |
|
6361a6381e | |
|
ae97658bc0 | |
|
e24b381d14 | |
|
799e694e68 | |
|
eff14ef287 | |
|
6ad85653fd | |
|
743f0f5897 | |
|
40ee026a8b | |
|
c10977bc1d | |
|
fb6cba9737 | |
|
57ec58ed26 | |
|
1f8bf96652 | |
|
1017fe7182 | |
|
e1343af330 | |
|
feee784396 | |
|
43b9665252 | |
|
46146edf7f | |
|
a76a635296 | |
|
cea6b51fe3 | |
|
bc40b43479 | |
|
154c28682f | |
|
9c79603247 | |
|
9f49e7ee8c | |
|
723474d5f7 | |
|
17b1abe348 | |
|
68a2ae9408 | |
|
3cf4f3e4b9 | |
|
b277fe823a | |
|
45dce3a323 | |
|
dbeb7b3e22 | |
|
f55110d6df | |
|
3f3314a62a | |
|
f688412e73 | |
|
fe7308e6b7 | |
|
2799e4135b | |
|
6e5438d8a4 | |
|
4144816f7c | |
|
388caa7bdc | |
|
0e57dc4151 | |
|
03f3975132 | |
|
c050381c49 | |
|
5c553d78c5 | |
|
3e0796f909 | |
|
53cad748e2 |
|
@ -0,0 +1,18 @@
|
|||
# This file is used by the build system to adjust CSS and JS output to support the specified browsers below.
|
||||
# For additional information regarding the format and rule options, please see:
|
||||
# https://github.com/browserslist/browserslist#queries
|
||||
|
||||
# For the full list of supported browsers by the Angular framework, please see:
|
||||
# https://angular.io/guide/browser-support
|
||||
|
||||
# You can see what browsers were selected by your queries by running:
|
||||
# npx browserslist
|
||||
|
||||
last 1 Chrome version
|
||||
last 1 Firefox version
|
||||
last 2 Edge major versions
|
||||
last 2 Safari major versions
|
||||
last 2 iOS major versions
|
||||
Firefox ESR
|
||||
not IE 9-10 # Angular support for IE 9-10 has been deprecated and will be removed as of Angular v11. To opt-in, remove the 'not' prefix on this line.
|
||||
not IE 11 # Angular supports IE 11 only as an opt-in. To opt-in, remove the 'not' prefix on this line.
|
|
@ -1,13 +1,13 @@
|
|||
# Editor configuration, see https://editorconfig.org
|
||||
root = true
|
||||
|
||||
[*]
|
||||
charset = utf-8
|
||||
indent_style = space
|
||||
indent_size = 2
|
||||
indent_style = space
|
||||
insert_final_newline = true
|
||||
max_line_length = 140
|
||||
trim_trailing_whitespace = true
|
||||
|
||||
[*.md]
|
||||
max_line_length = off
|
||||
max_line_length = false
|
||||
trim_trailing_whitespace = false
|
||||
|
|
|
@ -0,0 +1,8 @@
|
|||
.angular
|
||||
.pnpm-store
|
||||
dist
|
||||
e2e/protractor.conf.js
|
||||
node_modules
|
||||
pnpm-lock.yaml
|
||||
public
|
||||
src/test.ts
|
|
@ -0,0 +1,134 @@
|
|||
{
|
||||
"root": true,
|
||||
"env": {
|
||||
"browser": true
|
||||
},
|
||||
"ignorePatterns": ["projects/**/*"],
|
||||
"overrides": [
|
||||
{
|
||||
"files": ["*.ts"],
|
||||
"parserOptions": {
|
||||
"project": ["tsconfig.json", "e2e/tsconfig.json"],
|
||||
"createDefaultProgram": true
|
||||
},
|
||||
"plugins": ["rxjs-angular"],
|
||||
"extends": [
|
||||
"eslint:recommended",
|
||||
"plugin:@typescript-eslint/recommended",
|
||||
"plugin:@typescript-eslint/recommended-requiring-type-checking",
|
||||
"prettier",
|
||||
"plugin:rxjs/recommended",
|
||||
"plugin:@angular-eslint/all",
|
||||
"plugin:@angular-eslint/recommended--extra",
|
||||
"plugin:@angular-eslint/template/process-inline-templates"
|
||||
],
|
||||
"rules": {
|
||||
"@angular-eslint/directive-selector": [
|
||||
"error",
|
||||
{
|
||||
"type": "attribute",
|
||||
"prefix": "app",
|
||||
"style": "camelCase"
|
||||
}
|
||||
],
|
||||
"@angular-eslint/component-selector": [
|
||||
"error",
|
||||
{
|
||||
"type": "element",
|
||||
"prefix": "app",
|
||||
"style": "kebab-case"
|
||||
}
|
||||
],
|
||||
// Custom rules
|
||||
// @typescript-eslint
|
||||
"@typescript-eslint/array-type": "error",
|
||||
"@typescript-eslint/class-literal-property-style": "error",
|
||||
"@typescript-eslint/consistent-indexed-object-style": "error",
|
||||
"@typescript-eslint/consistent-type-assertions": [
|
||||
"error",
|
||||
{
|
||||
"assertionStyle": "as",
|
||||
"objectLiteralTypeAssertions": "never"
|
||||
}
|
||||
],
|
||||
"@typescript-eslint/consistent-type-definitions": "error",
|
||||
"@typescript-eslint/consistent-type-imports": "error",
|
||||
"@typescript-eslint/dot-notation": "error",
|
||||
"@typescript-eslint/explicit-function-return-type": "error",
|
||||
"@typescript-eslint/explicit-member-accessibility": [
|
||||
"error",
|
||||
{
|
||||
"accessibility": "no-public"
|
||||
}
|
||||
],
|
||||
"@typescript-eslint/member-delimiter-style": [
|
||||
"error",
|
||||
{
|
||||
"multiline": {
|
||||
"delimiter": "none",
|
||||
"requireLast": true
|
||||
}
|
||||
}
|
||||
],
|
||||
"@typescript-eslint/method-signature-style": "error",
|
||||
"@typescript-eslint/no-base-to-string": "error",
|
||||
"@typescript-eslint/no-confusing-non-null-assertion": "error",
|
||||
"@typescript-eslint/no-confusing-void-expression": [
|
||||
"error",
|
||||
{
|
||||
"ignoreArrowShorthand": true,
|
||||
"ignoreVoidOperator": true
|
||||
}
|
||||
],
|
||||
"@typescript-eslint/no-dynamic-delete": "error",
|
||||
"@typescript-eslint/no-empty-function": [
|
||||
"error",
|
||||
{
|
||||
"allow": ["private-constructors", "protected-constructors"]
|
||||
}
|
||||
],
|
||||
"@typescript-eslint/no-extra-parens": ["error", "functions"],
|
||||
"@typescript-eslint/no-implicit-any-catch": "error",
|
||||
"@typescript-eslint/no-invalid-void-type": "error",
|
||||
"@typescript-eslint/no-non-null-assertion": "error",
|
||||
"@typescript-eslint/no-unnecessary-boolean-literal-compare": "error",
|
||||
"@typescript-eslint/no-unnecessary-condition": "error",
|
||||
"@typescript-eslint/no-unnecessary-qualifier": "error",
|
||||
"@typescript-eslint/no-unnecessary-type-arguments": "error",
|
||||
"@typescript-eslint/no-unnecessary-type-constraint": "error",
|
||||
"@typescript-eslint/no-unsafe-argument": "error",
|
||||
"@typescript-eslint/no-unsafe-assignment": "error",
|
||||
"@typescript-eslint/no-var-requires": "error",
|
||||
"@typescript-eslint/non-nullable-type-assertion-style": "error",
|
||||
"@typescript-eslint/prefer-for-of": "error",
|
||||
"@typescript-eslint/prefer-function-type": "error",
|
||||
"@typescript-eslint/prefer-includes": "error",
|
||||
"@typescript-eslint/prefer-nullish-coalescing": "error",
|
||||
"@typescript-eslint/prefer-optional-chain": "error",
|
||||
"@typescript-eslint/prefer-readonly": "error",
|
||||
"@typescript-eslint/prefer-reduce-type-parameter": "error",
|
||||
"@typescript-eslint/prefer-return-this-type": "error",
|
||||
"@typescript-eslint/prefer-string-starts-ends-with": "error",
|
||||
"@typescript-eslint/prefer-ts-expect-error": "error",
|
||||
"@typescript-eslint/promise-function-async": "error",
|
||||
"@typescript-eslint/require-array-sort-compare": "error",
|
||||
"@typescript-eslint/semi": ["error", "never"],
|
||||
"@typescript-eslint/sort-type-union-intersection-members": "error",
|
||||
"@typescript-eslint/switch-exhaustiveness-check": "error",
|
||||
"@typescript-eslint/type-annotation-spacing": "error",
|
||||
"@typescript-eslint/unified-signatures": "error",
|
||||
// eslint-plugin-rxjs-angular
|
||||
//"rxjs-angular/prefer-async-pipe": "error",
|
||||
"rxjs-angular/prefer-takeuntil": "error"
|
||||
}
|
||||
},
|
||||
{
|
||||
"files": ["*.html"],
|
||||
"extends": ["plugin:@angular-eslint/template/all"],
|
||||
"rules": {
|
||||
// Custom rules
|
||||
"@angular-eslint/template/i18n": "off"
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
|
@ -0,0 +1,12 @@
|
|||
# These are supported funding model platforms
|
||||
|
||||
github: # Replace with up to 4 GitHub Sponsors-enabled usernames e.g., [user1, user2]
|
||||
patreon: NatoBoram # Replace with a single Patreon username
|
||||
open_collective: # Replace with a single Open Collective username
|
||||
ko_fi: # Replace with a single Ko-fi username
|
||||
tidelift: # Replace with a single Tidelift platform-name/package-name e.g., npm/babel
|
||||
community_bridge: # Replace with a single Community Bridge project-name e.g., cloud-foundry
|
||||
liberapay: # Replace with a single Liberapay username
|
||||
issuehunt: # Replace with a single IssueHunt username
|
||||
otechie: # Replace with a single Otechie username
|
||||
custom: ["https://paypal.me/NatoBoram/5"] # Replace with up to 4 custom sponsorship URLs e.g., ['link1', 'link2']
|
|
@ -1,46 +1,126 @@
|
|||
# See http://help.github.com/ignore-files/ for more about ignoring files.
|
||||
# Created by https://www.toptal.com/developers/gitignore/api/angular,linux,windows,macos,visualstudiocode
|
||||
# Edit at https://www.toptal.com/developers/gitignore?templates=angular,linux,windows,macos,visualstudiocode
|
||||
|
||||
### Angular ###
|
||||
## Angular ##
|
||||
# compiled output
|
||||
/dist
|
||||
/tmp
|
||||
/out-tsc
|
||||
# Only exists if Bazel was run
|
||||
/bazel-out
|
||||
dist/
|
||||
tmp/
|
||||
app/**/*.js
|
||||
app/**/*.js.map
|
||||
|
||||
# dependencies
|
||||
/node_modules
|
||||
|
||||
# profiling files
|
||||
chrome-profiler-events*.json
|
||||
speed-measure-plugin*.json
|
||||
node_modules/
|
||||
bower_components/
|
||||
|
||||
# IDEs and editors
|
||||
/.idea
|
||||
.project
|
||||
.classpath
|
||||
.c9/
|
||||
*.launch
|
||||
.settings/
|
||||
*.sublime-workspace
|
||||
.idea/
|
||||
|
||||
# IDE - VSCode
|
||||
# misc
|
||||
.sass-cache/
|
||||
connect.lock/
|
||||
coverage/
|
||||
libpeerconnection.log/
|
||||
npm-debug.log
|
||||
testem.log
|
||||
typings/
|
||||
.angular/
|
||||
|
||||
# e2e
|
||||
e2e/*.js
|
||||
e2e/*.map
|
||||
|
||||
# System Files
|
||||
.DS_Store/
|
||||
|
||||
### Linux ###
|
||||
*~
|
||||
|
||||
# temporary files which can be created if a process still has a handle open of a deleted file
|
||||
.fuse_hidden*
|
||||
|
||||
# KDE directory preferences
|
||||
.directory
|
||||
|
||||
# Linux trash folder which might appear on any partition or disk
|
||||
.Trash-*
|
||||
|
||||
# .nfs files are created when an open file is removed but is still being accessed
|
||||
.nfs*
|
||||
|
||||
### macOS ###
|
||||
# General
|
||||
.DS_Store
|
||||
.AppleDouble
|
||||
.LSOverride
|
||||
|
||||
# Icon must end with two \r
|
||||
Icon
|
||||
|
||||
# Thumbnails
|
||||
._*
|
||||
|
||||
# Files that might appear in the root of a volume
|
||||
.DocumentRevisions-V100
|
||||
.fseventsd
|
||||
.Spotlight-V100
|
||||
.TemporaryItems
|
||||
.Trashes
|
||||
.VolumeIcon.icns
|
||||
.com.apple.timemachine.donotpresent
|
||||
|
||||
# Directories potentially created on remote AFP share
|
||||
.AppleDB
|
||||
.AppleDesktop
|
||||
Network Trash Folder
|
||||
Temporary Items
|
||||
.apdisk
|
||||
|
||||
### VisualStudioCode ###
|
||||
.vscode/*
|
||||
!.vscode/settings.json
|
||||
!.vscode/tasks.json
|
||||
!.vscode/launch.json
|
||||
!.vscode/extensions.json
|
||||
.history/*
|
||||
!.vscode/*.code-snippets
|
||||
|
||||
# misc
|
||||
/.sass-cache
|
||||
/connect.lock
|
||||
/coverage
|
||||
/libpeerconnection.log
|
||||
npm-debug.log
|
||||
yarn-error.log
|
||||
testem.log
|
||||
/typings
|
||||
# Local History for Visual Studio Code
|
||||
.history/
|
||||
|
||||
# System Files
|
||||
.DS_Store
|
||||
# Built Visual Studio Code Extensions
|
||||
*.vsix
|
||||
|
||||
### VisualStudioCode Patch ###
|
||||
# Ignore all local history of files
|
||||
.history
|
||||
.ionide
|
||||
|
||||
# Support for Project snippet scope
|
||||
|
||||
### Windows ###
|
||||
# Windows thumbnail cache files
|
||||
Thumbs.db
|
||||
Thumbs.db:encryptable
|
||||
ehthumbs.db
|
||||
ehthumbs_vista.db
|
||||
|
||||
# Dump file
|
||||
*.stackdump
|
||||
|
||||
# Folder config file
|
||||
[Dd]esktop.ini
|
||||
|
||||
# Recycle Bin used on file shares
|
||||
$RECYCLE.BIN/
|
||||
|
||||
# Windows Installer files
|
||||
*.cab
|
||||
*.msi
|
||||
*.msix
|
||||
*.msm
|
||||
*.msp
|
||||
|
||||
# Windows shortcuts
|
||||
*.lnk
|
||||
|
||||
# End of https://www.toptal.com/developers/gitignore/api/angular,linux,windows,macos,visualstudiocode
|
||||
|
|
|
@ -1,20 +1,25 @@
|
|||
image: node:13
|
||||
image: node:latest
|
||||
|
||||
before_script:
|
||||
- yarn
|
||||
- curl -f https://get.pnpm.io/v6.16.js | node - add --global pnpm@6
|
||||
- pnpm config set store-dir .pnpm-store
|
||||
- pnpm i
|
||||
|
||||
variables:
|
||||
# https://stackoverflow.com/a/69746937/5083247
|
||||
NODE_OPTIONS: --openssl-legacy-provider
|
||||
|
||||
cache:
|
||||
key:
|
||||
files:
|
||||
- package.json
|
||||
- yarn.lock
|
||||
- pnpm-lock.yaml
|
||||
paths:
|
||||
- node_modules
|
||||
- .pnpm-store
|
||||
|
||||
build:
|
||||
stage: build
|
||||
script:
|
||||
- yarn run build:prod
|
||||
- pnpm run build:prod
|
||||
artifacts:
|
||||
paths:
|
||||
- dist/angular
|
||||
|
@ -22,12 +27,13 @@ build:
|
|||
test:
|
||||
stage: test
|
||||
script:
|
||||
- yarn run lint
|
||||
- pnpx ng lint
|
||||
- pnpx prettier --check .
|
||||
|
||||
pages:
|
||||
stage: deploy
|
||||
script:
|
||||
- yarn run build:gitlab
|
||||
- pnpm run build:gitlab
|
||||
- mv dist/angular public
|
||||
- cp public/index.html public/404.html
|
||||
artifacts:
|
||||
|
|
|
@ -1,3 +1,3 @@
|
|||
{
|
||||
"packageManager": "yarn"
|
||||
"packageManager": "pnpm"
|
||||
}
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
{
|
||||
"line-length": false,
|
||||
"line_length": false,
|
||||
"no-duplicate-heading": false
|
||||
}
|
||||
|
|
|
@ -0,0 +1,6 @@
|
|||
.angular
|
||||
.pnpm-store
|
||||
dist
|
||||
node_modules
|
||||
pnpm-lock.yaml
|
||||
public
|
|
@ -0,0 +1,3 @@
|
|||
arrowParens: avoid
|
||||
printWidth: 140
|
||||
semi: false
|
|
@ -5,16 +5,19 @@
|
|||
"recommendations": [
|
||||
"angular.ng-template",
|
||||
"davidanson.vscode-markdownlint",
|
||||
"dbaeumer.vscode-eslint",
|
||||
"editorconfig.editorconfig",
|
||||
"hookyqr.beautify",
|
||||
"esbenp.prettier-vscode",
|
||||
"gitlab.gitlab-workflow",
|
||||
"johnpapa.angular2",
|
||||
"ms-vscode.typescript-javascript-grammar",
|
||||
"ms-vscode.vscode-typescript-tslint-plugin",
|
||||
"msjsdiag.debugger-for-chrome",
|
||||
"visualstudioexptteam.vscodeintellicode",
|
||||
"ms-vscode.vscode-typescript-next",
|
||||
"visualstudioexptteam.vscodeintellicode"
|
||||
],
|
||||
// List of extensions recommended by VS Code that should not be recommended for users of this workspace.
|
||||
"unwantedRecommendations": [
|
||||
"eg2.tslint"
|
||||
"eg2.tslint",
|
||||
"ms-azuretools.vscode-docker",
|
||||
"ms-edgedevtools.vscode-edge-devtools",
|
||||
"ms-vscode-remote.remote-wsl"
|
||||
]
|
||||
}
|
||||
|
|
|
@ -37,9 +37,7 @@
|
|||
"request": "launch",
|
||||
"program": "${workspaceFolder}/node_modules/protractor/bin/protractor",
|
||||
"protocol": "inspector",
|
||||
"args": [
|
||||
"${workspaceFolder}/e2e/protractor.conf.js"
|
||||
]
|
||||
"args": ["${workspaceFolder}/e2e/protractor.conf.js"]
|
||||
}
|
||||
]
|
||||
}
|
||||
|
|
|
@ -1,17 +1,30 @@
|
|||
{
|
||||
"[css][scss][html][javascript][typescript][json][jsonc][markdown][yaml]": {
|
||||
"editor.defaultFormatter": "esbenp.prettier-vscode"
|
||||
},
|
||||
"editor.codeActionsOnSave": {
|
||||
"source.fixAll": true,
|
||||
"source.fixAll.eslint": true,
|
||||
"source.organizeImports": true
|
||||
},
|
||||
"editor.defaultFormatter": "esbenp.prettier-vscode",
|
||||
"editor.formatOnSave": true,
|
||||
"editor.rulers": [
|
||||
140
|
||||
],
|
||||
"editor.rulers": [140],
|
||||
"eslint.options": {
|
||||
"extensions": [".ts", ".html"]
|
||||
},
|
||||
"eslint.packageManager": "pnpm",
|
||||
"eslint.validate": ["javascript", "javascriptreact", "typescript", "typescriptreact", "html"],
|
||||
"files.associations": {
|
||||
".ipfs-npmrc": "json"
|
||||
},
|
||||
"html.format.indentHandlebars": true,
|
||||
"html.format.maxPreserveNewLines": 1,
|
||||
"html.format.wrapAttributes": "auto",
|
||||
"html.format.wrapLineLength": 140,
|
||||
"npm.packageManager": "yarn",
|
||||
"tslint.packageManager": "yarn",
|
||||
"npm.packageManager": "pnpm",
|
||||
"tslint.packageManager": "pnpm",
|
||||
"typescript.preferences.importModuleSpecifier": "relative",
|
||||
"typescript.updateImportsOnFileMove.enabled": "always",
|
||||
"typescript.tsdk": "node_modules\\typescript\\lib",
|
||||
"typescript.updateImportsOnFileMove.enabled": "always"
|
||||
}
|
||||
|
|
|
@ -17,10 +17,7 @@
|
|||
"owner": "typescript",
|
||||
"source": "ts",
|
||||
"applyTo": "closedDocuments",
|
||||
"fileLocation": [
|
||||
"relative",
|
||||
"${cwd}"
|
||||
],
|
||||
"fileLocation": ["relative", "${cwd}"],
|
||||
"pattern": "$tsc",
|
||||
"background": {
|
||||
"activeOnStart": true,
|
||||
|
@ -32,6 +29,6 @@
|
|||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
}
|
||||
]
|
||||
}
|
||||
|
|
71
CHANGELOG.md
71
CHANGELOG.md
|
@ -18,6 +18,63 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/), and this
|
|||
|
||||
### Security
|
||||
|
||||
## [2.2.1]
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated my own gateway to its HTTPS link
|
||||
|
||||
## [2.2.0] - 2022-03-11
|
||||
|
||||
### Added
|
||||
|
||||
- More information in the `package.json`.
|
||||
- Added ESLint
|
||||
- Added Prettier
|
||||
- Put success reponses at the top of the list
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated `gateways.json`
|
||||
- Upgraded to Angular 13
|
||||
- Targets ESNext
|
||||
|
||||
### Removed
|
||||
|
||||
- Removed TSLint
|
||||
|
||||
## [2.1.1] - 2021-03-20
|
||||
|
||||
### Added
|
||||
|
||||
- Added some accessibility tags
|
||||
- Added some VSCode settings
|
||||
|
||||
### Changed
|
||||
|
||||
- Updated to Angular 11
|
||||
- Updated gateways
|
||||
|
||||
### Fixed
|
||||
|
||||
- Corrected the title from "Public IPFS Cacher" to "Public Gateway Cacher".
|
||||
|
||||
## [2.1.0] - 2020-07-10
|
||||
|
||||
### Added
|
||||
|
||||
- Support for subdomain gateways
|
||||
- Strict mode
|
||||
- More icons
|
||||
- IPFS colours
|
||||
|
||||
### Changed
|
||||
|
||||
- Better screenshot
|
||||
- Upgraded to Angular 10
|
||||
- Now uses `--chunker=buzhash`
|
||||
- Updated `bootstrap` and `ipfs-css`
|
||||
|
||||
## [2.0.0] - 2019-12-03
|
||||
|
||||
Now based on Angular!
|
||||
|
@ -26,7 +83,7 @@ Tests were done with `ipfs-npm` : They weren't successful. `ipfs-css` is only mi
|
|||
|
||||
### Added
|
||||
|
||||
* GitLab Pages - <https://natoboram.gitlab.io/public-gateway-cacher/>
|
||||
- GitLab Pages - <https://natoboram.gitlab.io/public-gateway-cacher/>
|
||||
|
||||
## [1.0.0] - 2019-11-28
|
||||
|
||||
|
@ -34,9 +91,9 @@ This version is a fork of [github.com/ipfs/public-gateway-checker](https://githu
|
|||
|
||||
## Types of changes
|
||||
|
||||
* `Added` for new features.
|
||||
* `Changed` for changes in existing functionality.
|
||||
* `Deprecated` for soon-to-be removed features.
|
||||
* `Removed` for now removed features.
|
||||
* `Fixed` for any bug fixes.
|
||||
* `Security` in case of vulnerabilities.
|
||||
- `Added` for new features.
|
||||
- `Changed` for changes in existing functionality.
|
||||
- `Deprecated` for soon-to-be removed features.
|
||||
- `Removed` for now removed features.
|
||||
- `Fixed` for any bug fixes.
|
||||
- `Security` in case of vulnerabilities.
|
||||
|
|
41
README.md
41
README.md
|
@ -1,41 +1,14 @@
|
|||
# Public Gateway Cacher
|
||||
|
||||
[](https://gitlab.com/NatoBoram/public-gateway-cacher/-/commits/master)
|
||||
[](https://stackshare.io/NatoBoram/public-gateway-cacher)
|
||||
|
||||
Cache a specific hash on a bunch of public gateways.
|
||||
|
||||
**Note :** All of these (except gateway.ipfs.io and ipfs.io) are hosted by third-parties and should be treated as such.
|
||||
You can view this website on [GitLab Pages](https://natoboram.gitlab.io/public-gateway-cacher) and [IPFS](https://bafybeievsdzxuvuah5t6vzhig525jecp7wmupnm7olxdkonqmte57zoqf4.ipfs.dweb.link).
|
||||
|
||||
You can view this website on [IPFS](https://bafybeibjf6z3sxavox6uahfl4vogkuenimlpvn4eghdv6mtsm55rpnalve.cf-ipfs.com).
|
||||

|
||||
|
||||
Here's a screenshot :
|
||||
**NOTE :** All of these (except `ipfs.io` and `dweb.link`) are hosted by third-parties and should be treated as such.
|
||||
|
||||

|
||||
|
||||
If you'd like to add a new public gateway, please go to [github.com/ipfs/public-gateway-checker](https://github.com/ipfs/public-gateway-checker), submit a pull request then open an issue here.
|
||||
|
||||
## Angular
|
||||
|
||||
This project was generated with [Angular CLI](https://github.com/angular/angular-cli) version 8.3.20.
|
||||
|
||||
### Development server
|
||||
|
||||
Run `ng serve` for a dev server. Navigate to `http://localhost:4200/`. The app will automatically reload if you change any of the source files.
|
||||
|
||||
### Code scaffolding
|
||||
|
||||
Run `ng generate component component-name` to generate a new component. You can also use `ng generate directive|pipe|service|class|guard|interface|enum|module`.
|
||||
|
||||
### Build
|
||||
|
||||
Run `ng build` to build the project. The build artifacts will be stored in the `dist/` directory. Use the `--prod` flag for a production build.
|
||||
|
||||
### Running unit tests
|
||||
|
||||
Run `ng test` to execute the unit tests via [Karma](https://karma-runner.github.io).
|
||||
|
||||
### Running end-to-end tests
|
||||
|
||||
Run `ng e2e` to execute the end-to-end tests via [Protractor](http://www.protractortest.org/).
|
||||
|
||||
### Further help
|
||||
|
||||
To get more help on the Angular CLI use `ng help` or go check out the [Angular CLI README](https://github.com/angular/angular-cli/blob/master/README.md).
|
||||
If you'd like to add a new public gateway, please go to [github.com/ipfs/public-gateway-checker](https://github.com/ipfs/public-gateway-checker), submit a pull request then open an issue [here](https://gitlab.com/NatoBoram/public-gateway-cacher/issues/new).
|
||||
|
|
93
angular.json
93
angular.json
|
@ -1,6 +1,11 @@
|
|||
{
|
||||
"$schema": "./node_modules/@angular/cli/lib/config/schema.json",
|
||||
"version": 1,
|
||||
"cli": {
|
||||
"packageManager": "pnpm",
|
||||
"analytics": "10b848ad-8b81-4346-852f-5eff89573a85",
|
||||
"defaultCollection": "@angular-eslint/schematics"
|
||||
},
|
||||
"newProjectRoot": "projects",
|
||||
"projects": {
|
||||
"public-gateway-cacher": {
|
||||
|
@ -8,6 +13,9 @@
|
|||
"schematics": {
|
||||
"@schematics/angular:component": {
|
||||
"style": "scss"
|
||||
},
|
||||
"@schematics/angular:application": {
|
||||
"strict": true
|
||||
}
|
||||
},
|
||||
"root": "",
|
||||
|
@ -22,20 +30,18 @@
|
|||
"main": "src/main.ts",
|
||||
"polyfills": "src/polyfills.ts",
|
||||
"tsConfig": "tsconfig.app.json",
|
||||
"aot": true,
|
||||
"assets": [
|
||||
"src/favicon.png",
|
||||
"src/assets",
|
||||
{
|
||||
"glob": "*",
|
||||
"input": "node_modules/ipfs-css",
|
||||
"output": "assets/ipfs-css"
|
||||
}
|
||||
],
|
||||
"styles": [
|
||||
"src/styles.scss"
|
||||
],
|
||||
"scripts": []
|
||||
"assets": ["src/favicon.png", "src/assets"],
|
||||
"styles": ["src/styles.scss"],
|
||||
"stylePreprocessorOptions": {
|
||||
"includePaths": ["node_modules"]
|
||||
},
|
||||
"scripts": [],
|
||||
"vendorChunk": true,
|
||||
"extractLicenses": false,
|
||||
"buildOptimizer": false,
|
||||
"sourceMap": true,
|
||||
"optimization": false,
|
||||
"namedChunks": true
|
||||
},
|
||||
"configurations": {
|
||||
"production": {
|
||||
|
@ -47,12 +53,7 @@
|
|||
],
|
||||
"optimization": true,
|
||||
"outputHashing": "all",
|
||||
"sourceMap": true,
|
||||
"extractCss": true,
|
||||
"namedChunks": true,
|
||||
"aot": true,
|
||||
"extractLicenses": true,
|
||||
"vendorChunk": true,
|
||||
"buildOptimizer": true,
|
||||
"budgets": [
|
||||
{
|
||||
|
@ -76,12 +77,7 @@
|
|||
],
|
||||
"optimization": true,
|
||||
"outputHashing": "all",
|
||||
"sourceMap": true,
|
||||
"extractCss": true,
|
||||
"namedChunks": true,
|
||||
"aot": true,
|
||||
"extractLicenses": true,
|
||||
"vendorChunk": true,
|
||||
"buildOptimizer": true,
|
||||
"budgets": [
|
||||
{
|
||||
|
@ -105,12 +101,7 @@
|
|||
],
|
||||
"optimization": true,
|
||||
"outputHashing": "all",
|
||||
"sourceMap": true,
|
||||
"extractCss": true,
|
||||
"namedChunks": true,
|
||||
"aot": true,
|
||||
"extractLicenses": true,
|
||||
"vendorChunk": true,
|
||||
"buildOptimizer": true,
|
||||
"budgets": [
|
||||
{
|
||||
|
@ -125,7 +116,8 @@
|
|||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
"defaultConfiguration": ""
|
||||
},
|
||||
"serve": {
|
||||
"builder": "@angular-devkit/build-angular:dev-server",
|
||||
|
@ -151,32 +143,12 @@
|
|||
"polyfills": "src/polyfills.ts",
|
||||
"tsConfig": "tsconfig.spec.json",
|
||||
"karmaConfig": "karma.conf.js",
|
||||
"assets": [
|
||||
"src/favicon.png",
|
||||
"src/assets",
|
||||
{
|
||||
"glob": "*",
|
||||
"input": "node_modules/ipfs-css",
|
||||
"output": "assets/ipfs-css"
|
||||
}
|
||||
],
|
||||
"styles": [
|
||||
"src/styles.scss"
|
||||
],
|
||||
"scripts": []
|
||||
}
|
||||
"assets": ["src/favicon.png", "src/assets"],
|
||||
"styles": ["src/styles.scss"],
|
||||
"stylePreprocessorOptions": {
|
||||
"includePaths": ["node_modules"]
|
||||
},
|
||||
"lint": {
|
||||
"builder": "@angular-devkit/build-angular:tslint",
|
||||
"options": {
|
||||
"tsConfig": [
|
||||
"tsconfig.app.json",
|
||||
"tsconfig.spec.json",
|
||||
"e2e/tsconfig.json"
|
||||
],
|
||||
"exclude": [
|
||||
"**/node_modules/**"
|
||||
]
|
||||
"scripts": []
|
||||
}
|
||||
},
|
||||
"e2e": {
|
||||
|
@ -190,12 +162,15 @@
|
|||
"devServerTarget": "public-gateway-cacher:serve:production"
|
||||
}
|
||||
}
|
||||
},
|
||||
"lint": {
|
||||
"builder": "@angular-eslint/builder:lint",
|
||||
"options": {
|
||||
"lintFilePatterns": ["src/**/*.ts", "src/**/*.html"]
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"defaultProject": "public-gateway-cacher",
|
||||
"cli": {
|
||||
"packageManager": "yarn"
|
||||
}
|
||||
"defaultProject": "public-gateway-cacher"
|
||||
}
|
||||
|
|
12
browserslist
12
browserslist
|
@ -1,12 +0,0 @@
|
|||
# This file is used by the build system to adjust CSS and JS output to support the specified browsers below.
|
||||
# For additional information regarding the format and rule options, please see:
|
||||
# https://github.com/browserslist/browserslist#queries
|
||||
|
||||
# You can see what browsers were selected by your queries by running:
|
||||
# npx browserslist
|
||||
|
||||
> 0.5%
|
||||
last 2 versions
|
||||
Firefox ESR
|
||||
not dead
|
||||
not IE 9-11 # For IE 9-11 support, remove 'not'.
|
|
@ -2,31 +2,35 @@
|
|||
// Protractor configuration file, see link for more information
|
||||
// https://github.com/angular/protractor/blob/master/lib/config.ts
|
||||
|
||||
const { SpecReporter } = require('jasmine-spec-reporter');
|
||||
const { SpecReporter, StacktraceOption } = require("jasmine-spec-reporter")
|
||||
|
||||
/**
|
||||
* @type { import("protractor").Config }
|
||||
*/
|
||||
exports.config = {
|
||||
allScriptsTimeout: 11000,
|
||||
specs: [
|
||||
'./src/**/*.e2e-spec.ts'
|
||||
],
|
||||
specs: ["./src/**/*.e2e-spec.ts"],
|
||||
capabilities: {
|
||||
browserName: 'chrome'
|
||||
browserName: "chrome",
|
||||
},
|
||||
directConnect: true,
|
||||
baseUrl: 'http://localhost:4200/',
|
||||
framework: 'jasmine',
|
||||
baseUrl: "http://localhost:4200/",
|
||||
framework: "jasmine",
|
||||
jasmineNodeOpts: {
|
||||
showColors: true,
|
||||
defaultTimeoutInterval: 30000,
|
||||
print: function() {}
|
||||
print: function () {},
|
||||
},
|
||||
onPrepare() {
|
||||
require('ts-node').register({
|
||||
project: require('path').join(__dirname, './tsconfig.json')
|
||||
});
|
||||
jasmine.getEnv().addReporter(new SpecReporter({ spec: { displayStacktrace: true } }));
|
||||
}
|
||||
};
|
||||
require("ts-node").register({
|
||||
project: require("path").join(__dirname, "./tsconfig.json"),
|
||||
})
|
||||
jasmine.getEnv().addReporter(
|
||||
new SpecReporter({
|
||||
spec: {
|
||||
displayStacktrace: StacktraceOption.PRETTY,
|
||||
},
|
||||
})
|
||||
)
|
||||
},
|
||||
}
|
||||
|
|
|
@ -1,23 +1,25 @@
|
|||
import { browser, logging } from 'protractor';
|
||||
import { AppPage } from './app.po';
|
||||
import { browser, logging } from "protractor"
|
||||
import { AppPage } from "./app.po"
|
||||
|
||||
describe('workspace-project App', () => {
|
||||
let page: AppPage;
|
||||
describe("workspace-project App", (): void => {
|
||||
let page: AppPage
|
||||
|
||||
beforeEach(() => {
|
||||
page = new AppPage();
|
||||
});
|
||||
beforeEach((): void => {
|
||||
page = new AppPage()
|
||||
})
|
||||
|
||||
it('should display welcome message', () => {
|
||||
page.navigateTo();
|
||||
expect(page.getTitleText()).toEqual('public-gateway-cacher app is running!');
|
||||
});
|
||||
it("should display welcome message", (): void => {
|
||||
void page.navigateTo()
|
||||
void expect(page.getTitleText()).toEqual("public-gateway-cacher app is running!")
|
||||
})
|
||||
|
||||
afterEach(async () => {
|
||||
afterEach(async (): Promise<void> => {
|
||||
// Assert that there are no errors emitted from the browser
|
||||
const logs = await browser.manage().logs().get(logging.Type.BROWSER);
|
||||
expect(logs).not.toContain(jasmine.objectContaining({
|
||||
const logs = await browser.manage().logs().get(logging.Type.BROWSER)
|
||||
const expected: Partial<logging.Entry> = {
|
||||
level: logging.Level.SEVERE,
|
||||
} as logging.Entry));
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
void expect(logs).not.toContain(jasmine.objectContaining(expected))
|
||||
})
|
||||
})
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
import { browser, by, element } from 'protractor';
|
||||
import { browser, by, element } from "protractor"
|
||||
|
||||
export class AppPage {
|
||||
navigateTo() {
|
||||
return browser.get(browser.baseUrl) as Promise<any>;
|
||||
async navigateTo(): Promise<unknown> {
|
||||
return browser.get(browser.baseUrl) as Promise<unknown>
|
||||
}
|
||||
|
||||
getTitleText() {
|
||||
return element(by.css('app-root .content span')).getText() as Promise<string>;
|
||||
async getTitleText(): Promise<string> {
|
||||
return element(by.css("pgc-root .content span")).getText() as Promise<string>
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,13 +1,10 @@
|
|||
/* To learn more about this file see: https://angular.io/config/tsconfig. */
|
||||
{
|
||||
"extends": "../tsconfig.json",
|
||||
"compilerOptions": {
|
||||
"outDir": "../out-tsc/e2e",
|
||||
"module": "commonjs",
|
||||
"target": "es5",
|
||||
"types": [
|
||||
"jasmine",
|
||||
"jasminewd2",
|
||||
"node"
|
||||
]
|
||||
"target": "ESNext",
|
||||
"types": ["jasmine", "jasminewd2", "node"]
|
||||
}
|
||||
}
|
||||
|
|
|
@ -3,30 +3,30 @@
|
|||
|
||||
module.exports = function (config) {
|
||||
config.set({
|
||||
basePath: '',
|
||||
frameworks: ['jasmine', '@angular-devkit/build-angular'],
|
||||
basePath: "",
|
||||
frameworks: ["jasmine", "@angular-devkit/build-angular"],
|
||||
plugins: [
|
||||
require('karma-jasmine'),
|
||||
require('karma-chrome-launcher'),
|
||||
require('karma-jasmine-html-reporter'),
|
||||
require('karma-coverage-istanbul-reporter'),
|
||||
require('@angular-devkit/build-angular/plugins/karma')
|
||||
require("karma-jasmine"),
|
||||
require("karma-chrome-launcher"),
|
||||
require("karma-jasmine-html-reporter"),
|
||||
require("karma-coverage-istanbul-reporter"),
|
||||
require("@angular-devkit/build-angular/plugins/karma"),
|
||||
],
|
||||
client: {
|
||||
clearContext: false // leave Jasmine Spec Runner output visible in browser
|
||||
clearContext: false, // leave Jasmine Spec Runner output visible in browser
|
||||
},
|
||||
coverageIstanbulReporter: {
|
||||
dir: require('path').join(__dirname, './coverage/public-gateway-cacher'),
|
||||
reports: ['html', 'lcovonly', 'text-summary'],
|
||||
fixWebpackSourcePaths: true
|
||||
dir: require("path").join(__dirname, "./coverage/public-gateway-cacher"),
|
||||
reports: ["html", "lcovonly", "text-summary"],
|
||||
fixWebpackSourcePaths: true,
|
||||
},
|
||||
reporters: ['progress', 'kjhtml'],
|
||||
reporters: ["progress", "kjhtml"],
|
||||
port: 9876,
|
||||
colors: true,
|
||||
logLevel: config.LOG_INFO,
|
||||
autoWatch: true,
|
||||
browsers: ['Chrome'],
|
||||
browsers: ["Chrome"],
|
||||
singleRun: false,
|
||||
restartOnFileChange: true
|
||||
});
|
||||
};
|
||||
restartOnFileChange: true,
|
||||
})
|
||||
}
|
||||
|
|
119
package.json
119
package.json
|
@ -1,6 +1,28 @@
|
|||
{
|
||||
"name": "public-gateway-cacher",
|
||||
"version": "2.0.0",
|
||||
"version": "2.2.1",
|
||||
"description": "Cache a specific hash on a bunch of public gateways.",
|
||||
"keywords": [
|
||||
"IPFS"
|
||||
],
|
||||
"homepage": "https://natoboram.gitlab.io/public-gateway-cacher",
|
||||
"bugs": {
|
||||
"url": "https://gitlab.com/NatoBoram/public-gateway-cacher/-/issues",
|
||||
"email": "contact-project+natoboram-public-gateway-cacher-11685619-issue-@incoming.gitlab.com"
|
||||
},
|
||||
"license": "GPL-3.0-or-later",
|
||||
"author": {
|
||||
"name": "Nato Boram",
|
||||
"url": "https://gitlab.com/NatoBoram"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
"type": "patreon",
|
||||
"url": "https://www.patreon.com/NatoBoram"
|
||||
},
|
||||
"https://paypal.me/NatoBoram/5"
|
||||
],
|
||||
"repository": "gitlab:NatoBoram/public-gateway-cacher",
|
||||
"scripts": {
|
||||
"ng": "ng",
|
||||
"start": "ng serve --ssl",
|
||||
|
@ -9,54 +31,61 @@
|
|||
"build:gitlab": "ng build --configuration=gitlab --base-href /public-gateway-cacher/",
|
||||
"build:ipfs": "ng build --configuration=ipfs",
|
||||
"test": "ng test",
|
||||
"lint": "ng lint",
|
||||
"lint": "ng lint --fix",
|
||||
"eslint": "eslint --fix .",
|
||||
"prettier": "prettier --write .",
|
||||
"e2e": "ng e2e",
|
||||
"yarn": "ipfs-yarn",
|
||||
"publish:ipfs": "yarn run build:ipfs; ipfs add --recursive --chunker=rabin --cid-version=1 dist/angular"
|
||||
"publish:ipfs": "pnpm run build:ipfs && ipfs add --recursive --chunker=buzhash --cid-version=1 dist/angular",
|
||||
"postinstall": "ngcc"
|
||||
},
|
||||
"private": false,
|
||||
"dependencies": {
|
||||
"@angular/animations": "~8.2.14",
|
||||
"@angular/cdk": "~8.2.3",
|
||||
"@angular/common": "~8.2.14",
|
||||
"@angular/compiler": "~8.2.14",
|
||||
"@angular/core": "~8.2.14",
|
||||
"@angular/flex-layout": "^8.0.0-beta.27",
|
||||
"@angular/forms": "~8.2.14",
|
||||
"@angular/material": "^8.2.3",
|
||||
"@angular/platform-browser": "~8.2.14",
|
||||
"@angular/platform-browser-dynamic": "~8.2.14",
|
||||
"@angular/router": "~8.2.14",
|
||||
"bootstrap": "^4.4.1",
|
||||
"hammerjs": "^2.0.8",
|
||||
"ipfs-css": "^0.13.1",
|
||||
"rxjs": "~6.5.3",
|
||||
"tslib": "^1.10.0",
|
||||
"zone.js": "~0.9.1"
|
||||
"@angular/animations": "~13.3.9",
|
||||
"@angular/cdk": "~13.3.7",
|
||||
"@angular/common": "~13.3.9",
|
||||
"@angular/compiler": "~13.3.9",
|
||||
"@angular/core": "~13.3.9",
|
||||
"@angular/flex-layout": "^13.0.0-beta.38",
|
||||
"@angular/forms": "~13.3.9",
|
||||
"@angular/material": "^13.3.7",
|
||||
"@angular/platform-browser": "~13.3.9",
|
||||
"@angular/platform-browser-dynamic": "~13.3.9",
|
||||
"@angular/router": "~13.3.9",
|
||||
"bootstrap": "^5.1.3",
|
||||
"ipfs-css": "^1.3.0",
|
||||
"rxjs": "~7.5.5",
|
||||
"tslib": "^2.0.0",
|
||||
"zone.js": "~0.11.4"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@angular-devkit/build-angular": "~0.803.20",
|
||||
"@angular/cli": "~8.3.20",
|
||||
"@angular/compiler-cli": "~8.2.14",
|
||||
"@angular/language-service": "~8.2.14",
|
||||
"@types/jasmine": "~3.3.8",
|
||||
"@angular-devkit/build-angular": "~13.3.6",
|
||||
"@angular-eslint/builder": "13.2.1",
|
||||
"@angular-eslint/eslint-plugin": "13.2.1",
|
||||
"@angular-eslint/eslint-plugin-template": "13.2.1",
|
||||
"@angular-eslint/schematics": "13.2.1",
|
||||
"@angular-eslint/template-parser": "13.2.1",
|
||||
"@angular/cli": "~13.3.6",
|
||||
"@angular/compiler-cli": "~13.3.9",
|
||||
"@angular/language-service": "~13.3.9",
|
||||
"@types/jasmine": "~3.10.3",
|
||||
"@types/jasminewd2": "~2.0.3",
|
||||
"@types/node": "~8.9.4",
|
||||
"codelyzer": "^5.0.0",
|
||||
"jasmine-core": "~3.4.0",
|
||||
"jasmine-spec-reporter": "~4.2.1",
|
||||
"karma": "~4.1.0",
|
||||
"karma-chrome-launcher": "~2.2.0",
|
||||
"karma-coverage-istanbul-reporter": "~2.0.1",
|
||||
"karma-jasmine": "~2.0.1",
|
||||
"karma-jasmine-html-reporter": "^1.4.0",
|
||||
"protractor": "~5.4.0",
|
||||
"rxjs-tslint-rules": "^4.26.3",
|
||||
"ts-node": "~7.0.0",
|
||||
"tslint": "~5.15.0",
|
||||
"tslint-consistent-codestyle": "^1.16.0",
|
||||
"tslint-origin-ordered-imports-rule": "^1.2.2",
|
||||
"tslint-rxjs-subject-restrictions-rule": "^1.0.4",
|
||||
"typescript": "~3.5.3"
|
||||
}
|
||||
"@types/node": "^17.0.21",
|
||||
"@typescript-eslint/eslint-plugin": "5.14.0",
|
||||
"@typescript-eslint/parser": "5.14.0",
|
||||
"eslint": "^8.2.0",
|
||||
"eslint-config-prettier": "^8.5.0",
|
||||
"eslint-plugin-rxjs": "^5.0.2",
|
||||
"eslint-plugin-rxjs-angular": "^2.0.0",
|
||||
"jasmine-core": "~4.0.1",
|
||||
"jasmine-spec-reporter": "~7.0.0",
|
||||
"karma": "~6.3.17",
|
||||
"karma-chrome-launcher": "~3.1.0",
|
||||
"karma-coverage-istanbul-reporter": "~3.0.2",
|
||||
"karma-jasmine": "~4.0.0",
|
||||
"karma-jasmine-html-reporter": "^1.5.0",
|
||||
"prettier": "^2.5.1",
|
||||
"protractor": "~7.0.0",
|
||||
"ts-node": "~10.7.0",
|
||||
"typescript": "~4.5.5"
|
||||
},
|
||||
"private": true
|
||||
}
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -1,14 +1,17 @@
|
|||
import { NgModule } from '@angular/core';
|
||||
import { RouterModule, Routes } from '@angular/router';
|
||||
import { environment } from '../environments/environment';
|
||||
import { NgModule } from "@angular/core"
|
||||
import type { Routes } from "@angular/router"
|
||||
import { RouterModule } from "@angular/router"
|
||||
import { environment } from "../environments/environment"
|
||||
|
||||
const routes: Routes = [{
|
||||
path: '',
|
||||
loadChildren: () => import('./pages/pages.module').then(m => m.PagesModule),
|
||||
}];
|
||||
const routes: Routes = [
|
||||
{
|
||||
path: "",
|
||||
loadChildren: async () => import("./pages/pages.module").then(m => m.PagesModule),
|
||||
},
|
||||
]
|
||||
|
||||
@NgModule({
|
||||
imports: [RouterModule.forRoot(routes, { useHash: environment.useHash })],
|
||||
exports: [RouterModule]
|
||||
imports: [RouterModule.forRoot(routes, { useHash: environment.useHash, relativeLinkResolution: "legacy" })],
|
||||
exports: [RouterModule],
|
||||
})
|
||||
export class AppRoutingModule { }
|
||||
export class AppRoutingModule {}
|
||||
|
|
|
@ -1 +1,9 @@
|
|||
<mat-toolbar color="primary" fxLayout="row" fxLayoutAlign="space-between center" fxLayoutGap="1em">
|
||||
<h1>Public Gateway Cacher</h1>
|
||||
|
||||
<!-- Theme Switcher -->
|
||||
<button mat-icon-button="">
|
||||
<mat-icon (click)="themeService.switchTheme()">{{ themeService.icon }}</mat-icon>
|
||||
</button>
|
||||
</mat-toolbar>
|
||||
<router-outlet></router-outlet>
|
||||
|
|
|
@ -1,35 +1,41 @@
|
|||
import { TestBed, async } from '@angular/core/testing';
|
||||
import { RouterTestingModule } from '@angular/router/testing';
|
||||
import { AppComponent } from './app.component';
|
||||
import { TestBed, waitForAsync } from "@angular/core/testing"
|
||||
import { RouterTestingModule } from "@angular/router/testing"
|
||||
import { AppComponent } from "./app.component"
|
||||
|
||||
describe('AppComponent', () => {
|
||||
beforeEach(async(() => {
|
||||
TestBed.configureTestingModule({
|
||||
imports: [
|
||||
RouterTestingModule
|
||||
],
|
||||
declarations: [
|
||||
AppComponent
|
||||
],
|
||||
}).compileComponents();
|
||||
}));
|
||||
describe("AppComponent", (): void => {
|
||||
beforeEach(waitForAsync((): void => {
|
||||
void TestBed.configureTestingModule({
|
||||
imports: [RouterTestingModule],
|
||||
declarations: [AppComponent],
|
||||
}).compileComponents()
|
||||
}))
|
||||
|
||||
it('should create the app', () => {
|
||||
const fixture = TestBed.createComponent(AppComponent);
|
||||
const app = fixture.debugElement.componentInstance;
|
||||
expect(app).toBeTruthy();
|
||||
});
|
||||
it("should create the app", (): void => {
|
||||
const fixture = TestBed.createComponent(AppComponent)
|
||||
if (!(fixture.debugElement.componentInstance instanceof AppComponent)) throw new Error("Expected AppComponent")
|
||||
|
||||
it(`should have as title 'public-gateway-cacher'`, () => {
|
||||
const fixture = TestBed.createComponent(AppComponent);
|
||||
const app = fixture.debugElement.componentInstance;
|
||||
expect(app.title).toEqual('public-gateway-cacher');
|
||||
});
|
||||
const app: AppComponent = fixture.debugElement.componentInstance
|
||||
void expect(app).toBeTruthy()
|
||||
})
|
||||
|
||||
it('should render title', () => {
|
||||
const fixture = TestBed.createComponent(AppComponent);
|
||||
fixture.detectChanges();
|
||||
const compiled = fixture.debugElement.nativeElement;
|
||||
expect(compiled.querySelector('.content span').textContent).toContain('public-gateway-cacher app is running!');
|
||||
});
|
||||
});
|
||||
it(`should have a themeService`, (): void => {
|
||||
const fixture = TestBed.createComponent(AppComponent)
|
||||
if (!(fixture.debugElement.componentInstance instanceof AppComponent)) throw new Error("Expected AppComponent")
|
||||
|
||||
const app: AppComponent = fixture.debugElement.componentInstance
|
||||
void expect(app.themeService).toBeTruthy()
|
||||
})
|
||||
|
||||
it("should render title", (): void => {
|
||||
const fixture = TestBed.createComponent(AppComponent)
|
||||
fixture.detectChanges()
|
||||
if (!isHTMLElement(fixture.debugElement.nativeElement)) throw new Error("Expected HTMLElement")
|
||||
|
||||
const compiled: HTMLElement = fixture.debugElement.nativeElement
|
||||
void expect(compiled.querySelector("h1")?.textContent).toContain("Public Gateway Cacher")
|
||||
})
|
||||
})
|
||||
|
||||
function isHTMLElement(element: unknown): element is HTMLElement {
|
||||
return Object.getPrototypeOf(element) instanceof HTMLElement
|
||||
}
|
||||
|
|
|
@ -1,10 +1,12 @@
|
|||
import { Component } from '@angular/core';
|
||||
import { ChangeDetectionStrategy, Component, Inject } from "@angular/core"
|
||||
import { ThemeService } from "./services/theme.service"
|
||||
|
||||
@Component({
|
||||
selector: 'app-root',
|
||||
templateUrl: './app.component.html',
|
||||
styleUrls: ['./app.component.scss']
|
||||
selector: "app-root",
|
||||
templateUrl: "./app.component.html",
|
||||
styleUrls: ["./app.component.scss"],
|
||||
changeDetection: ChangeDetectionStrategy.OnPush,
|
||||
})
|
||||
export class AppComponent {
|
||||
title = 'public-gateway-cacher';
|
||||
constructor(@Inject(ThemeService) readonly themeService: ThemeService) {}
|
||||
}
|
||||
|
|
|
@ -1,23 +1,29 @@
|
|||
import { CommonModule } from '@angular/common';
|
||||
import { HttpClientModule } from '@angular/common/http';
|
||||
import { NgModule } from '@angular/core';
|
||||
import { BrowserModule } from '@angular/platform-browser';
|
||||
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
|
||||
import { AppRoutingModule } from './app-routing.module';
|
||||
import { AppComponent } from './app.component';
|
||||
import { CommonModule } from "@angular/common"
|
||||
import { HttpClientModule } from "@angular/common/http"
|
||||
import { NgModule } from "@angular/core"
|
||||
import { FlexLayoutModule } from "@angular/flex-layout"
|
||||
import { MatButtonModule } from "@angular/material/button"
|
||||
import { MatIconModule } from "@angular/material/icon"
|
||||
import { MatToolbarModule } from "@angular/material/toolbar"
|
||||
import { BrowserModule } from "@angular/platform-browser"
|
||||
import { BrowserAnimationsModule } from "@angular/platform-browser/animations"
|
||||
import { AppRoutingModule } from "./app-routing.module"
|
||||
import { AppComponent } from "./app.component"
|
||||
|
||||
@NgModule({
|
||||
declarations: [
|
||||
AppComponent
|
||||
],
|
||||
declarations: [AppComponent],
|
||||
imports: [
|
||||
CommonModule,
|
||||
BrowserModule,
|
||||
BrowserAnimationsModule,
|
||||
HttpClientModule,
|
||||
AppRoutingModule,
|
||||
BrowserAnimationsModule,
|
||||
BrowserModule,
|
||||
CommonModule,
|
||||
FlexLayoutModule,
|
||||
HttpClientModule,
|
||||
MatButtonModule,
|
||||
MatIconModule,
|
||||
MatToolbarModule,
|
||||
],
|
||||
providers: [],
|
||||
bootstrap: [AppComponent]
|
||||
bootstrap: [AppComponent],
|
||||
})
|
||||
export class AppModule { }
|
||||
export class AppModule {}
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
export enum Protocol {
|
||||
IPFS = "ipfs",
|
||||
IPNS = "ipns",
|
||||
}
|
|
@ -0,0 +1,4 @@
|
|||
export enum Theme {
|
||||
Light = "theme-light",
|
||||
Dark = "theme-dark",
|
||||
}
|
|
@ -1,5 +1,5 @@
|
|||
export interface Environment {
|
||||
production: boolean;
|
||||
base_href?: string;
|
||||
useHash: boolean;
|
||||
production: boolean
|
||||
base_href?: string
|
||||
useHash: boolean
|
||||
}
|
||||
|
|
|
@ -0,0 +1,9 @@
|
|||
{
|
||||
"name": "public-gateway-cacher",
|
||||
"private": true,
|
||||
"description_1": "This is a special package.json file that is not used by package managers.",
|
||||
"description_2": "It is used to tell the tools and bundlers whether the code under this directory is free of code with non-local side-effect. Any code that does have non-local side-effects can't be well optimized (tree-shaken) and will result in unnecessary increased payload size.",
|
||||
"description_3": "It should be safe to set this option to 'false' for new applications, but existing code bases could be broken when built with the production config if the application code does contain non-local side-effects that the application depends on.",
|
||||
"description_4": "To learn more about this file see: https://angular.io/config/app-package-json.",
|
||||
"sideEffects": false
|
||||
}
|
|
@ -1,14 +1,17 @@
|
|||
import { NgModule } from '@angular/core';
|
||||
import { RouterModule, Routes } from '@angular/router';
|
||||
import { PagesComponent } from './pages.component';
|
||||
import { NgModule } from "@angular/core"
|
||||
import type { Routes } from "@angular/router"
|
||||
import { RouterModule } from "@angular/router"
|
||||
import { PagesComponent } from "./pages.component"
|
||||
|
||||
const routes: Routes = [{
|
||||
path: '',
|
||||
const routes: Routes = [
|
||||
{
|
||||
path: "",
|
||||
component: PagesComponent,
|
||||
}];
|
||||
},
|
||||
]
|
||||
|
||||
@NgModule({
|
||||
imports: [RouterModule.forChild(routes)],
|
||||
exports: [RouterModule]
|
||||
exports: [RouterModule],
|
||||
})
|
||||
export class PagesRoutingModule { }
|
||||
export class PagesRoutingModule {}
|
||||
|
|
|
@ -1,84 +1,82 @@
|
|||
<div fxLayout="column" fxLayoutAlign="space-evenly center" fxLayoutGap="1em" class="container">
|
||||
|
||||
<h1>Public IPFS Cacher</h1>
|
||||
|
||||
<div class="container" fxLayout="column" fxLayoutAlign="space-evenly center" fxLayoutGap="1em">
|
||||
<!-- IPFS -->
|
||||
<form fxLayout="row" fxLayoutAlign="space-evenly center" fxLayoutGap="1em">
|
||||
|
||||
<!-- Hash -->
|
||||
<mat-form-field>
|
||||
<mat-form-field [color]="inputColour">
|
||||
<mat-label>IPFS</mat-label>
|
||||
<input matInput [(ngModel)]="ipfs" name="ipfs">
|
||||
<input name="ipfs" [(ngModel)]="ipfs" matInput />
|
||||
</mat-form-field>
|
||||
|
||||
<!-- Cache -->
|
||||
<button mat-flat-button color="primary" type="button" (click)="cacheIPFS()">Cache</button>
|
||||
|
||||
<button (click)="cacheIPFS()" type="button" mat-flat-button color="primary">Cache</button>
|
||||
</form>
|
||||
|
||||
<!-- IPNS -->
|
||||
<form fxLayout="row" fxLayoutAlign="space-evenly center" fxLayoutGap="1em">
|
||||
|
||||
<!-- Hash -->
|
||||
<mat-form-field>
|
||||
<mat-form-field [color]="inputColour">
|
||||
<mat-label>IPNS</mat-label>
|
||||
<input matInput [(ngModel)]="ipns" name="ipns">
|
||||
<input name="ipns" [(ngModel)]="ipns" matInput />
|
||||
</mat-form-field>
|
||||
|
||||
<!-- Cache -->
|
||||
<button mat-flat-button color="primary" type="button" (click)="cacheIPNS()">Cache</button>
|
||||
|
||||
<button (click)="cacheIPNS()" type="button" mat-flat-button color="primary">Cache</button>
|
||||
</form>
|
||||
|
||||
<mat-progress-bar *ngIf="subscriptions.length" mode="determinate" [value]="dataSource.data.length / gateways.length * 100">
|
||||
<mat-progress-bar
|
||||
[value]="(dataSource.data.length / gateways.length) * 100"
|
||||
*ngIf="subscriptions.length"
|
||||
mode="determinate"
|
||||
color="primary"
|
||||
>
|
||||
</mat-progress-bar>
|
||||
|
||||
<table mat-table [dataSource]="dataSource" class="mat-elevation-z8">
|
||||
|
||||
<table class="mat-elevation-z8" [dataSource]="dataSource" mat-table aria-label="List of IPFS gateways and their statuses.">
|
||||
<!-- Result Column -->
|
||||
<ng-container matColumnDef="error">
|
||||
<th mat-header-cell *matHeaderCellDef> Status </th>
|
||||
<ng-container matColumnDef="icon">
|
||||
<th mat-header-cell *matHeaderCellDef scope="col">Status</th>
|
||||
<td mat-cell *matCellDef="let element">
|
||||
<div [ngSwitch]="element.error">
|
||||
<div *ngSwitchCase="null">✅</div>
|
||||
<div *ngSwitchDefault [matTooltip]="element.error.statusText">❌</div>
|
||||
</div>
|
||||
<span [matTooltip]="element.message"> {{ element.icon }} </span>
|
||||
</td>
|
||||
</ng-container>
|
||||
|
||||
<!-- Gateway Column -->
|
||||
<ng-container matColumnDef="gateway">
|
||||
<th mat-header-cell *matHeaderCellDef> Gateway </th>
|
||||
<th mat-header-cell *matHeaderCellDef scope="col">Gateway</th>
|
||||
<td mat-cell *matCellDef="let element">
|
||||
<div [ngSwitch]="element.error">
|
||||
<div *ngSwitchCase="null">
|
||||
<strong><a href="{{ element.gateway }}#x-ipfs-companion-no-redirect" class="aqua"> {{ element.gateway }} </a></strong>
|
||||
<div [ngSwitch]="element.ok">
|
||||
<div *ngSwitchCase="true">
|
||||
<strong>
|
||||
<a class="aqua" href="{{ element.gateway }}#x-ipfs-companion-no-redirect" target="_blank">
|
||||
{{ element.gateway }}
|
||||
</a>
|
||||
</strong>
|
||||
</div>
|
||||
<div *ngSwitchDefault>
|
||||
<a href="{{ element.gateway }}#x-ipfs-companion-no-redirect" class="aqua-muted"> {{ element.gateway }} </a>
|
||||
<div *ngSwitchCase="false">
|
||||
<a class="aqua-muted" href="{{ element.gateway }}#x-ipfs-companion-no-redirect" target="_blank">
|
||||
{{ element.gateway }}
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</td>
|
||||
</ng-container>
|
||||
|
||||
<tr mat-header-row *matHeaderRowDef="displayedColumns"></tr>
|
||||
<tr mat-row *matRowDef="let row; columns: displayedColumns;"></tr>
|
||||
<tr mat-row *matRowDef="let row; columns: displayedColumns"></tr>
|
||||
</table>
|
||||
|
||||
<!-- About -->
|
||||
<div fxLayout="column" fxLayoutAlign="space-evenly start" fxLayoutGap="1em">
|
||||
<h3>About</h3>
|
||||
<p>
|
||||
This allows you to cache a specific IPFS hash to a bunch of public gateways.
|
||||
It's inspired from <a href="https://github.com/ipfs/public-gateway-checker">github.com/ipfs/public-gateway-checker</a>.
|
||||
The source code is available at <a
|
||||
href="https://gitlab.com/NatoBoram/public-gateway-cacher">gitlab.com/NatoBoram/public-gateway-cacher</a>.
|
||||
This allows you to cache a specific IPFS hash to a bunch of public gateways. It's inspired from
|
||||
<a class="link" href="https://github.com/ipfs/public-gateway-checker">github.com/ipfs/public-gateway-checker</a>. The source code is
|
||||
available at <a class="link" href="https://gitlab.com/NatoBoram/public-gateway-cacher">gitlab.com/NatoBoram/public-gateway-cacher</a>.
|
||||
</p>
|
||||
<p>
|
||||
If you'd like to add a new public gateway,
|
||||
please go to <a href="https://github.com/ipfs/public-gateway-checker">github.com/ipfs/public-gateway-checker</a>,
|
||||
submit a pull request then open an issue <a href="https://gitlab.com/NatoBoram/public-gateway-cacher/issues/new">here</a>.
|
||||
If you'd like to add a new public gateway, please go to
|
||||
<a class="link" href="https://github.com/ipfs/public-gateway-checker">github.com/ipfs/public-gateway-checker</a>, submit a pull
|
||||
request then open an issue <a class="link" href="https://gitlab.com/NatoBoram/public-gateway-cacher/issues/new">here</a>.
|
||||
</p>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
padding: 1em;
|
||||
}
|
||||
|
||||
.mat-column-error {
|
||||
.mat-column-icon {
|
||||
text-align: center;
|
||||
width: 5em;
|
||||
max-width: 100%;
|
||||
|
|
|
@ -1,24 +1,26 @@
|
|||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
import { PagesComponent } from './pages.component';
|
||||
import { HttpClientTestingModule } from "@angular/common/http/testing"
|
||||
import type { ComponentFixture } from "@angular/core/testing"
|
||||
import { TestBed, waitForAsync } from "@angular/core/testing"
|
||||
import { PagesComponent } from "./pages.component"
|
||||
|
||||
describe('PagesComponent', () => {
|
||||
let component: PagesComponent;
|
||||
let fixture: ComponentFixture<PagesComponent>;
|
||||
describe("PagesComponent", (): void => {
|
||||
let component: PagesComponent
|
||||
let fixture: ComponentFixture<PagesComponent>
|
||||
|
||||
beforeEach(async(() => {
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [PagesComponent]
|
||||
beforeEach(waitForAsync((): void => {
|
||||
void TestBed.configureTestingModule({
|
||||
imports: [HttpClientTestingModule],
|
||||
declarations: [PagesComponent],
|
||||
}).compileComponents()
|
||||
}))
|
||||
|
||||
beforeEach((): void => {
|
||||
fixture = TestBed.createComponent(PagesComponent)
|
||||
component = fixture.componentInstance
|
||||
fixture.detectChanges()
|
||||
})
|
||||
.compileComponents();
|
||||
}));
|
||||
|
||||
beforeEach(() => {
|
||||
fixture = TestBed.createComponent(PagesComponent);
|
||||
component = fixture.componentInstance;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
});
|
||||
it("should create", (): void => {
|
||||
void expect(component).toBeTruthy()
|
||||
})
|
||||
})
|
||||
|
|
|
@ -1,75 +1,151 @@
|
|||
import { HttpErrorResponse } from '@angular/common/http';
|
||||
import { Component, OnInit, ViewChild } from '@angular/core';
|
||||
import { MatTable, MatTableDataSource } from '@angular/material/table';
|
||||
import { Subscription } from 'rxjs';
|
||||
import { GatewayService } from '../services/gateway.service';
|
||||
import { HttpErrorResponse } from "@angular/common/http"
|
||||
import type { OnDestroy, OnInit } from "@angular/core"
|
||||
import { ChangeDetectionStrategy, Component, EventEmitter, Inject, ViewChild } from "@angular/core"
|
||||
import type { ThemePalette } from "@angular/material/core"
|
||||
import { MatTable, MatTableDataSource } from "@angular/material/table"
|
||||
import type { Subscription } from "rxjs"
|
||||
import { takeUntil } from "rxjs/operators"
|
||||
import { environment } from "../../environments/environment"
|
||||
import { Protocol } from "../enums/protocol.enum"
|
||||
import { Theme } from "../enums/theme.enum"
|
||||
import { GatewayService } from "../services/gateway.service"
|
||||
import { ThemeService } from "../services/theme.service"
|
||||
|
||||
@Component({
|
||||
selector: 'app-pages',
|
||||
templateUrl: './pages.component.html',
|
||||
styleUrls: ['./pages.component.scss']
|
||||
selector: "app-pages",
|
||||
templateUrl: "./pages.component.html",
|
||||
styleUrls: ["./pages.component.scss"],
|
||||
changeDetection: ChangeDetectionStrategy.OnPush,
|
||||
})
|
||||
export class PagesComponent implements OnInit {
|
||||
export class PagesComponent implements OnInit, OnDestroy {
|
||||
@ViewChild(MatTable) matTable!: MatTable<Result>
|
||||
|
||||
gateways: string[];
|
||||
ipfs: string;
|
||||
ipns: string;
|
||||
dataSource: MatTableDataSource<Result>;
|
||||
displayedColumns = [
|
||||
'error',
|
||||
'gateway',
|
||||
];
|
||||
subscriptions: Subscription[] = [];
|
||||
gateways!: string[]
|
||||
inputColour: ThemePalette = "primary"
|
||||
ipfs = ""
|
||||
ipns = ""
|
||||
|
||||
@ViewChild(MatTable, { static: false }) matTable: MatTable<Result>;
|
||||
readonly dataSource = new MatTableDataSource<Result>([])
|
||||
readonly displayedColumns = ["icon", "gateway"]
|
||||
readonly subscriptions: Subscription[] = []
|
||||
|
||||
private readonly destroy$ = new EventEmitter<void>()
|
||||
|
||||
constructor(
|
||||
private readonly gatewayService: GatewayService
|
||||
) { }
|
||||
@Inject(GatewayService) private readonly gatewayService: GatewayService,
|
||||
@Inject(ThemeService) private readonly themeService: ThemeService
|
||||
) {}
|
||||
|
||||
ngOnInit(): void {
|
||||
this.dataSource = new MatTableDataSource([]);
|
||||
this.gatewayService.list().subscribe(gateways => this.gateways = gateways);
|
||||
this.gatewayService
|
||||
.list()
|
||||
.pipe(takeUntil(this.destroy$))
|
||||
.subscribe((gateways): void => {
|
||||
this.gateways = gateways
|
||||
})
|
||||
|
||||
// Theme
|
||||
this.setColours(this.themeService.current)
|
||||
this.themeService.valueChanges.pipe(takeUntil(this.destroy$)).subscribe((theme): void => {
|
||||
this.setColours(theme)
|
||||
})
|
||||
}
|
||||
|
||||
ngOnDestroy(): void {
|
||||
this.destroy$.next()
|
||||
this.destroy$.complete()
|
||||
}
|
||||
|
||||
cacheIPFS(): void {
|
||||
this.cache('ipfs', this.ipfs);
|
||||
this.ipfs = this.ipfs.trim()
|
||||
this.cache(Protocol.IPFS, this.ipfs)
|
||||
}
|
||||
|
||||
cacheIPNS(): void {
|
||||
this.cache('ipns', this.ipns);
|
||||
this.ipns = this.ipns.trim()
|
||||
this.cache(Protocol.IPNS, this.ipns)
|
||||
}
|
||||
|
||||
cache(type: string, hash: string): void {
|
||||
|
||||
cache(protocol: Protocol, hashpath: string): void {
|
||||
// Clear subscriptions
|
||||
while (this.subscriptions.length) {
|
||||
const sub = this.subscriptions.pop();
|
||||
if (!sub.closed) {
|
||||
sub.unsubscribe();
|
||||
const sub = this.subscriptions.pop()
|
||||
if (sub && !sub.closed) {
|
||||
sub.unsubscribe()
|
||||
}
|
||||
}
|
||||
|
||||
this.dataSource.data = [];
|
||||
this.matTable.renderRows();
|
||||
console.clear();
|
||||
// Clear table
|
||||
this.dataSource.data = []
|
||||
this.matTable.renderRows()
|
||||
console.clear()
|
||||
|
||||
this.gateways.forEach(gateway => {
|
||||
this.gateways.forEach((gateway): void => {
|
||||
this.subscriptions.push(
|
||||
this.gatewayService.get(gateway, type, hash).subscribe(_ => {
|
||||
this.dataSource.data.push({ gateway: `${gateway.replace(':type', type).replace(':hash', hash)}`, error: null });
|
||||
this.matTable.renderRows();
|
||||
}, (error: HttpErrorResponse) => {
|
||||
this.dataSource.data.push({ gateway: `${gateway.replace(':type', type).replace(':hash', hash)}`, error });
|
||||
this.matTable.renderRows();
|
||||
this.gatewayService
|
||||
.get(gateway, protocol, hashpath)
|
||||
.pipe(takeUntil(this.destroy$))
|
||||
.subscribe(
|
||||
(resp): void => {
|
||||
this.dataSource.data.unshift({
|
||||
gateway: this.gatewayService.url(gateway, protocol, hashpath),
|
||||
message: resp.statusText,
|
||||
icon: this.getIcon(resp.status),
|
||||
ok: resp.ok,
|
||||
})
|
||||
);
|
||||
});
|
||||
this.matTable.renderRows()
|
||||
},
|
||||
(error: unknown): void => {
|
||||
if (!(error instanceof HttpErrorResponse)) return
|
||||
|
||||
this.dataSource.data.push({
|
||||
gateway: this.gatewayService.url(gateway, protocol, hashpath),
|
||||
message: error.statusText,
|
||||
icon: this.getIcon(error.status),
|
||||
ok: error.ok,
|
||||
})
|
||||
this.matTable.renderRows()
|
||||
}
|
||||
)
|
||||
)
|
||||
})
|
||||
}
|
||||
|
||||
private setColours(theme: Theme): void {
|
||||
switch (theme) {
|
||||
case Theme.Light:
|
||||
this.inputColour = "primary"
|
||||
break
|
||||
case Theme.Dark:
|
||||
this.inputColour = "accent"
|
||||
break
|
||||
default:
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
private getIcon(status: number): string {
|
||||
if (status >= 200 && status < 300) {
|
||||
return "✅"
|
||||
}
|
||||
switch (status) {
|
||||
case 0:
|
||||
return "❌"
|
||||
case 403:
|
||||
return "⛔"
|
||||
case 404:
|
||||
return "❓"
|
||||
case 500:
|
||||
return "❗"
|
||||
default:
|
||||
return environment.production ? "❌" : "❔"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
interface Result {
|
||||
gateway: string;
|
||||
error: HttpErrorResponse;
|
||||
gateway: string
|
||||
message: string
|
||||
icon: string
|
||||
ok: boolean
|
||||
}
|
||||
|
|
|
@ -1,15 +1,15 @@
|
|||
import { CommonModule } from '@angular/common';
|
||||
import { NgModule } from '@angular/core';
|
||||
import { FlexLayoutModule } from '@angular/flex-layout';
|
||||
import { FormsModule } from '@angular/forms';
|
||||
import { MatButtonModule } from '@angular/material/button';
|
||||
import { MatInputModule } from '@angular/material/input';
|
||||
import { MatProgressBarModule } from '@angular/material/progress-bar';
|
||||
import { MatSortModule } from '@angular/material/sort';
|
||||
import { MatTableModule } from '@angular/material/table';
|
||||
import { MatTooltipModule } from '@angular/material/tooltip';
|
||||
import { PagesRoutingModule } from './pages-routing.module';
|
||||
import { PagesComponent } from './pages.component';
|
||||
import { CommonModule } from "@angular/common"
|
||||
import { NgModule } from "@angular/core"
|
||||
import { FlexLayoutModule } from "@angular/flex-layout"
|
||||
import { FormsModule } from "@angular/forms"
|
||||
import { MatButtonModule } from "@angular/material/button"
|
||||
import { MatInputModule } from "@angular/material/input"
|
||||
import { MatProgressBarModule } from "@angular/material/progress-bar"
|
||||
import { MatSortModule } from "@angular/material/sort"
|
||||
import { MatTableModule } from "@angular/material/table"
|
||||
import { MatTooltipModule } from "@angular/material/tooltip"
|
||||
import { PagesRoutingModule } from "./pages-routing.module"
|
||||
import { PagesComponent } from "./pages.component"
|
||||
|
||||
@NgModule({
|
||||
declarations: [PagesComponent],
|
||||
|
@ -24,6 +24,6 @@ import { PagesComponent } from './pages.component';
|
|||
MatTableModule,
|
||||
MatTooltipModule,
|
||||
PagesRoutingModule,
|
||||
]
|
||||
],
|
||||
})
|
||||
export class PagesModule { }
|
||||
export class PagesModule {}
|
||||
|
|
|
@ -1,12 +1,18 @@
|
|||
import { TestBed } from '@angular/core/testing';
|
||||
import { HttpClientTestingModule } from "@angular/common/http/testing"
|
||||
import type { TestBedStatic } from "@angular/core/testing"
|
||||
import { TestBed } from "@angular/core/testing"
|
||||
import { GatewayService } from "./gateway.service"
|
||||
|
||||
import { GatewayService } from './gateway.service';
|
||||
describe("GatewayService", (): void => {
|
||||
beforeEach(
|
||||
(): TestBedStatic =>
|
||||
TestBed.configureTestingModule({
|
||||
imports: [HttpClientTestingModule],
|
||||
})
|
||||
)
|
||||
|
||||
describe('GatewayService', () => {
|
||||
beforeEach(() => TestBed.configureTestingModule({}));
|
||||
|
||||
it('should be created', () => {
|
||||
const service: GatewayService = TestBed.get(GatewayService);
|
||||
expect(service).toBeTruthy();
|
||||
});
|
||||
});
|
||||
it("should be created", (): void => {
|
||||
const service: GatewayService = TestBed.inject(GatewayService)
|
||||
void expect(service).toBeTruthy()
|
||||
})
|
||||
})
|
||||
|
|
|
@ -1,29 +1,34 @@
|
|||
import { HttpClient } from '@angular/common/http';
|
||||
import { Injectable } from '@angular/core';
|
||||
import { Observable } from 'rxjs';
|
||||
import { environment } from '../../environments/environment';
|
||||
import type { HttpResponse } from "@angular/common/http"
|
||||
import { HttpClient } from "@angular/common/http"
|
||||
import { Inject, Injectable } from "@angular/core"
|
||||
import type { Observable } from "rxjs"
|
||||
import { environment } from "../../environments/environment"
|
||||
import type { Protocol } from "../enums/protocol.enum"
|
||||
|
||||
@Injectable({
|
||||
providedIn: 'root'
|
||||
providedIn: "root",
|
||||
})
|
||||
export class GatewayService {
|
||||
|
||||
constructor(
|
||||
private readonly http: HttpClient
|
||||
) { }
|
||||
constructor(@Inject(HttpClient) private readonly http: HttpClient) {}
|
||||
|
||||
list(): Observable<string[]> {
|
||||
return this.http.get<string[]>(
|
||||
environment.base_href && environment.base_href !== '/'
|
||||
environment.base_href && environment.base_href !== "/"
|
||||
? `${environment.base_href}/assets/json/gateways.json`
|
||||
: `${document.querySelector('base').href}/assets/json/gateways.json`
|
||||
);
|
||||
: `${document.querySelector("base")?.href ?? ""}assets/json/gateways.json`
|
||||
)
|
||||
}
|
||||
|
||||
get(gateway: string, type: string, hash: string): Observable<Blob> {
|
||||
return this.http.get<Blob>(`${gateway.replace(':type', type).replace(':hash', hash)}#x-ipfs-companion-no-redirect`, {
|
||||
responseType: 'blob' as 'json'
|
||||
});
|
||||
get(gateway: string, protocol: Protocol, hashpath: string): Observable<HttpResponse<string>> {
|
||||
return this.http.get(`${this.url(gateway, protocol, hashpath)}#x-ipfs-companion-no-redirect`, {
|
||||
observe: "response",
|
||||
responseType: "text",
|
||||
})
|
||||
}
|
||||
|
||||
url(gateway: string, protocol: Protocol, hashpath: string): string {
|
||||
const splits: string[] = hashpath.split("/")
|
||||
const url: string = gateway.replaceAll(":type", protocol).replaceAll(":hash", splits.shift() ?? "")
|
||||
return splits.length ? [url, splits.join("/")].join("/") : url
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,15 @@
|
|||
import { TestBed } from "@angular/core/testing"
|
||||
import { ThemeService } from "./theme.service"
|
||||
|
||||
describe("ThemeService", (): void => {
|
||||
let service: ThemeService
|
||||
|
||||
beforeEach((): void => {
|
||||
TestBed.configureTestingModule({})
|
||||
service = TestBed.inject(ThemeService)
|
||||
})
|
||||
|
||||
it("should be created", (): void => {
|
||||
void expect(service).toBeTruthy()
|
||||
})
|
||||
})
|
|
@ -0,0 +1,51 @@
|
|||
import { Injectable } from "@angular/core"
|
||||
import type { Observable } from "rxjs"
|
||||
import { Subject } from "rxjs"
|
||||
import { Theme } from "../enums/theme.enum"
|
||||
|
||||
function enumGuard<T>(enumeration: T): (token: unknown) => token is T[keyof T] {
|
||||
return (token: unknown): token is T[keyof T] => Object.values(enumeration).includes(token)
|
||||
}
|
||||
|
||||
@Injectable({
|
||||
providedIn: "root",
|
||||
})
|
||||
export class ThemeService {
|
||||
current = Theme.Light
|
||||
icon = "brightness_low"
|
||||
readonly valueChanges: Observable<Theme>
|
||||
|
||||
private readonly subject$ = new Subject<Theme>()
|
||||
|
||||
constructor() {
|
||||
const stored = localStorage.getItem("theme")
|
||||
if (enumGuard(Theme)(stored)) {
|
||||
this.setTheme(stored)
|
||||
}
|
||||
|
||||
this.valueChanges = this.subject$.asObservable()
|
||||
}
|
||||
|
||||
switchTheme(): void {
|
||||
this.setTheme(this.current === Theme.Light ? Theme.Dark : Theme.Light)
|
||||
}
|
||||
|
||||
setTheme(theme: Theme): void {
|
||||
document.querySelector("body")?.classList.remove(this.current)
|
||||
document.querySelector("body")?.classList.add(theme)
|
||||
this.current = theme
|
||||
this.icon = this.getIcon(theme)
|
||||
this.subject$.next(theme)
|
||||
localStorage.setItem("theme", theme)
|
||||
}
|
||||
|
||||
getIcon(theme: Theme): string {
|
||||
switch (theme) {
|
||||
case Theme.Dark:
|
||||
return "brightness_high"
|
||||
case Theme.Light:
|
||||
default:
|
||||
return "brightness_low"
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,23 +1,18 @@
|
|||
[
|
||||
"https://ipfs.io/:type/:hash",
|
||||
"https://dweb.link/:type/:hash",
|
||||
"https://gateway.ipfs.io/:type/:hash",
|
||||
"https://ipfs.infura.io/:type/:hash",
|
||||
"https://rx14.co.uk/:type/:hash",
|
||||
"https://infura-ipfs.io/:type/:hash",
|
||||
"https://ninetailed.ninja/:type/:hash",
|
||||
"https://ipfs.globalupload.io/:hash",
|
||||
"https://ipfs.jes.xxx/:type/:hash",
|
||||
"https://siderus.io/:type/:hash",
|
||||
"https://eu.siderus.io/:type/:hash",
|
||||
"https://na.siderus.io/:type/:hash",
|
||||
"https://ap.siderus.io/:type/:hash",
|
||||
"https://10.via0.com/:type/:hash",
|
||||
"https://via0.com/:type/:hash",
|
||||
"https://ipfs.eternum.io/:type/:hash",
|
||||
"https://hardbin.com/:type/:hash",
|
||||
"https://ipfs.wa.hle.rs/:type/:hash",
|
||||
"https://gateway.blocksec.com/:type/:hash",
|
||||
"https://ipfs.renehsz.com/:type/:hash",
|
||||
"https://cloudflare-ipfs.com/:type/:hash",
|
||||
"https://ipns.co/:hash",
|
||||
"https://astyanax.io/:type/:hash",
|
||||
"https://cf-ipfs.com/:type/:hash",
|
||||
"https://ipns.co/:type/:hash",
|
||||
"https://ipfs.mrh.io/:type/:hash",
|
||||
"https://gateway.originprotocol.com/:type/:hash",
|
||||
"https://gateway.pinata.cloud/:type/:hash",
|
||||
|
@ -26,14 +21,76 @@
|
|||
"https://ipfs.busy.org/:type/:hash",
|
||||
"https://ipfs.greyh.at/:type/:hash",
|
||||
"https://gateway.serph.network/:type/:hash",
|
||||
"https://jorropo.ovh/:type/:hash",
|
||||
"https://gateway.temporal.cloud/:type/:hash",
|
||||
"https://jorropo.net/:type/:hash",
|
||||
"https://ipfs.fooock.com/:type/:hash",
|
||||
"https://cdn.cwinfo.net/:type/:hash",
|
||||
"https://ipfs.privacytools.io/:type/:hash",
|
||||
"https://ipfs.jeroendeneef.com/:type/:hash",
|
||||
"https://aragon.ventures/:type/:hash",
|
||||
"https://ipfs-cdn.aragon.ventures/:type/:hash",
|
||||
"https://permaweb.io/:type/:hash",
|
||||
"https://ipfs.stibarc.gq/:type/:hash",
|
||||
"https://ipfs.best-practice.se/:type/:hash",
|
||||
"https://lineageos-on-ipfs.com/:type/:hash"
|
||||
"https://storjipfs-gateway.com/:type/:hash",
|
||||
"https://ipfs.runfission.com/:type/:hash",
|
||||
"https://ipfs.trusti.id/:type/:hash",
|
||||
"https://ipfs.overpi.com/:type/:hash",
|
||||
"https://gateway.ipfs.lc/:type/:hash",
|
||||
"https://ipfs.ink/:type/:hash",
|
||||
"https://ipfsgateway.makersplace.com/:type/:hash",
|
||||
"https://gateway.ravenland.org/:type/:hash",
|
||||
"https://ipfs.funnychain.co/:type/:hash",
|
||||
"https://ipfs.telos.miami/:type/:hash",
|
||||
"https://ipfs.mttk.net/:type/:hash",
|
||||
"https://ipfs.fleek.co/:type/:hash",
|
||||
"https://ipfs.jbb.one/:type/:hash",
|
||||
"https://ipfs.yt/:type/:hash",
|
||||
"https://hashnews.k1ic.com/:type/:hash",
|
||||
"https://ipfs.vip/:type/:hash",
|
||||
"https://ipfs.drink.cafe/:type/:hash",
|
||||
"https://ipfs.azurewebsites.net/:type/:hash",
|
||||
"https://gw.ipfspin.com/:type/:hash",
|
||||
"https://ipfs.kavin.rocks/:type/:hash",
|
||||
"https://ipfs.denarius.io/:type/:hash",
|
||||
"https://ipfs.mihir.ch/:type/:hash",
|
||||
"https://crustwebsites.net/:type/:hash",
|
||||
"https://ipfs0.sjc.cloudsigma.com/:type/:hash",
|
||||
"http://ipfs.genenetwork.org/:type/:hash",
|
||||
"https://ipfs.eth.aragon.network/:type/:hash",
|
||||
"https://ipfs.smartholdem.io/:type/:hash",
|
||||
"https://ipfs.xoqq.ch/:type/:hash",
|
||||
"https://natoboram.mynetgear.com/:type/:hash",
|
||||
"https://video.oneloveipfs.com/:type/:hash",
|
||||
"http://ipfs.anonymize.com/:type/:hash",
|
||||
"https://ipfs.taxi/:type/:hash",
|
||||
"https://ipfs.scalaproject.io/:type/:hash",
|
||||
"https://search.ipfsgate.com/:type/:hash",
|
||||
"https://ipfs.decoo.io/:type/:hash",
|
||||
"https://ivoputzer.xyz/:type/:hash",
|
||||
"https://alexdav.id/:type/:hash",
|
||||
"https://ipfs.uploads.nu/:type/:hash",
|
||||
"https://hub.textile.io/:type/:hash",
|
||||
"https://ipfs1.pixura.io/:type/:hash",
|
||||
"https://ravencoinipfs-gateway.com/:type/:hash",
|
||||
"https://konubinix.eu/:type/:hash",
|
||||
"https://3cloud.ee/:type/:hash",
|
||||
"https://ipfs.tubby.cloud/:type/:hash",
|
||||
"https://ipfs.lain.la/:type/:hash",
|
||||
"https://ipfs.adatools.io/:type/:hash",
|
||||
"https://ipfs.kaleido.art/:type/:hash",
|
||||
"https://ipfs.slang.cx/:type/:hash",
|
||||
"https://ipfs.arching-kaos.com/:type/:hash",
|
||||
"https://storry.tv/:type/:hash",
|
||||
"https://ipfs.kxv.io/:type/:hash",
|
||||
"https://ipfs.1-2.dev/:type/:hash",
|
||||
"https://ipfs-nosub.stibarc.com/:type/:hash",
|
||||
"https://dweb.eu.org/:type/:hash",
|
||||
"https://permaweb.eu.org/:type/:hash",
|
||||
"https://ipfs.namebase.io/:type/:hash",
|
||||
"https://ipfs.tribecap.co/:type/:hash",
|
||||
"https://ipfs.kinematiks.com/:type/:hash",
|
||||
"https://c4rex.co/:type/:hash",
|
||||
"https://ipfs.zod.tv/:type/:hash",
|
||||
"https://nftstorage.link/:type/:hash",
|
||||
"https://gravity.jup.io/:type/:hash",
|
||||
"http://fzdqwfb5ml56oadins5jpuhe6ki6bk33umri35p5kt2tue4fpws5efid.onion/:type/:hash",
|
||||
"https://tth-ipfs.com/:type/:hash",
|
||||
"https://:type.natoboram.com/:type/:hash"
|
||||
]
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
import { Environment } from '../app/interfaces/environment';
|
||||
import type { Environment } from "../app/interfaces/environment"
|
||||
|
||||
export const environment: Environment = {
|
||||
production: true,
|
||||
base_href: '/public-gateway-cacher',
|
||||
base_href: "/public-gateway-cacher",
|
||||
useHash: false,
|
||||
};
|
||||
}
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
import { Environment } from '../app/interfaces/environment';
|
||||
import type { Environment } from "../app/interfaces/environment"
|
||||
|
||||
export const environment: Environment = {
|
||||
production: true,
|
||||
useHash: true,
|
||||
};
|
||||
}
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
import { Environment } from '../app/interfaces/environment';
|
||||
import type { Environment } from "../app/interfaces/environment"
|
||||
|
||||
export const environment: Environment = {
|
||||
production: true,
|
||||
base_href: '/',
|
||||
base_href: "/",
|
||||
useHash: false,
|
||||
};
|
||||
}
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import { Environment } from '../app/interfaces/environment';
|
||||
import type { Environment } from "../app/interfaces/environment"
|
||||
|
||||
// This file can be replaced during build by using the `fileReplacements` array.
|
||||
// `ng build --prod` replaces `environment.ts` with `environment.prod.ts`.
|
||||
|
@ -6,9 +6,9 @@ import { Environment } from '../app/interfaces/environment';
|
|||
|
||||
export const environment: Environment = {
|
||||
production: false,
|
||||
base_href: '/',
|
||||
base_href: "/",
|
||||
useHash: false,
|
||||
};
|
||||
}
|
||||
|
||||
/*
|
||||
* For easier debugging in development mode, you can import the following file
|
||||
|
@ -17,4 +17,4 @@ export const environment: Environment = {
|
|||
* This import should be commented out in production mode because it will have a negative impact
|
||||
* on performance if an error is thrown.
|
||||
*/
|
||||
// import 'zone.js/dist/zone-error'; // Included with Angular CLI.
|
||||
// import 'zone.js/plugins/zone-error'; // Included with Angular CLI.
|
||||
|
|
|
@ -1,29 +1,23 @@
|
|||
<!doctype html>
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
<title>Public Gateway Cacher</title>
|
||||
|
||||
<!-- IPFS -->
|
||||
<script>
|
||||
if (document.getElementsByTagName('base').length === 0) document.write('<base href="' + window.location.pathname + '"/>');
|
||||
if (document.getElementsByTagName("base").length === 0) document.write('<base href="' + window.location.pathname + '"/>')
|
||||
</script>
|
||||
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1">
|
||||
<link rel="icon" type="image/x-icon" href="favicon.png">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
||||
<link rel="icon" type="image/x-icon" href="favicon.png" />
|
||||
|
||||
<!-- Material -->
|
||||
<link href="https://fonts.googleapis.com/css?family=Roboto:300,400,500&display=swap" rel="stylesheet">
|
||||
<link href="https://fonts.googleapis.com/icon?family=Material+Icons" rel="stylesheet">
|
||||
<link href="https://fonts.googleapis.com/css?family=Roboto:300,400,500&display=swap" rel="stylesheet" />
|
||||
<link href="https://fonts.googleapis.com/icon?family=Material+Icons" rel="stylesheet" />
|
||||
</head>
|
||||
|
||||
<!-- IPFS-CSS -->
|
||||
<link href="assets/ipfs-css/ipfs.css" rel="stylesheet">
|
||||
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<body class="mat-app-background theme-light">
|
||||
<app-root></app-root>
|
||||
</body>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
|
|
16
src/main.ts
16
src/main.ts
|
@ -1,12 +1,12 @@
|
|||
import { enableProdMode } from '@angular/core';
|
||||
import { platformBrowserDynamic } from '@angular/platform-browser-dynamic';
|
||||
import 'hammerjs';
|
||||
import { AppModule } from './app/app.module';
|
||||
import { environment } from './environments/environment';
|
||||
import { enableProdMode } from "@angular/core"
|
||||
import { platformBrowserDynamic } from "@angular/platform-browser-dynamic"
|
||||
import { AppModule } from "./app/app.module"
|
||||
import { environment } from "./environments/environment"
|
||||
|
||||
if (environment.production) {
|
||||
enableProdMode();
|
||||
enableProdMode()
|
||||
}
|
||||
|
||||
platformBrowserDynamic().bootstrapModule(AppModule)
|
||||
.catch(err => console.error(err));
|
||||
platformBrowserDynamic()
|
||||
.bootstrapModule(AppModule)
|
||||
.catch((err): void => console.error(err))
|
||||
|
|
|
@ -18,16 +18,6 @@
|
|||
* BROWSER POLYFILLS
|
||||
*/
|
||||
|
||||
/** IE10 and IE11 requires the following for NgClass support on SVG elements */
|
||||
// import 'classlist.js'; // Run `npm install --save classlist.js`.
|
||||
|
||||
/**
|
||||
* Web Animations `@angular/platform-browser/animations`
|
||||
* Only required if AnimationBuilder is used within the application and using IE/Edge or Safari.
|
||||
* Standard animation support in Angular DOES NOT require any polyfills (as of Angular 6.0).
|
||||
*/
|
||||
// import 'web-animations-js'; // Run `npm install --save web-animations-js`.
|
||||
|
||||
/**
|
||||
* By default, zone.js will patch all possible macroTask and DomEvents
|
||||
* user can disable parts of macroTask/DomEvents patch by setting following flags
|
||||
|
@ -55,8 +45,7 @@
|
|||
/***************************************************************************************************
|
||||
* Zone JS is required by default for Angular itself.
|
||||
*/
|
||||
import 'zone.js/dist/zone'; // Included with Angular CLI.
|
||||
|
||||
import "zone.js" // Included with Angular CLI.
|
||||
|
||||
/***************************************************************************************************
|
||||
* APPLICATION IMPORTS
|
||||
|
|
|
@ -1,29 +1,39 @@
|
|||
// Custom Theming for Angular Material
|
||||
@use "@angular/material" as mat;
|
||||
// For more information: https://material.angular.io/guide/theming
|
||||
@import '~@angular/material/theming';
|
||||
// Plus imports for other components in your app.
|
||||
|
||||
// Include the common styles for Angular Material. We include this here so that you only
|
||||
// have to load a single css file for Angular Material in your app.
|
||||
// Be sure that you only ever include this mixin once!
|
||||
@include mat-core();
|
||||
@include mat.core();
|
||||
|
||||
// Define the palettes for your theme using the Material Design palettes available in palette.scss
|
||||
// (imported above). For each palette, you can optionally specify a default, lighter, and darker
|
||||
// hue. Available color palettes: https://material.io/design/color/
|
||||
$public-gateway-cacher-primary: mat-palette($mat-indigo);
|
||||
$public-gateway-cacher-accent: mat-palette($mat-pink, A200, A100, A400);
|
||||
// // Define the palettes for your theme using the Material Design palettes available in palette.scss
|
||||
// // (imported above). For each palette, you can optionally specify a default, lighter, and darker
|
||||
// // hue. Available color palettes: https://material.io/design/color/
|
||||
// $public-gateway-cacher-primary: mat-palette($mat-indigo);
|
||||
// $public-gateway-cacher-accent: mat-palette($mat-pink, A200, A100, A400);
|
||||
|
||||
// The warn palette is optional (defaults to red).
|
||||
$public-gateway-cacher-warn: mat-palette($mat-red);
|
||||
// // The warn palette is optional (defaults to red).
|
||||
// $public-gateway-cacher-warn: mat-palette($mat-red);
|
||||
|
||||
// Create the theme object (a Sass map containing all of the palettes).
|
||||
$public-gateway-cacher-theme: mat-light-theme($public-gateway-cacher-primary, $public-gateway-cacher-accent, $public-gateway-cacher-warn);
|
||||
// // Create the theme object (a Sass map containing all of the palettes).
|
||||
// $public-gateway-cacher-theme: mat-light-theme($public-gateway-cacher-primary, $public-gateway-cacher-accent, $public-gateway-cacher-warn);
|
||||
|
||||
// Include theme styles for core and each component used in your app.
|
||||
// Alternatively, you can import and @include the theme mixins for each component
|
||||
// that you are using.
|
||||
@include angular-material-theme($public-gateway-cacher-theme);
|
||||
// // Include theme styles for core and each component used in your app.
|
||||
// // Alternatively, you can import and @include the theme mixins for each component
|
||||
// // that you are using.
|
||||
// @include angular-material-theme($public-gateway-cacher-theme);
|
||||
|
||||
@import "styles/ipfs-themes.scss";
|
||||
|
||||
.theme-light {
|
||||
@include mat.all-component-themes($ipfs-light-theme);
|
||||
}
|
||||
|
||||
.theme-dark {
|
||||
@include mat.all-component-themes($ipfs-dark-theme);
|
||||
}
|
||||
|
||||
/* You can add global styles to this file, and also import other style files */
|
||||
|
||||
|
@ -37,4 +47,5 @@ body {
|
|||
font-family: Roboto, "Helvetica Neue", sans-serif;
|
||||
}
|
||||
|
||||
@import '~bootstrap/scss/bootstrap-grid.scss';
|
||||
@import "~bootstrap/scss/bootstrap-grid.scss";
|
||||
@import "~ipfs-css/theme.scss";
|
||||
|
|
|
@ -0,0 +1,34 @@
|
|||
@import "@angular/material/core/theming/palette";
|
||||
|
||||
$ipfs-colour-navy: (
|
||||
default: #0b3a53,
|
||||
lighter: #3e6480,
|
||||
darker: #00142a,
|
||||
contrast: (
|
||||
default: $light-primary-text,
|
||||
lighter: $light-primary-text,
|
||||
darker: $light-primary-text,
|
||||
),
|
||||
);
|
||||
|
||||
$ipfs-colour-aqua: (
|
||||
default: #69c5cd,
|
||||
lighter: #9df8ff,
|
||||
darker: #32949c,
|
||||
contrast: (
|
||||
default: $dark-primary-text,
|
||||
lighter: $dark-primary-text,
|
||||
darker: $dark-primary-text,
|
||||
),
|
||||
);
|
||||
|
||||
$ipfs-colour-yellow: (
|
||||
default: #f39021,
|
||||
lighter: #ffc155,
|
||||
darker: #bb6200,
|
||||
contrast: (
|
||||
default: $dark-primary-text,
|
||||
lighter: $dark-primary-text,
|
||||
darker: $dark-primary-text,
|
||||
),
|
||||
);
|
|
@ -0,0 +1,6 @@
|
|||
@use "@angular/material" as mat;
|
||||
@import "ipfs-colours.scss";
|
||||
|
||||
$ipfs-primary: mat.define-palette($ipfs-colour-navy, "default", "lighter", "darker");
|
||||
$ipfs-accent: mat.define-palette($ipfs-colour-aqua, "default", "lighter", "darker");
|
||||
$ipfs-warn: mat.define-palette($ipfs-colour-yellow, "default", "lighter", "darker");
|
|
@ -0,0 +1,5 @@
|
|||
@use "@angular/material" as mat;
|
||||
@import "ipfs-palettes.scss";
|
||||
|
||||
$ipfs-light-theme: mat.define-light-theme($ipfs-primary, $ipfs-accent, $ipfs-warn);
|
||||
$ipfs-dark-theme: mat.define-dark-theme($ipfs-primary, $ipfs-accent, $ipfs-warn);
|
22
src/test.ts
22
src/test.ts
|
@ -1,20 +1,16 @@
|
|||
// This file is required by karma.conf.js and loads recursively all the .spec and framework files
|
||||
import "zone.js/testing"
|
||||
|
||||
import 'zone.js/dist/zone-testing';
|
||||
import { getTestBed } from '@angular/core/testing';
|
||||
import {
|
||||
BrowserDynamicTestingModule,
|
||||
platformBrowserDynamicTesting
|
||||
} from '@angular/platform-browser-dynamic/testing';
|
||||
import { getTestBed } from "@angular/core/testing"
|
||||
import { BrowserDynamicTestingModule, platformBrowserDynamicTesting } from "@angular/platform-browser-dynamic/testing"
|
||||
|
||||
declare const require: any;
|
||||
declare const require: any
|
||||
|
||||
// First, initialize the Angular testing environment.
|
||||
getTestBed().initTestEnvironment(
|
||||
BrowserDynamicTestingModule,
|
||||
platformBrowserDynamicTesting()
|
||||
);
|
||||
getTestBed().initTestEnvironment(BrowserDynamicTestingModule, platformBrowserDynamicTesting(), { teardown: { destroyAfterEach: false } })
|
||||
|
||||
// Then we find all the tests.
|
||||
const context = require.context('./', true, /\.spec\.ts$/);
|
||||
const context = require.context("./", true, /\.spec\.ts$/)
|
||||
|
||||
// And load the modules.
|
||||
context.keys().map(context);
|
||||
context.keys().map(context)
|
||||
|
|
|
@ -1,17 +1,10 @@
|
|||
/* To learn more about this file see: https://angular.io/config/tsconfig. */
|
||||
{
|
||||
"extends": "./tsconfig.json",
|
||||
"compilerOptions": {
|
||||
"outDir": "./out-tsc/app",
|
||||
"types": []
|
||||
},
|
||||
"files": [
|
||||
"src/main.ts",
|
||||
"src/polyfills.ts"
|
||||
],
|
||||
"include": [
|
||||
"src/**/*.d.ts"
|
||||
],
|
||||
"angularCompilerOptions": {
|
||||
"enableIvy": false
|
||||
}
|
||||
"files": ["src/main.ts", "src/polyfills.ts"],
|
||||
"include": ["src/**/*.d.ts"]
|
||||
}
|
||||
|
|
|
@ -1,26 +1,40 @@
|
|||
/* To learn more about this file see: https://angular.io/config/tsconfig. */
|
||||
{
|
||||
"compileOnSave": false,
|
||||
"compilerOptions": {
|
||||
"baseUrl": "./",
|
||||
"outDir": "./dist/out-tsc",
|
||||
"forceConsistentCasingInFileNames": true,
|
||||
"strict": true,
|
||||
"noImplicitAny": true,
|
||||
"strictNullChecks": true,
|
||||
"strictFunctionTypes": true,
|
||||
"strictBindCallApply": true,
|
||||
"strictPropertyInitialization": true,
|
||||
"noImplicitThis": true,
|
||||
"useUnknownInCatchVariables": true,
|
||||
"alwaysStrict": true,
|
||||
"noUnusedLocals": true,
|
||||
"noUnusedParameters": true,
|
||||
"exactOptionalPropertyTypes": true,
|
||||
"noImplicitReturns": true,
|
||||
"noFallthroughCasesInSwitch": true,
|
||||
"noUncheckedIndexedAccess": true,
|
||||
"noImplicitOverride": true,
|
||||
"noPropertyAccessFromIndexSignature": true,
|
||||
"sourceMap": true,
|
||||
"declaration": false,
|
||||
"downlevelIteration": true,
|
||||
"experimentalDecorators": true,
|
||||
"module": "esnext",
|
||||
"moduleResolution": "node",
|
||||
"importHelpers": true,
|
||||
"target": "es2015",
|
||||
"typeRoots": [
|
||||
"node_modules/@types"
|
||||
],
|
||||
"lib": [
|
||||
"es2018",
|
||||
"dom"
|
||||
]
|
||||
"target": "ESNext",
|
||||
"module": "ESNext",
|
||||
"lib": ["ESNext", "DOM"]
|
||||
},
|
||||
"angularCompilerOptions": {
|
||||
"fullTemplateTypeCheck": true,
|
||||
"strictInjectionParameters": true
|
||||
"strictInjectionParameters": true,
|
||||
"strictTemplates": true
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,21 +1,10 @@
|
|||
/* To learn more about this file see: https://angular.io/config/tsconfig. */
|
||||
{
|
||||
"extends": "./tsconfig.json",
|
||||
"compilerOptions": {
|
||||
"outDir": "./out-tsc/spec",
|
||||
"types": [
|
||||
"jasmine",
|
||||
"node"
|
||||
]
|
||||
"types": ["jasmine"]
|
||||
},
|
||||
"files": [
|
||||
"src/test.ts",
|
||||
"src/polyfills.ts"
|
||||
],
|
||||
"include": [
|
||||
"src/**/*.spec.ts",
|
||||
"src/**/*.d.ts"
|
||||
],
|
||||
"angularCompilerOptions": {
|
||||
"enableIvy": false
|
||||
}
|
||||
"files": ["src/test.ts", "src/polyfills.ts"],
|
||||
"include": ["src/**/*.spec.ts", "src/**/*.d.ts"]
|
||||
}
|
||||
|
|
279
tslint.json
279
tslint.json
|
@ -1,279 +0,0 @@
|
|||
{
|
||||
"extends": [
|
||||
"tslint:recommended",
|
||||
"rxjs-tslint-rules"
|
||||
],
|
||||
"rules": {
|
||||
"array-type": false,
|
||||
"arrow-parens": false,
|
||||
"deprecation": {
|
||||
"severity": "warning"
|
||||
},
|
||||
"component-class-suffix": true,
|
||||
"contextual-lifecycle": true,
|
||||
"directive-class-suffix": true,
|
||||
"directive-selector": [
|
||||
true,
|
||||
"attribute",
|
||||
"app",
|
||||
"camelCase"
|
||||
],
|
||||
"component-selector": [
|
||||
true,
|
||||
"element",
|
||||
"app",
|
||||
"kebab-case"
|
||||
],
|
||||
"import-blacklist": [
|
||||
true,
|
||||
"rxjs/Rx"
|
||||
],
|
||||
"interface-name": false,
|
||||
"max-classes-per-file": false,
|
||||
"max-line-length": [
|
||||
true,
|
||||
{
|
||||
"limit": 140,
|
||||
"ignore-pattern": "^import |^export {(.*?)}|class [a-zA-Z]+ implements |// "
|
||||
}
|
||||
],
|
||||
"member-access": false,
|
||||
"member-ordering": [
|
||||
true,
|
||||
{
|
||||
"order": [
|
||||
"public-static-field",
|
||||
"private-static-field",
|
||||
"public-instance-field",
|
||||
"private-instance-field",
|
||||
"public-constructor",
|
||||
"private-constructor",
|
||||
"public-instance-method",
|
||||
"protected-instance-method",
|
||||
"private-instance-method",
|
||||
"public-static-method",
|
||||
"protected-static-method",
|
||||
"private-static-method"
|
||||
]
|
||||
}
|
||||
],
|
||||
"no-consecutive-blank-lines": [
|
||||
true,
|
||||
1
|
||||
],
|
||||
"no-console": [
|
||||
true,
|
||||
"debug",
|
||||
"info",
|
||||
"time",
|
||||
"timeEnd",
|
||||
"trace"
|
||||
],
|
||||
"no-empty": [
|
||||
true,
|
||||
"allow-empty-functions"
|
||||
],
|
||||
"no-inferrable-types": [
|
||||
true,
|
||||
"ignore-params"
|
||||
],
|
||||
"no-non-null-assertion": true,
|
||||
"no-redundant-jsdoc": true,
|
||||
"no-switch-case-fall-through": true,
|
||||
"no-use-before-declare": true,
|
||||
"no-var-requires": false,
|
||||
"object-literal-key-quotes": [
|
||||
true,
|
||||
"as-needed"
|
||||
],
|
||||
"object-literal-sort-keys": false,
|
||||
"ordered-imports": false,
|
||||
"quotemark": [
|
||||
true,
|
||||
"single"
|
||||
],
|
||||
"no-conflicting-lifecycle": true,
|
||||
"no-host-metadata-property": true,
|
||||
"no-input-rename": true,
|
||||
"no-inputs-metadata-property": true,
|
||||
"no-output-native": true,
|
||||
"no-output-on-prefix": true,
|
||||
"no-output-rename": true,
|
||||
"no-outputs-metadata-property": true,
|
||||
"template-banana-in-box": true,
|
||||
"template-no-negated-async": true,
|
||||
"use-lifecycle-interface": true,
|
||||
"use-pipe-transform-interface": true,
|
||||
"origin-ordered-imports": [
|
||||
true
|
||||
],
|
||||
"rx-subject-restrictions": true,
|
||||
"ban-types": [
|
||||
true,
|
||||
[
|
||||
"Object",
|
||||
"Use {} instead."
|
||||
],
|
||||
[
|
||||
"String"
|
||||
]
|
||||
],
|
||||
"no-unnecessary-class": [
|
||||
true,
|
||||
"allow-constructor-only",
|
||||
"allow-static-only",
|
||||
"allow-empty-class"
|
||||
],
|
||||
"no-for-in-array": true,
|
||||
"typedef": [
|
||||
true,
|
||||
"call-signature",
|
||||
"property-declaration",
|
||||
"object-destructuring",
|
||||
"arrow-call-signature"
|
||||
],
|
||||
"no-unused": true,
|
||||
"no-return-undefined": true,
|
||||
"no-collapsible-if": true,
|
||||
"arrow-return-shorthand": [
|
||||
true,
|
||||
"multiline"
|
||||
],
|
||||
"no-static-this": true,
|
||||
"template-use-track-by-function": true,
|
||||
"prefer-template": true,
|
||||
"contextual-decorator": false,
|
||||
"no-pipe-impure": true,
|
||||
"component-max-inline-declarations": true,
|
||||
"no-attribute-decorator": true,
|
||||
"no-forward-ref": true,
|
||||
"no-lifecycle-call": true,
|
||||
"template-no-call-expression": true,
|
||||
"no-unused-css": true,
|
||||
"prefer-output-readonly": true,
|
||||
"template-conditional-complexity": true,
|
||||
"use-pipe-decorator": true,
|
||||
"use-component-view-encapsulation": true,
|
||||
"no-queries-metadata-property": true,
|
||||
"prefer-inline-decorator": false,
|
||||
"import-destructuring-spacing": true,
|
||||
"newline-before-return": false,
|
||||
"no-trailing-whitespace": true,
|
||||
"space-within-parens": true,
|
||||
"space-before-function-paren": [
|
||||
true,
|
||||
{
|
||||
"anonymous": "never",
|
||||
"named": "never",
|
||||
"asyncArrow": "always",
|
||||
"method": "never",
|
||||
"constructor": "never"
|
||||
}
|
||||
],
|
||||
"max-file-line-count": [
|
||||
true,
|
||||
400
|
||||
],
|
||||
"cyclomatic-complexity": [
|
||||
true,
|
||||
20
|
||||
],
|
||||
"encoding": true,
|
||||
"no-unsafe-finally": true,
|
||||
"no-duplicate-switch-case": true,
|
||||
"increment-decrement": [
|
||||
true,
|
||||
"allow-post"
|
||||
],
|
||||
"triple-equals": [
|
||||
true,
|
||||
"allow-null-check"
|
||||
],
|
||||
"no-invalid-template-strings": true,
|
||||
"no-unnecessary-type-assertion": true,
|
||||
"callable-types": true,
|
||||
"no-reference": true,
|
||||
"no-default-import": true,
|
||||
"no-default-export": true,
|
||||
"no-require-imports": true,
|
||||
"no-duplicate-imports": true,
|
||||
"no-import-side-effect": [
|
||||
true,
|
||||
{
|
||||
"ignore-module": "(hammerjs|core-js|zone.js)"
|
||||
}
|
||||
],
|
||||
"no-implicit-dependencies": [
|
||||
true,
|
||||
"dev"
|
||||
],
|
||||
"no-unnecessary-initializer": true,
|
||||
"no-var-keyword": true,
|
||||
"prefer-const": true,
|
||||
"no-return-await": true,
|
||||
"no-unnecessary-callback-wrapper": true,
|
||||
"no-arg": true,
|
||||
"eofline": true,
|
||||
"no-tautology-expression": true,
|
||||
"use-isnan": true,
|
||||
"restrict-plus-operands": true,
|
||||
"no-this-assignment": true,
|
||||
"no-invalid-this": [
|
||||
true,
|
||||
"check-function-in-method"
|
||||
],
|
||||
"no-unbound-method": true,
|
||||
"prefer-readonly": true,
|
||||
"radix": false,
|
||||
"no-misused-new": true,
|
||||
"no-duplicate-super": true,
|
||||
"rxjs-no-compat": true,
|
||||
"rxjs-no-internal": true,
|
||||
"unnecessary-else": [
|
||||
true,
|
||||
{
|
||||
"allow-else-if": true
|
||||
}
|
||||
],
|
||||
"no-any": [
|
||||
true,
|
||||
{
|
||||
"ignore-rest-args": true
|
||||
}
|
||||
],
|
||||
"variable-name": {
|
||||
"options": [
|
||||
"ban-keywords",
|
||||
"check-format",
|
||||
"allow-leading-underscore",
|
||||
"allow-pascal-case"
|
||||
]
|
||||
},
|
||||
"trailing-comma": [
|
||||
true,
|
||||
{
|
||||
"multiline": {
|
||||
"objects": "ignore",
|
||||
"arrays": "ignore",
|
||||
"functions": "never",
|
||||
"typeLiterals": "ignore"
|
||||
},
|
||||
"esSpecCompliant": true
|
||||
}
|
||||
]
|
||||
},
|
||||
"rulesDirectory": [
|
||||
"codelyzer",
|
||||
"node_modules/tslint-origin-ordered-imports-rule/dist",
|
||||
"node_modules/tslint-rxjs-subject-restrictions-rule/dist",
|
||||
"node_modules/tslint-consistent-codestyle/rules"
|
||||
],
|
||||
"linterOptions": {
|
||||
"exclude": [
|
||||
"**/*-routing.module.ts",
|
||||
"src/polyfills.ts",
|
||||
"src/test.ts",
|
||||
"**/*.po.ts"
|
||||
]
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue