From 5a7b0f9636de45f71296165a47cb12931ea02097 Mon Sep 17 00:00:00 2001 From: Corentin THOMASSET Date: Mon, 13 May 2024 10:11:47 +0200 Subject: [PATCH 1/8] chore(issues): removed old issue templates (#1077) --- .github/ISSUE_TEMPLATE/feature-request.yml | 2 +- .github/ISSUE_TEMPLATE/new-tool-request.md | 19 ------------------- .github/ISSUE_TEMPLATE/other-request.md | 13 ------------- .github/ISSUE_TEMPLATE/tool-improvement.md | 13 ------------- 4 files changed, 1 insertion(+), 46 deletions(-) delete mode 100644 .github/ISSUE_TEMPLATE/new-tool-request.md delete mode 100644 .github/ISSUE_TEMPLATE/other-request.md delete mode 100644 .github/ISSUE_TEMPLATE/tool-improvement.md diff --git a/.github/ISSUE_TEMPLATE/feature-request.yml b/.github/ISSUE_TEMPLATE/feature-request.yml index ed666db9..edae822e 100644 --- a/.github/ISSUE_TEMPLATE/feature-request.yml +++ b/.github/ISSUE_TEMPLATE/feature-request.yml @@ -1,5 +1,5 @@ name: 🚀 New feature proposal -description: Propose a new feature to be added to IT-Tools. +description: Propose a new feature/enhancement or tool idea for IT-Tools labels: ['enhancement', 'triage'] body: diff --git a/.github/ISSUE_TEMPLATE/new-tool-request.md b/.github/ISSUE_TEMPLATE/new-tool-request.md deleted file mode 100644 index a67a9cd0..00000000 --- a/.github/ISSUE_TEMPLATE/new-tool-request.md +++ /dev/null @@ -1,19 +0,0 @@ ---- -name: New tool request -about: Suggest a new tool idea -title: '[NEW TOOL]' -labels: new tool -assignees: CorentinTh ---- - -**What tool do you want?** -Example: a token generator - -**Describe the solution you'd like** -A clear and concise description of what you want to happen. - -**Is their example of this tool in the wild?** -Provide link to already existing tool or npm packages if any exists - -**Additional context** -Add any other context about the feature request here. diff --git a/.github/ISSUE_TEMPLATE/other-request.md b/.github/ISSUE_TEMPLATE/other-request.md deleted file mode 100644 index b4901ed4..00000000 --- a/.github/ISSUE_TEMPLATE/other-request.md +++ /dev/null @@ -1,13 +0,0 @@ ---- -name: Other request -about: Any request that does not concern a tool creation, a new feature request on a tool or a bug -title: '[OTHER] ' -labels: -assignees: CorentinTh ---- - -**Describe the solution you'd like** -A clear and concise description of what you want. - -**Additional context** -Add any other context about the feature request here. diff --git a/.github/ISSUE_TEMPLATE/tool-improvement.md b/.github/ISSUE_TEMPLATE/tool-improvement.md deleted file mode 100644 index 8ff8bb6c..00000000 --- a/.github/ISSUE_TEMPLATE/tool-improvement.md +++ /dev/null @@ -1,13 +0,0 @@ ---- -name: Tool improvement -about: Improvement on an existing tool -title: '[TOOL IMPROVEMENT]' -labels: enhancement -assignees: CorentinTh ---- - -**Describe the solution you'd like** -A clear and concise description of what you want to happen. - -**Additional context** -Add any other context about the feature request here. From a0bc3468b256739d83b08ef25fb5709281260f69 Mon Sep 17 00:00:00 2001 From: Corentin THOMASSET Date: Mon, 13 May 2024 10:44:04 +0200 Subject: [PATCH 2/8] chore(issues): prevent empty issues (#1078) --- .github/ISSUE_TEMPLATE/config.yml | 1 + 1 file changed, 1 insertion(+) create mode 100644 .github/ISSUE_TEMPLATE/config.yml diff --git a/.github/ISSUE_TEMPLATE/config.yml b/.github/ISSUE_TEMPLATE/config.yml new file mode 100644 index 00000000..3ba13e0c --- /dev/null +++ b/.github/ISSUE_TEMPLATE/config.yml @@ -0,0 +1 @@ +blank_issues_enabled: false From 81cf6b54835499952ee39c5cb9bb20a196adc625 Mon Sep 17 00:00:00 2001 From: Corentin Thomasset Date: Mon, 13 May 2024 10:54:18 +0200 Subject: [PATCH 3/8] docs(changelog): update changelog for 2024.05.13-a0bc346 --- CHANGELOG.md | 51 ++++++++++++++++++++++++++++++++++++++++++++++++++- package.json | 2 +- 2 files changed, 51 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 7d908d43..984fa58e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,7 +2,7 @@ All notable changes to this project will be documented in this file. See [standard-version](https://github.com/conventional-changelog/standard-version) for commit guidelines. -## Version 2024.05.10-33e5294 +## Version 2024.05.13-a0bc346 ### Features - **i18n**: added German translation (#1038) (2c2fb21) @@ -33,12 +33,20 @@ All notable changes to this project will be documented in this file. See [standa - **i18n**: added locales per tool (#861) (95698cb) ### Chores +- **issues**: prevent empty issues (#1078) (a0bc346) +- **issues**: removed old issue templates (#1077) (5a7b0f9) +- **node**: upgraded node version in CI workflows (b59942a) +- **version**: release 2024.05.10-33e5294 (38d5687) - **issues**: improved issues template (2852c30) - **issues**: improved bug issue template (#1046) (a799234) +### Documentation +- **changelog**: update changelog for 2024.05.10-33e5294 (9dfd347) + ## Version 2023.12.21-5ed3693 ### Features + - **i18n**: improve chinese i18n (#757) (2e56641) - **i18n**: add tooltip and favoriteButton i18n (#756) (a1037cf) - **i18n**: add Chinese translation base (#718) (8f99eb6) @@ -46,6 +54,7 @@ All notable changes to this project will be documented in this file. See [standa - **new tool**: numeronym generator (#729) (e07e2ae) ### Bug fixes + - **jwt-parser**: jwt claim array support (#799) (5ed3693) - **camera-recorder**: stop camera on navigation (#782) (80e46c9) - **doc**: updated create new tool command in readme (#762) (7a70dbb) @@ -54,6 +63,7 @@ All notable changes to this project will be documented in this file. See [standa - **eta**: corrected example (#737) (821cbea) ### Refactoring + - **about, i18n**: improved i18n dx with markdown (#753) (bd3edcb) - **token, i18n**: complete fr translation (#752) (de1ee69) - **uuid generator**: uuid version picker (#751) (38586ca) @@ -63,6 +73,7 @@ All notable changes to this project will be documented in this file. See [standa - **bcrypt**: fix input label align (#721) (093ff31) ### Chores + - **deps**: switched from oui to oui-data for mac address lookup (#693) (0fe9a20) - **deps**: update unocss monorepo to ^0.57.0 (#638) (2e396d8) - **docker**: added armv7 plateform for docker releases (#722) (fe1de8c) @@ -70,19 +81,23 @@ All notable changes to this project will be documented in this file. See [standa ## Version 2023.11.02-7d94e11 ### Features + - **i18n**: language selector (#710) (e86fd96) ### Bug fixes + - **dockerfile**: revert replacement of nginx image with non-privileged one (#716) (7d94e11) - **encryption**: alert on decryption error (#711) (02b0d0d) ### Refactoring + - **math-evaluator**: improved description (e87f4b1) - **math-evaluator**: improved search and UX (#713) (58de897) ## Version 2023.11.01-e164afb ### Features + - **command-palette**: clear prompt on palette close (#708) (d013696) - **command-palette**: added about page in command palette (99b1eb9) - **new tool**: random MAC address generator (#657) (cc3425d) @@ -101,11 +116,13 @@ All notable changes to this project will be documented in this file. See [standa - **new tool**: text diff and comparator (#588) (81bfe57) ### Bug fixes + - **deps**: fix issue on slugify (#593) (#673) (720201a) - **deps**: update dependency monaco-editor to ^0.43.0 (#620) (e371ef7) - **deps**: update dependency sql-formatter to v13 (#606) (c7d4562) ### Refactoring + - **ui**: better ui demo preview menu (#664) (015c673) - **color-converter**: improved color-converter UX (#701) (abb8335) - **docker**: improved docker config (#700) (020e9cb) @@ -122,6 +139,7 @@ All notable changes to this project will be documented in this file. See [standa - **bcrypt**: fix typo (#604) (e18bae1) ### Chores + - **deps**: clean unused dependencies (#709) (e164afb) - **deps**: update docker/setup-qemu-action action to v3 (#627) (4365226) - **deps**: update docker/setup-buildx-action action to v3 (#626) (57ecda1) @@ -136,19 +154,23 @@ All notable changes to this project will be documented in this file. See [standa - **deps**: update dependency typescript to ~5.2.0 (#587) (f3e14fc) ### Doc + - **readme**: added contributors list (#622) (557b304) - **hosting**: added cloudron in the other hosting solutions section (#589) (06c3547) ## Version 2023.08.21-6f93cba ### Features + - **copy**: support legacy copy to clipboard for older browser (#581) (6f93cba) - **new tool**: string obfuscator (#575) (c58d6e3) ### Bug fixes + - **deps**: update dependency sql-formatter to v12 (#520) (2bcb77a) ### Chores + - **deps**: switched to fucking typescript v5 (#501) (76b2761) - **deps**: update dependency @antfu/eslint-config to ^0.40.0 (#552) (6ff9a01) - **deps**: update dependency prettier to v3 (#564) (a2b9b15) @@ -158,6 +180,7 @@ All notable changes to this project will be documented in this file. See [standa ## Version 2023.08.16-9bd4ad4 ### Features + - **Case Converter**: Add lowercase and uppercase (#534) (7b6232a) - **new tool**: emoji picker (#551) (93f7cf0) - **ui**: added c-select in the ui lib (#550) (dfa1ba8) @@ -178,6 +201,7 @@ All notable changes to this project will be documented in this file. See [standa - **base64-string-converter**: switch to encode and decode url safe base64 strings (#392) (0b20f1c) ### Bug fixes + - **deps**: update dependency uuid to v9 (#566) (5e12991) - **deps**: update dependency mathjs to v11 (#519) (7924456) - **deps**: update dependency @vueuse/router to v10 (#516) (ea0f27c) @@ -197,6 +221,7 @@ All notable changes to this project will be documented in this file. See [standa - **ipv4-converter**: removed readonly on input (7aed9c5) ### Refactoring + - **navbar**: consistent spacing in navbar buttons (#507) (30f88fc) - **ui**: remove n-text (#506) (72c98a3) - **ui**: replaced some n-input to c-input (#505) (05ea545) @@ -209,6 +234,7 @@ All notable changes to this project will be documented in this file. See [standa - **ui**: replaced some n-input with c-input-text (f7fc779) ### Chores + - **deps**: update dependency vitest to ^0.34.0 (#562) (9bd4ad4) - **deps**: update dependency node to v18.17.1 (#560) (65a9474) - **deps**: update dependency unocss to ^0.55.0 (#561) (85cc7a8) @@ -249,47 +275,58 @@ All notable changes to this project will be documented in this file. See [standa - **lint**: switched to a better lint config (33c9b66) ### Refacor + - **transformers**: use monospace font for JSON and SQL text areas (#476) (ba4876d) ### Documentation + - **ide**: updated vscode extensions settings (#472) (847323c) ### Chors + - **deps**: updated vueuse dependency version (8515c24) ## Version 2023.05.14-77f2efc ### Features + - **list-converter**: a small converter who deals with column based data and do some stuff with it (#387) (83a7b3b) - **new tool**: phone parser and normalizer (ce3150c) ### Bug fixes + - **phone-parser**: use default country code (a43c546) - **home**: prevent weird blue border on card (3f6c8f0) ### Refactoring + - **ui**: replaced some n-input with c-input-text (77f2efc) ### Chores + - **issues**: updated new tool request issue template (edae4c6) ### Ui-lib + - **new-component**: added text input component in the c-lib (aad8d84) - **button**: size variants (401f13f) ## Version 2023.04.23-92bd835 ### Features + - **ui-lib**: demo pages for c-lib components (92bd835) - **new-tool**: diff of two json objects (362f2fa) - **ipv4-range-expander**: expands a given IPv4 start and end address to a valid IPv4 subnet (#366) (df989e2) - **date converter**: auto focus main input (6d22025) ### Bug fixes + - **ts**: cleaned legacy typechecking warning (e88c1d5) - **mac-address-lookup**: added copy handler on button click (c311e38) ### Refactoring + - **ui-lib**: prevent c-button to shrink (61ece23) - **ui**: replaced naive ui cards with custom ones (f080933) - **clean**: removed unused lodash import (bb32513) @@ -299,48 +336,60 @@ All notable changes to this project will be documented in this file. See [standa ## Version 2023.04.14-dbad773 ### Features + - **new-tool**: http status codes (8355bd2) ### Refactoring + - **uuid-generator**: prevent NaN in quantity (6fb4994) ### Chores + - **release**: create a github release on new version (dbad773) - **version**: reset CHANGELOG content to support new format (85cb0ff) ## Version 2023.04.14-f9b77b7 ### Features + - **new-tool**: http status codes (8355bd2) ### Refactoring + - **uuid-generator**: prevent NaN in quantity (6fb4994) ### Chores + - **release**: create a github release on new version (f9b77b7) - **version**: reset CHANGELOG content to support new format (85cb0ff) ## Version 2023.04.14-2f0d239 ### Features + - **new-tool**: http status codes (8355bd2) ### Refactoring + - **uuid-generator**: prevent NaN in quantity (6fb4994) ### Chores + - **release**: create a github release on new version (2f0d239) - **version**: reset CHANGELOG content to support new format (85cb0ff) ## Version 2023.04.14-474cae4 ### Features + - **new-tool**: http status codes (8355bd2) ### Refactoring + - **uuid-generator**: prevent NaN in quantity (6fb4994) ### Chores + - **release**: create a github release on new version (474cae4) - **version**: reset CHANGELOG content to support new format (85cb0ff) diff --git a/package.json b/package.json index b8b1eeee..801f5c0f 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "it-tools", - "version": "2024.5.10-33e5294", + "version": "2024.5.13-b62e12f", "description": "Collection of handy online tools for developers, with great UX. ", "keywords": [ "productivity", From e876d0360812eab1255e414102a44d65f7c1bfaf Mon Sep 17 00:00:00 2001 From: Corentin Thomasset Date: Mon, 13 May 2024 10:54:18 +0200 Subject: [PATCH 4/8] chore(version): release 2024.05.13-a0bc346 --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 801f5c0f..9f39ff1d 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "it-tools", - "version": "2024.5.13-b62e12f", + "version": "2024.5.13-a0bc346", "description": "Collection of handy online tools for developers, with great UX. ", "keywords": [ "productivity", From 30144aa3f51f5d0dc90f64cf888bc6f83de11b10 Mon Sep 17 00:00:00 2001 From: sharevb Date: Mon, 20 May 2024 22:13:55 +0200 Subject: [PATCH 5/8] feat(base64): Base64 enhancements (#905) * fix(base64): use js-base64 to handle non ascii text Use js-base64 to handle non ascii text and ignore whitespaces Fix #879 and #409 * fix(base64): use js-base64 to handle non ascii text Use js-base64 to handle non ascii text and ignore whitespaces Fix #879 and #409 * feat(base64 file converter): add a filename and extension fields Add filename and extension (auto filled if data url) to allow downloading with right extension and filename Fix #788 * feat(base64 file converter): add a preview image Fix #594. Taken from #595 (thanks @SAF2k) --- package.json | 1 + pnpm-lock.yaml | 19 ++-- src/composable/downloadBase64.ts | 91 +++++++++++++++---- .../base64-file-converter.vue | 67 +++++++++++++- src/utils/base64.test.ts | 13 +-- src/utils/base64.ts | 11 ++- 6 files changed, 164 insertions(+), 38 deletions(-) diff --git a/package.json b/package.json index 9f39ff1d..c6cb7757 100644 --- a/package.json +++ b/package.json @@ -64,6 +64,7 @@ "highlight.js": "^11.7.0", "iarna-toml-esm": "^3.0.5", "ibantools": "^4.3.3", + "js-base64": "^3.7.6", "json5": "^2.2.3", "jwt-decode": "^3.1.2", "libphonenumber-js": "^1.10.28", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index bd6c38c9..8619d8c0 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -92,6 +92,9 @@ dependencies: ibantools: specifier: ^4.3.3 version: 4.3.3 + js-base64: + specifier: ^3.7.6 + version: 3.7.7 json5: specifier: ^2.2.3 version: 2.2.3 @@ -3351,7 +3354,7 @@ packages: dependencies: '@unhead/dom': 0.5.1 '@unhead/schema': 0.5.1 - '@vueuse/shared': 10.7.2(vue@3.3.4) + '@vueuse/shared': 10.8.0(vue@3.3.4) unhead: 0.5.1 vue: 3.3.4 transitivePeerDependencies: @@ -3993,10 +3996,10 @@ packages: - vue dev: false - /@vueuse/shared@10.7.2(vue@3.3.4): - resolution: {integrity: sha512-qFbXoxS44pi2FkgFjPvF4h7c9oMDutpyBdcJdMYIMg9XyXli2meFMuaKn+UMgsClo//Th6+beeCgqweT/79BVA==} + /@vueuse/shared@10.8.0(vue@3.3.4): + resolution: {integrity: sha512-dUdy6zwHhULGxmr9YUg8e+EnB39gcM4Fe2oKBSrh3cOsV30JcMPtsyuspgFCUo5xxFNaeMf/W2yyKfST7Bg8oQ==} dependencies: - vue-demi: 0.14.6(vue@3.3.4) + vue-demi: 0.14.7(vue@3.3.4) transitivePeerDependencies: - '@vue/composition-api' - vue @@ -6472,6 +6475,10 @@ packages: hasBin: true dev: true + /js-base64@3.7.7: + resolution: {integrity: sha512-7rCnleh0z2CkXhH67J8K1Ytz0b2Y+yxTPL+/KOJoa20hfnVQ/3/T6W/KflYI4bRHRagNeXeU2bkNGI3v1oS/lw==} + dev: false + /js-beautify@1.14.6: resolution: {integrity: sha512-GfofQY5zDp+cuHc+gsEXKPpNw2KbPddreEo35O6jT6i0RVK6LhsoYBhq5TvK4/n74wnA0QbK8gGd+jUZwTMKJw==} engines: {node: '>=10'} @@ -9151,8 +9158,8 @@ packages: vue: 3.3.4 dev: false - /vue-demi@0.14.6(vue@3.3.4): - resolution: {integrity: sha512-8QA7wrYSHKaYgUxDA5ZC24w+eHm3sYCbp0EzcDwKqN3p6HqtTCGR/GVsPyZW92unff4UlcSh++lmqDWN3ZIq4w==} + /vue-demi@0.14.7(vue@3.3.4): + resolution: {integrity: sha512-EOG8KXDQNwkJILkx/gPcoL/7vH+hORoBaKgGe+6W7VFMvCYJfmF2dGbvgDroVnI8LU7/kTu8mbjRZGBU1z9NTA==} engines: {node: '>=12'} hasBin: true requiresBuild: true diff --git a/src/composable/downloadBase64.ts b/src/composable/downloadBase64.ts index 37b0428d..3bc20226 100644 --- a/src/composable/downloadBase64.ts +++ b/src/composable/downloadBase64.ts @@ -1,8 +1,13 @@ -import { extension as getExtensionFromMime } from 'mime-types'; +import { extension as getExtensionFromMimeType, extension as getMimeTypeFromExtension } from 'mime-types'; import type { Ref } from 'vue'; import _ from 'lodash'; -export { getMimeTypeFromBase64, useDownloadFileFromBase64 }; +export { + getMimeTypeFromBase64, + getMimeTypeFromExtension, getExtensionFromMimeType, + useDownloadFileFromBase64, useDownloadFileFromBase64Refs, + previewImageFromBase64, +}; const commonMimeTypesSignatures = { 'JVBERi0': 'application/pdf', @@ -36,30 +41,78 @@ function getFileExtensionFromMimeType({ defaultExtension?: string }) { if (mimeType) { - return getExtensionFromMime(mimeType) ?? defaultExtension; + return getExtensionFromMimeType(mimeType) ?? defaultExtension; } return defaultExtension; } -function useDownloadFileFromBase64({ source, filename }: { source: Ref; filename?: string }) { +function downloadFromBase64({ sourceValue, filename, extension, fileMimeType }: +{ sourceValue: string; filename?: string; extension?: string; fileMimeType?: string }) { + if (sourceValue === '') { + throw new Error('Base64 string is empty'); + } + + const defaultExtension = extension ?? 'txt'; + const { mimeType } = getMimeTypeFromBase64({ base64String: sourceValue }); + let base64String = sourceValue; + if (!mimeType) { + const targetMimeType = fileMimeType ?? getMimeTypeFromExtension(defaultExtension); + base64String = `data:${targetMimeType};base64,${sourceValue}`; + } + + const cleanExtension = extension ?? getFileExtensionFromMimeType( + { mimeType, defaultExtension }); + let cleanFileName = filename ?? `file.${cleanExtension}`; + if (extension && !cleanFileName.endsWith(`.${extension}`)) { + cleanFileName = `${cleanFileName}.${cleanExtension}`; + } + + const a = document.createElement('a'); + a.href = base64String; + a.download = cleanFileName; + a.click(); +} + +function useDownloadFileFromBase64( + { source, filename, extension, fileMimeType }: + { source: Ref; filename?: string; extension?: string; fileMimeType?: string }) { return { download() { - if (source.value === '') { - throw new Error('Base64 string is empty'); - } - - const { mimeType } = getMimeTypeFromBase64({ base64String: source.value }); - const base64String = mimeType - ? source.value - : `data:text/plain;base64,${source.value}`; - - const cleanFileName = filename ?? `file.${getFileExtensionFromMimeType({ mimeType })}`; - - const a = document.createElement('a'); - a.href = base64String; - a.download = cleanFileName; - a.click(); + downloadFromBase64({ sourceValue: source.value, filename, extension, fileMimeType }); }, }; } + +function useDownloadFileFromBase64Refs( + { source, filename, extension }: + { source: Ref; filename?: Ref; extension?: Ref }) { + return { + download() { + downloadFromBase64({ sourceValue: source.value, filename: filename?.value, extension: extension?.value }); + }, + }; +} + +function previewImageFromBase64(base64String: string): HTMLImageElement { + if (base64String === '') { + throw new Error('Base64 string is empty'); + } + + const img = document.createElement('img'); + img.src = base64String; + + const container = document.createElement('div'); + container.appendChild(img); + + const previewContainer = document.getElementById('previewContainer'); + if (previewContainer) { + previewContainer.innerHTML = ''; + previewContainer.appendChild(container); + } + else { + throw new Error('Preview container element not found'); + } + + return img; +} diff --git a/src/tools/base64-file-converter/base64-file-converter.vue b/src/tools/base64-file-converter/base64-file-converter.vue index 377625bd..a489f9a1 100644 --- a/src/tools/base64-file-converter/base64-file-converter.vue +++ b/src/tools/base64-file-converter/base64-file-converter.vue @@ -2,12 +2,19 @@ import { useBase64 } from '@vueuse/core'; import type { Ref } from 'vue'; import { useCopy } from '@/composable/copy'; -import { useDownloadFileFromBase64 } from '@/composable/downloadBase64'; +import { getExtensionFromMimeType, getMimeTypeFromBase64, previewImageFromBase64, useDownloadFileFromBase64Refs } from '@/composable/downloadBase64'; import { useValidation } from '@/composable/validation'; import { isValidBase64 } from '@/utils/base64'; +const fileName = ref('file'); +const fileExtension = ref(''); const base64Input = ref(''); -const { download } = useDownloadFileFromBase64({ source: base64Input }); +const { download } = useDownloadFileFromBase64Refs( + { + source: base64Input, + filename: fileName, + extension: fileExtension, + }); const base64InputValidation = useValidation({ source: base64Input, rules: [ @@ -18,6 +25,35 @@ const base64InputValidation = useValidation({ ], }); +watch( + base64Input, + (newValue, _) => { + const { mimeType } = getMimeTypeFromBase64({ base64String: newValue }); + if (mimeType) { + fileExtension.value = getExtensionFromMimeType(mimeType) || fileExtension.value; + } + }, +); + +function previewImage() { + if (!base64InputValidation.isValid) { + return; + } + try { + const image = previewImageFromBase64(base64Input.value); + image.style.maxWidth = '100%'; + image.style.maxHeight = '400px'; + const previewContainer = document.getElementById('previewContainer'); + if (previewContainer) { + previewContainer.innerHTML = ''; + previewContainer.appendChild(image); + } + } + catch (_) { + // + } +} + function downloadFile() { if (!base64InputValidation.isValid) { return; @@ -44,6 +80,24 @@ async function onUpload(file: File) {