{"id":19554133,"url":"https://github.com/revdotcom/fstalign","last_synced_at":"2026-01-08T00:03:19.131Z","repository":{"id":37569858,"uuid":"351148123","full_name":"revdotcom/fstalign","owner":"revdotcom","description":"An efficient OpenFST-based tool for calculating WER and aligning two transcript sequences.","archived":false,"fork":false,"pushed_at":"2025-01-27T19:37:30.000Z","size":347,"stargazers_count":166,"open_issues_count":2,"forks_count":9,"subscribers_count":35,"default_branch":"develop","last_synced_at":"2025-03-28T14:09:19.289Z","etag":null,"topics":["alignment","asr-benchmark","fst","speech-recognition","word-error-rate"],"latest_commit_sha":null,"homepage":"","language":"C++","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/revdotcom.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2021-03-24T16:23:11.000Z","updated_at":"2025-03-20T14:03:35.000Z","dependencies_parsed_at":"2024-11-11T04:28:13.115Z","dependency_job_id":"80c1519d-97aa-4471-af6b-7800f49835eb","html_url":"https://github.com/revdotcom/fstalign","commit_stats":null,"previous_names":[],"tags_count":27,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/revdotcom%2Ffstalign","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/revdotcom%2Ffstalign/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/revdotcom%2Ffstalign/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/revdotcom%2Ffstalign/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/revdotcom","download_url":"https://codeload.github.com/revdotcom/fstalign/tar.gz/refs/heads/develop","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247198460,"owners_count":20900080,"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","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":["alignment","asr-benchmark","fst","speech-recognition","word-error-rate"],"created_at":"2024-11-11T04:26:01.091Z","updated_at":"2026-01-08T00:03:19.122Z","avatar_url":"https://github.com/revdotcom.png","language":"C++","readme":"![CI](https://github.com/revdotcom/fstalign/workflows/CI/badge.svg)\n[![License](https://img.shields.io/badge/License-Apache%202.0-blue.svg)](https://opensource.org/licenses/Apache-2.0)\n\n# fstalign\n- [Overview](#Overview)\n- [What's new in 2.0](#What's-new-in-2.0)\n- [Installation](#Installation)\n  * [Dependencies](#Dependencies)\n  * [Build](#Build)\n  * [Docker](#Docker)\n- [Documentation](#Documentation)\n\n## Overview\n`fstalign` is a tool for creating alignment between two sequences of tokens (here out referred to as “reference” and “hypothesis”). It has two key functions: computing word error rate (WER) and aligning [NLP-formatted](https://github.com/revdotcom/fstalign/blob/develop/docs/NLP-Format.md) references with CTM hypotheses.\n\nDue to its use of OpenFST and lazy algorithms for text-based alignment, `fstalign` is efficient for calculating WER while also providing significant flexibility for different measurement features and error analysis.\n\n## What's new in 2.0\n\nVersion 2.0 introduces two major changes: \n1. A new method to traverse the composition graph, which dramatically improves the overall speed, especially when the sequences are long contain many errors.\nWe have files that took 25 minutes to align before that can now take about 7 seconds. This is especially noticeable with the adapted composition (the default).\n1. Some smarts were introduced when --use-case and --use-punctuation are enabled.\nNow, by default, punctuation symbols can only be substituted by other punctuation symbols (or deleted/inserted).\nAlso, words that differ only by the first letter case will be preffered for substitution.\n\n\nHere's an example of the 1.x behavior and the 2.0 version\n```\n==\u003e v1.x sbs.txt \u003c==\n           ref_token\thyp_token           \tIsErr\tClass\tWer_Tag_Entities\n             Welcome\tWelcome             \t\t\t###322_###|\n                back\tback                \t\t\t\n                  to\tto                  \t\t\t\n             another\tanother             \t\t\t\n             episode\tepisode             \t\t\t###323_###|\n                  of\tof                  \t\t\t\n            Podcasts\tPodcast             \tERR\t\t###324_###|\n                  in\tand                 \tERR\t\t\n               Color\tColor               \t\t\t###167_###|###325_###|\n                   :\tof                  \tERR\t\t\n                 The\tthe                 \tERR\t\t\n             Podcast\tPodcast             \t\t\t###168_###|###326_###|\n                   .\t.                   \t\t\t\n                   I\tI                   \t\t\t\n\n==\u003e v2.0 sbs.txt \u003c==\n           ref_token\thyp_token           \tIsErr\tClass\tWer_Tag_Entities\n             Welcome\tWelcome             \t\t\t###322_###|\n                back\tback                \t\t\t\n                  to\tto                  \t\t\t\n             another\tanother             \t\t\t\n             episode\tepisode             \t\t\t###323_###|\n                  of\tof                  \t\t\t\n            Podcasts\tPodcast             \tERR\t\t###324_###|\n                  in\tand                 \tERR\t\t\n               Color\tColor               \t\t\t###167_###|###325_###|\n               \u003cins\u003e\tof                  \tERR\t\t\n                   :\t\u003cdel\u003e               \tERR\t\t\n                 The\tthe                 \tERR\t\t\n             Podcast\tPodcast             \t\t\t###168_###|###326_###|\n```\nThe confusion between `:` and `of` is not longer allowed.\n\nAlso, here's how favoring or not the substitution based on case-insensitive comparison, while still counting it as an error, looks like:\n```\n==\u003e v1.x sbs.txt \u003c==\n           ref_token\thyp_token           \tIsErr\tClass\tWer_Tag_Entities\n             shorten    shorten                         ###801_###|\n                It's    it's                    ERR     \n               Berry    Barry                   ERR     ###785_###|###788_###|###802_###|\n                   .    .        \n                Just    Just   \n                Yeah    like                    ERR     ###805_###|                                                                                                             \n                   .    \u003cdel\u003e                   ERR\n                Like    \u003cdel\u003e                   ERR     \n                   ,    \u003cdel\u003e                   ERR     \n                   I    I                               ###809_###|\n                have    have   \n                   a    a         \n            nickname    nickname \n\n==\u003e v2.0 sbs.txt \u003c==\n           ref_token\thyp_token           \tIsErr\tClass\tWer_Tag_Entities\n                It's    it's                    ERR     \n               Berry    Barry                   ERR     ###785_###|###788_###|###802_###|\n                   .    .     \n                Just    Just     \n                Yeah    \u003cdel\u003e                   ERR     ###805_###|\n                   .    \u003cdel\u003e                   ERR     \n                Like    like                    ERR     \n                   ,    \u003cdel\u003e                   ERR     \n                   I    I                               ###809_###|\n                have    have     \n                   a    a        \n            nickname    nickname  \n```\nHere, `Like \u003c-\u003e like` substitution is favored.  While this generally won't change the WER value itself (although it can), it will improve the timing alignments.  \n\n\nThese behavior, as well as the beam size (that has a default value of 50.0) can be controlled with the following new parameters:\n```\n  --disable-strict-punctuation\n                              Disable strict punctuation alignment (which prevents punctuation aligning with words).\n  --disable-favored-subs      Disable favored substitutions (which makes alignment favor substitutions between words which differ only by case).\n  --favored-sub-cost FLOAT    Cost for favored substitutions (e.g., case diff). Default: 0.1\n```\n\n## Installation\n\n### Dependencies\nWe use git submodules to manage third-party dependencies. Initialize and update submodules before proceeding to the main build steps.\n```\ngit submodule update --init --recursive\n```\n\nThis will pull the current dependencies:\n- catch2 - for unit testing\n- spdlog - for logging\n- CLI11 - for CLI construction\n- csv - for CTM and NLP input parsing\n- jsoncpp - for JSON output construction\n- strtk - for various string utilities\n\nAdditionally, we have dependencies outside of the third-party submodules:\n- OpenFST - currently provided to the build system by settings the $OPENFST_ROOT environment variable or during the CMake command via `-DOPENFST_ROOT`.\n\n### Build\nThe current build framework is CMake. Install CMake following the instructions here (https://cmake.org/install/).\n\nTo build fstalign, run:\n```\n    mkdir build \u0026\u0026 cd build\n    cmake .. -DOPENFST_ROOT=\"\u003cpath to OpenFST\u003e\" -DDYNAMIC_OPENFST=ON\n    make\n```\n\nNote: `-DDYNAMIC_OPENFST=ON` is needed if OpenFST at `OPENFST_ROOT` is compiled as shared libraries. Otherwise static libraries are assumed.\n\nFinally, tests can be run using:\n```\nmake test\n```\n\n### Docker\n\nThe fstalign docker image is hosted on Docker Hub and can be easily pulled and run:\n```\ndocker pull revdotcom/fstalign\ndocker run --rm -it revdotcom/fstalign\n```\n\nSee https://hub.docker.com/r/revdotcom/fstalign/tags for the available versions/tags to pull. If you desire to run the tool on local files you can mount local directories with the `-v` flag of the `docker run` command.\n\nFrom inside the container:\n```\n/fstalign/build/fstalign --help\n```\n\nFor development you can also build the docker image locally using:\n```\ndocker build . -t fstalign-dev\n```\n\n## Documentation\nFor more information on how to use `fstalign` see our [documentation](https://github.com/revdotcom/fstalign/blob/develop/docs/Usage.md) for more details.\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frevdotcom%2Ffstalign","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Frevdotcom%2Ffstalign","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frevdotcom%2Ffstalign/lists"}