{"id":16831163,"url":"https://github.com/chearon/fontconfigjs","last_synced_at":"2025-09-11T16:19:10.204Z","repository":{"id":44308102,"uuid":"247572138","full_name":"chearon/fontconfigjs","owner":"chearon","description":"In-memory version of FontConfig in JS/WASM (no native dependencies)","archived":false,"fork":false,"pushed_at":"2023-02-04T04:04:39.000Z","size":26146,"stargazers_count":11,"open_issues_count":9,"forks_count":1,"subscribers_count":3,"default_branch":"master","last_synced_at":"2025-09-11T08:46:02.656Z","etag":null,"topics":["fontconfig","nodejs","webassembly"],"latest_commit_sha":null,"homepage":"https://chearon.github.io/fontconfigjs/","language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/chearon.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2020-03-15T23:51:41.000Z","updated_at":"2025-08-11T18:13:41.000Z","dependencies_parsed_at":"2023-02-18T13:45:35.812Z","dependency_job_id":null,"html_url":"https://github.com/chearon/fontconfigjs","commit_stats":null,"previous_names":[],"tags_count":8,"template":false,"template_full_name":null,"purl":"pkg:github/chearon/fontconfigjs","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chearon%2Ffontconfigjs","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chearon%2Ffontconfigjs/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chearon%2Ffontconfigjs/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chearon%2Ffontconfigjs/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/chearon","download_url":"https://codeload.github.com/chearon/fontconfigjs/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/chearon%2Ffontconfigjs/sbom","scorecard":{"id":275296,"data":{"date":"2025-08-11","repo":{"name":"github.com/chearon/fontconfigjs","commit":"0ab1d62b278faa19dfc33c914b5ebfb803279ddd"},"scorecard":{"version":"v5.2.1-40-gf6ed084d","commit":"f6ed084d17c9236477efd66e5b258b9d4cc7b389"},"score":1,"checks":[{"name":"Code-Review","score":0,"reason":"Found 0/26 approved changesets -- score normalized to 0","details":null,"documentation":{"short":"Determines if the project requires human code review before pull requests (aka merge requests) are merged.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#code-review"}},{"name":"Packaging","score":-1,"reason":"packaging workflow not detected","details":["Warn: no GitHub/GitLab publishing workflow detected."],"documentation":{"short":"Determines if the project is published as a package that others can easily download, install, easily update, and uninstall.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#packaging"}},{"name":"Token-Permissions","score":-1,"reason":"No tokens found","details":null,"documentation":{"short":"Determines if the project's workflows follow the principle of least privilege.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#token-permissions"}},{"name":"Maintained","score":0,"reason":"0 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 0","details":null,"documentation":{"short":"Determines if the project is \"actively maintained\".","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#maintained"}},{"name":"Dangerous-Workflow","score":-1,"reason":"no workflows found","details":null,"documentation":{"short":"Determines if the project's GitHub Action workflows avoid dangerous patterns.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#dangerous-workflow"}},{"name":"Binary-Artifacts","score":8,"reason":"binaries present in source code","details":["Warn: binary detected: docs/lib.wasm:1","Warn: binary detected: packages/core/lib.wasm:1"],"documentation":{"short":"Determines if the project has generated executable (binary) artifacts in the source repository.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#binary-artifacts"}},{"name":"CII-Best-Practices","score":0,"reason":"no effort to earn an OpenSSF best practices badge detected","details":null,"documentation":{"short":"Determines if the project has an OpenSSF (formerly CII) Best Practices Badge.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#cii-best-practices"}},{"name":"Security-Policy","score":0,"reason":"security policy file not detected","details":["Warn: no security policy file detected","Warn: no security file to analyze","Warn: no security file to analyze","Warn: no security file to analyze"],"documentation":{"short":"Determines if the project has published a security policy.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#security-policy"}},{"name":"License","score":0,"reason":"license file not detected","details":["Warn: project does not have a license file"],"documentation":{"short":"Determines if the project has defined a license.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#license"}},{"name":"Signed-Releases","score":-1,"reason":"no releases found","details":null,"documentation":{"short":"Determines if the project cryptographically signs release artifacts.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#signed-releases"}},{"name":"Branch-Protection","score":0,"reason":"branch protection not enabled on development/release branches","details":["Warn: branch protection not enabled for branch 'master'"],"documentation":{"short":"Determines if the default and release branches are protected with GitHub's branch protection settings.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#branch-protection"}},{"name":"Fuzzing","score":0,"reason":"project is not fuzzed","details":["Warn: no fuzzer integrations found"],"documentation":{"short":"Determines if the project uses fuzzing.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#fuzzing"}},{"name":"Pinned-Dependencies","score":-1,"reason":"no dependencies found","details":null,"documentation":{"short":"Determines if the project has declared and pinned the dependencies of its build process.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#pinned-dependencies"}},{"name":"SAST","score":0,"reason":"SAST tool is not run on all commits -- score normalized to 0","details":["Warn: 0 commits out of 4 are checked with a SAST tool"],"documentation":{"short":"Determines if the project uses static code analysis.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#sast"}},{"name":"Vulnerabilities","score":0,"reason":"68 existing vulnerabilities detected","details":["Warn: Project is vulnerable to: GHSA-968p-4wvh-cqc8","Warn: Project is vulnerable to: GHSA-67hx-6x53-jw92","Warn: Project is vulnerable to: GHSA-v88g-cgmw-v5xw","Warn: Project is vulnerable to: GHSA-whgm-jr23-g3j9","Warn: Project is vulnerable to: GHSA-93q8-gq69-wqmw","Warn: Project is vulnerable to: GHSA-v6h2-p8h4-qcjw","Warn: Project is vulnerable to: GHSA-grv7-fg5c-xmjg","Warn: Project is vulnerable to: GHSA-x9w5-v3q2-3rhw","Warn: Project is vulnerable to: GHSA-w8qv-6jwh-64r5","Warn: Project is vulnerable to: GHSA-257v-vj4p-3w2h","Warn: Project is vulnerable to: GHSA-3xgq-45jj-v275","Warn: Project is vulnerable to: GHSA-gxpj-cx7g-858c","Warn: Project is vulnerable to: GHSA-w573-4hg7-7wgq","Warn: Project is vulnerable to: GHSA-phwq-j96m-2c2q","Warn: Project is vulnerable to: GHSA-ghr5-ch3p-vcr6","Warn: Project is vulnerable to: GHSA-r9p9-mrjm-926w","Warn: Project is vulnerable to: GHSA-434g-2637-qmqr","Warn: Project is vulnerable to: GHSA-49q7-c7j4-3p7m","Warn: Project is vulnerable to: GHSA-977x-g7h5-7qgw","Warn: Project is vulnerable to: GHSA-f7q4-pwc6-w24p","Warn: Project is vulnerable to: GHSA-fc9h-whq2-v747","Warn: Project is vulnerable to: GHSA-vjh7-7g9h-fjfh","Warn: Project is vulnerable to: GHSA-74fj-2j2h-c42q","Warn: Project is vulnerable to: GHSA-pw2r-vq6v-hr8c","Warn: Project is vulnerable to: GHSA-jchw-25xp-jwwc","Warn: Project is vulnerable to: GHSA-cxjh-pqwp-8mfp","Warn: Project is vulnerable to: GHSA-fjxv-7rqg-78g4","Warn: Project is vulnerable to: GHSA-ww39-953v-wcq6","Warn: Project is vulnerable to: GHSA-vfrc-7r7c-w9mx","Warn: Project is vulnerable to: GHSA-7wwv-vh3v-89cq","Warn: Project is vulnerable to: GHSA-c7qv-q95q-8v27","Warn: Project is vulnerable to: GHSA-7r28-3m3f-r2pr","Warn: Project is vulnerable to: GHSA-r8j5-h5cx-65gg","Warn: Project is vulnerable to: GHSA-896r-f27r-55mw","Warn: Project is vulnerable to: GHSA-9c47-m6qq-7p4h","Warn: Project is vulnerable to: GHSA-29mw-wpgm-hmr9","Warn: Project is vulnerable to: GHSA-35jh-r3h4-6jhm","Warn: Project is vulnerable to: GHSA-952p-6rrq-rcjv","Warn: Project is vulnerable to: GHSA-f8q6-p94x-37v3","Warn: Project is vulnerable to: GHSA-xvch-5gv4-984h","Warn: Project is vulnerable to: GHSA-92xj-mqp7-vmcj","Warn: Project is vulnerable to: GHSA-wxgw-qj99-44c2","Warn: Project is vulnerable to: GHSA-5rrq-pxf6-6jx5","Warn: Project is vulnerable to: GHSA-8fr3-hfg3-gpgp","Warn: Project is vulnerable to: GHSA-gf8q-jrpm-jvxq","Warn: Project is vulnerable to: GHSA-2r2c-g63r-vccr","Warn: Project is vulnerable to: GHSA-cfm4-qjh2-4765","Warn: Project is vulnerable to: GHSA-x4jg-mjrx-434g","Warn: Project is vulnerable to: GHSA-rp65-9cf3-cjxr","Warn: Project is vulnerable to: GHSA-hj48-42vr-x3v9","Warn: Project is vulnerable to: GHSA-h7cp-r72f-jxh6","Warn: Project is vulnerable to: GHSA-v62p-rq8g-8h59","Warn: Project is vulnerable to: GHSA-566m-qj78-rww5","Warn: Project is vulnerable to: GHSA-7fh5-64p2-3v2j","Warn: Project is vulnerable to: GHSA-hwj9-h5mp-3pm3","Warn: Project is vulnerable to: GHSA-hrpp-h998-j3pp","Warn: Project is vulnerable to: GHSA-p8p7-x288-28g6","Warn: Project is vulnerable to: GHSA-c2qf-rxjj-qqgw","Warn: Project is vulnerable to: GHSA-wpg7-2c88-r8xv","Warn: Project is vulnerable to: GHSA-pq67-2wwv-3xjx","Warn: Project is vulnerable to: GHSA-8cj5-5rvv-wf4v","Warn: Project is vulnerable to: GHSA-4wf5-vphf-c2xc","Warn: Project is vulnerable to: GHSA-72xf-g2v4-qvf3","Warn: Project is vulnerable to: GHSA-5j4c-8p2g-v4jx","Warn: Project is vulnerable to: GHSA-j8xg-fqg3-53r7","Warn: Project is vulnerable to: GHSA-6fc8-4gx4-v693","Warn: Project is vulnerable to: GHSA-3h5v-q93c-6h6q","Warn: Project is vulnerable to: GHSA-c4w7-xm78-47vh"],"documentation":{"short":"Determines if the project has open, known unfixed vulnerabilities.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#vulnerabilities"}}]},"last_synced_at":"2025-08-17T14:15:01.150Z","repository_id":44308102,"created_at":"2025-08-17T14:15:01.150Z","updated_at":"2025-08-17T14:15:01.150Z"},"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":274666779,"owners_count":25327511,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-09-11T02:00:13.660Z","response_time":74,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["fontconfig","nodejs","webassembly"],"created_at":"2024-10-13T11:42:31.689Z","updated_at":"2025-09-11T16:19:10.134Z","avatar_url":"https://github.com/chearon.png","language":"JavaScript","readme":"# fontconfigjs\n\nThis is essentially a stripped-down version of FontConfig compiled to WebAssembly with a Javascript API that works in nodejs and the browser.\n\n## How?\n\n```javascript\nimport FontConfigInit from 'fontconfig';\nimport fs from 'fs';\n\nconst FontConfig = await FontConfigInit(/* wasm URL if you're in the browser */);\nconst cfg = new FontConfig();\n\nconst fonts = [\n  '/Library/Fonts/Comic Sans MS.ttf',\n  '/Library/Fonts/Futura.ttc',\n  '/Library/Fonts/GillSans.ttc'\n];\n\nfor (const filename of fonts) {\n  cfg.addFont(new Uint8Array(fs.readFileSync(filename)), filename);\n}\n\ncfg.sort({\n  family: 'Gill Sans',\n  weight: FontConfig.FC_WEIGHT_LIGHT\n});\n\n// returns this:\n[\n  { file: '/Library/Fonts/GillSans.ttc', index: 7 },\n  { file: '/Library/Fonts/GillSans.ttc', index: 6 },\n  { file: '/Library/Fonts/Comic Sans MS.ttf', index: 0 },\n  { file: '/Library/Fonts/Futura.ttc', index: 2 }\n]\n```\n\nUnlike the full FontConfig library, it does not read configuration files for font lookup rules or font search directories. The part of FontConfig for adding and querying fonts (the matching module) is exposed instead, which the Javascript wrapper makes calls to. At some point support for FontConfig [rules and aliases](https://www.freedesktop.org/software/fontconfig/fontconfig-user.html) (the configuration module) could be added. I don't expect it to be very useful since consumers of this library are typically adding and selecting fonts on their own, rather than users doing it.\n\nInstead of using [FreeType](http://freetype.org) to read fonts, [fontkit](https://github.com/foliojs/fontkit) is used.\n\n## API\n\n### `FontConfig.sort(pattern)`\n\nReturns the best possible cascade list of fonts based on a description (with later fonts suited to use when previous fonts don't have proper coverage).\n\nThe pattern object passed to `FontConfig.prototype.sort` looks like:\n\n- `family` (string|string[]) (required)\n- `weight` (number|string) (a CSS2 weight like `'200'` or `FontConfig.FC_WEIGHT_EXTRALIGHT`)\n- `width` (number|string) (a CSS3 width like `'condensed'` or `FontConfig.FC_WIDTH_CONDENSED`)\n- `slant` (number|string) (a CSS2 slant like `'oblique'` or `FontConfig.FC_SLANT_OBLIQUE`)\n- `lang`  (string|string[])\n- `coverage` (number[])\n\nWhen the `family` is an array of more than one family, it is a prioritized list. If the first family isn't found, FontConfig tries the second family. If more than one is found, they will all appear in the results in prioritized order.\n\nFor more details on other properties' individual values, continue below.\n\n#### Weights\n\n_Note you can also use CSS2 `font-weight` values as a string like `'300'`_\n\n- `FontConfig.FC_WEIGHT_THIN`\n- `FontConfig.FC_WEIGHT_EXTRALIGHT`\n- `FontConfig.FC_WEIGHT_ULTRALIGHT`\n- `FontConfig.FC_WEIGHT_LIGHT`\n- `FontConfig.FC_WEIGHT_DEMILIGHT`\n- `FontConfig.FC_WEIGHT_SEMILIGHT`\n- `FontConfig.FC_WEIGHT_BOOK`\n- `FontConfig.FC_WEIGHT_REGULAR`\n- `FontConfig.FC_WEIGHT_NORMAL`\n- `FontConfig.FC_WEIGHT_MEDIUM`\n- `FontConfig.FC_WEIGHT_DEMIBOLD`\n- `FontConfig.FC_WEIGHT_SEMIBOLD`\n- `FontConfig.FC_WEIGHT_BOLD`\n- `FontConfig.FC_WEIGHT_EXTRABOLD`\n- `FontConfig.FC_WEIGHT_ULTRABOLD`\n- `FontConfig.FC_WEIGHT_BLACK`\n- `FontConfig.FC_WEIGHT_HEAVY`\n- `FontConfig.FC_WEIGHT_EXTRABLACK`\n- `FontConfig.FC_WEIGHT_ULTRABLACK`\n\n#### Widths\n\n_Note you can also use CSS3 `font-stretch` values as a string like `'condensed'`_\n\n- `FontConfig.FC_WIDTH_ULTRACONDENSED`\n- `FontConfig.FC_WIDTH_EXTRACONDENSED`\n- `FontConfig.FC_WIDTH_CONDENSED`\n- `FontConfig.FC_WIDTH_SEMICONDENSED`\n- `FontConfig.FC_WIDTH_NORMAL`\n- `FontConfig.FC_WIDTH_SEMIEXPANDED`\n- `FontConfig.FC_WIDTH_EXPANDED`\n- `FontConfig.FC_WIDTH_EXTRAEXPANDED`\n- `FontConfig.FC_WIDTH_ULTRAEXPANDED`\n\n#### Slants\n\n_Note you can also use CSS2 `font-style` values as a string like `'italic'`_\n\n- `FontConfig.FC_SLANT_ROMAN`\n- `FontConfig.FC_SLANT_ITALIC`\n- `FontConfig.FC_SLANT_OBLIQUE`\n\n#### Languages\n\nAn [RFC3366](https://tools.ietf.org/html/rfc3066) language tag such as `\"en\"` or `\"zh-tw\"`\n\n#### Unicode Coverage\n\nThe `coverage` option is an array of unicode codepoints. For example, if you pass `{coverage: [0x1780]}`, a Khmer font will be at the top of the list.\n\n## Enabling debugging\n\nThanks to [WASI](https://wasi.dev), you can set the environment variable [`FC_DEBUG`](https://www.freedesktop.org/software/fontconfig/fontconfig-user.html)\u003csup\u003e1\u003c/sup\u003e just like regular font config. This will print information to stdout, but only if\n\n1. You built with `-DWASI_RUNTIME` (see below)\n2. You're using nodejs 13.3.0 or newer\n3. You run nodejs with `--experimental-wasi-unstable-preview1 --experimental-wasm-bigint`\n\nThe WASM distributed in NPM is not built with debugging calls, though there are probably WASI runtimes available for web browsers.\n\n\u003csup\u003e1\u003c/sup\u003eAs of node 13.10 this doesn't seem to be implemented yet, so you have to manually edit `src/fcdbg.c` until it's fixed.\n\n## Building the C parts\n\nMake sure you clone with `--recurse-submodules`\n\nThese instructions are for macOS, but they should be similar for Linux. The steps are familiar to anyone who has done cross-compilation before, but the first few are WebAssembly-specific.\n\n1. `cd fontconfig; patch -p1 \u003c ../pure-wasm-compat-fontconfig.patch; cd..`\n2. `LLVM_PATH=/usr/local/Cellar/llvm/9.0.0/bin`. or somewhere else appropriate. You do need a recent version of LLVM that supports WebAssembly.\n3. `git clone git@github.com:chearon/wasi-libc.git`. The upstream version builds with symbols that introduce runtime dependencies.\n4. `cd wasi-libc`\n5. `make WASM_CC=$LLVM_PATH/clang WASM_AR=$LLVM_PATH/llvm-ar WASM_NM=$LLVM_PATH/llvm-nm`\n6. `WASI_SYSROOT=$(pwd)/sysroot`\n7. Download [`wasi-sdk` builtins](https://github.com/WebAssembly/wasi-sdk/releases/download/wasi-sdk-8/libclang_rt.builtins-wasm32-wasi-8.0.tar.gz) and copy `libclang_rt.builtins-wasm32.a` to `/usr/local/Cellar/llvm/9.0.0/lib/clang/9.0.0/lib/wasi/` (or wherever you installed your compiler in step 1).\n8. `export LIBTOOLIZE=glibtoolize` (these next 3 steps might be macOS-specific)\n9. `export GETTEXTIZE=/usr/local/opt/gettext/bin/gettextize`\n10. `export AUTOPOINT=/usr/local/opt/gettext/bin/autopoint`\n11. `export CC=$LLVM_PATH/clang`\n12. `export CFLAGS=-target wasm32-wasi --sysroot=$WASI_SYSROOT` (for debugging, you can also add `-DWASI_RUNTIME` to see FontConfig logging)\n13. `export AR=$LLVM_PATH/llvm-ar`\n14. `export RANLIB=$LLVM_PATH/llvm-ranlib`\n15. Patch config.sub: `grep -q -F -- '-wasi' config.sub || sed -i -e 's/-nacl\\*)/-nacl*|-wasi)/' config.sub` (thank you so much, [Frank Denis](https://00f.net/2019/04/07/compiling-to-webassembly-with-llvm-and-clang/))\n16. `./autogen.sh --host=wasm32-wasi`\n17. `make`\n18. `$LLVM_PATH/wasm-ld  -L$WASI_SYSROOT/lib/wasm32-wasi --no-entry --export-all -lc --whole-archive src/.libs/libfontconfig.a -o ../packages/core/lib.wasm`\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fchearon%2Ffontconfigjs","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fchearon%2Ffontconfigjs","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fchearon%2Ffontconfigjs/lists"}