{"id":15018970,"url":"https://github.com/soundcloud/remixin","last_synced_at":"2025-08-24T01:16:37.249Z","repository":{"id":26000936,"uuid":"29443419","full_name":"soundcloud/remixin","owner":"soundcloud","description":"Mixin library for Javascript","archived":false,"fork":false,"pushed_at":"2023-10-19T18:02:01.000Z","size":793,"stargazers_count":27,"open_issues_count":7,"forks_count":4,"subscribers_count":164,"default_branch":"master","last_synced_at":"2025-08-14T15:53:09.354Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":"","language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/soundcloud.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2015-01-18T22:24:08.000Z","updated_at":"2024-09-13T06:56:48.000Z","dependencies_parsed_at":"2023-01-14T03:50:34.594Z","dependency_job_id":null,"html_url":"https://github.com/soundcloud/remixin","commit_stats":null,"previous_names":[],"tags_count":4,"template":false,"template_full_name":null,"purl":"pkg:github/soundcloud/remixin","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/soundcloud%2Fremixin","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/soundcloud%2Fremixin/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/soundcloud%2Fremixin/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/soundcloud%2Fremixin/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/soundcloud","download_url":"https://codeload.github.com/soundcloud/remixin/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/soundcloud%2Fremixin/sbom","scorecard":{"id":839082,"data":{"date":"2025-08-18","repo":{"name":"github.com/soundcloud/remixin","commit":"6d5baf5b0c4738b535b86def4ab87bb9a5259fb3"},"scorecard":{"version":"v5.2.1-41-g40576783","commit":"40576783fda6698350fcbbeaea760ff827433034"},"score":2.8,"checks":[{"name":"Code-Review","score":5,"reason":"Found 6/12 approved changesets -- score normalized to 5","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/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#code-review"}},{"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/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#dangerous-workflow"}},{"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/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#maintained"}},{"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/40576783fda6698350fcbbeaea760ff827433034/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/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#token-permissions"}},{"name":"Binary-Artifacts","score":10,"reason":"no binaries found in the repo","details":null,"documentation":{"short":"Determines if the project has generated executable (binary) artifacts in the source repository.","url":"https://github.com/ossf/scorecard/blob/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#binary-artifacts"}},{"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/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#pinned-dependencies"}},{"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/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#cii-best-practices"}},{"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/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#fuzzing"}},{"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/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#security-policy"}},{"name":"License","score":10,"reason":"license file detected","details":["Info: project has a license file: LICENSE:0","Info: FSF or OSI recognized license: MIT License: LICENSE:0"],"documentation":{"short":"Determines if the project has defined a license.","url":"https://github.com/ossf/scorecard/blob/40576783fda6698350fcbbeaea760ff827433034/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/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#signed-releases"}},{"name":"Branch-Protection","score":-1,"reason":"internal error: error during branchesHandler.setup: internal error: githubv4.Query: Resource not accessible by integration","details":null,"documentation":{"short":"Determines if the default and release branches are protected with GitHub's branch protection settings.","url":"https://github.com/ossf/scorecard/blob/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#branch-protection"}},{"name":"SAST","score":0,"reason":"SAST tool is not run on all commits -- score normalized to 0","details":["Warn: 0 commits out of 24 are checked with a SAST tool"],"documentation":{"short":"Determines if the project uses static code analysis.","url":"https://github.com/ossf/scorecard/blob/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#sast"}},{"name":"Vulnerabilities","score":0,"reason":"47 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-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-w8qv-6jwh-64r5","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-8r6j-v8pm-fqw3","Warn: Project is vulnerable to: MAL-2023-462","Warn: Project is vulnerable to: GHSA-q42p-pg8m-cqh6","Warn: Project is vulnerable to: GHSA-w457-6q6x-cgp9","Warn: Project is vulnerable to: GHSA-62gr-4qp9-h98f","Warn: Project is vulnerable to: GHSA-f52g-6jhx-586p","Warn: Project is vulnerable to: GHSA-2cf5-4w76-r9qv","Warn: Project is vulnerable to: GHSA-3cqr-58rm-57f8","Warn: Project is vulnerable to: GHSA-g9r4-xpmj-mj65","Warn: Project is vulnerable to: GHSA-q2c6-c6pm-g3gh","Warn: Project is vulnerable to: GHSA-765h-qjxv-5f44","Warn: Project is vulnerable to: GHSA-f2jv-r9rf-7988","Warn: Project is vulnerable to: GHSA-43f8-2h32-f4cj","Warn: Project is vulnerable to: GHSA-qqgx-2p2h-9c37","Warn: Project is vulnerable to: GHSA-9c47-m6qq-7p4h","Warn: Project is vulnerable to: GHSA-6c8f-qphg-qjgp","Warn: Project is vulnerable to: GHSA-p6mc-m468-83gw","Warn: Project is vulnerable to: GHSA-29mw-wpgm-hmr9","Warn: Project is vulnerable to: GHSA-35jh-r3h4-6jhm","Warn: Project is vulnerable to: GHSA-4xcv-9jjx-gfj3","Warn: Project is vulnerable to: GHSA-952p-6rrq-rcjv","Warn: Project is vulnerable to: GHSA-f8q6-p94x-37v3","Warn: Project is vulnerable to: GHSA-vh95-rmgr-6w4m","Warn: Project is vulnerable to: GHSA-xvch-5gv4-984h","Warn: Project is vulnerable to: GHSA-fhjf-83wg-r2j9","Warn: Project is vulnerable to: GHSA-hj48-42vr-x3v9","Warn: Project is vulnerable to: GHSA-c2qf-rxjj-qqgw","Warn: Project is vulnerable to: GHSA-4g88-fppr-53pp","Warn: Project is vulnerable to: GHSA-4jqc-8m5r-9rpr","Warn: Project is vulnerable to: GHSA-3jfq-g458-7qm9","Warn: Project is vulnerable to: GHSA-r628-mhmh-qjhw","Warn: Project is vulnerable to: GHSA-9r2w-394v-53qc","Warn: Project is vulnerable to: GHSA-5955-9wpr-37jh","Warn: Project is vulnerable to: GHSA-qq89-hq3f-393p","Warn: Project is vulnerable to: GHSA-f5x3-32g6-xq36","Warn: Project is vulnerable to: GHSA-cf4h-3jhx-xvhq","Warn: Project is vulnerable to: GHSA-c4w7-xm78-47vh","Warn: Project is vulnerable to: GHSA-p9pc-299p-vxgp"],"documentation":{"short":"Determines if the project has open, known unfixed vulnerabilities.","url":"https://github.com/ossf/scorecard/blob/40576783fda6698350fcbbeaea760ff827433034/docs/checks.md#vulnerabilities"}}]},"last_synced_at":"2025-08-23T19:58:34.887Z","repository_id":26000936,"created_at":"2025-08-23T19:58:34.887Z","updated_at":"2025-08-23T19:58:34.887Z"},"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":271778236,"owners_count":24819265,"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-08-23T02:00:09.327Z","response_time":69,"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":[],"created_at":"2024-09-24T19:52:41.338Z","updated_at":"2025-08-24T01:16:37.229Z","avatar_url":"https://github.com/soundcloud.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"## Remixin [![version][npm badge]][npm] [![build status][travis badge]][travis]\n\nRemixin is the aspect-oriented mixin library developed and in use at [SoundCloud][soundcloud]. It is inspired by Twitter's [advice.js][advice] and [Joose][joose].\n\nFor an introduction about why you'd want to use a mixin library, Angus Croll and Dan Webb from Twitter gave a good [talk about the concept][slides] and Angus [blogged on the subject][blog].\n\n## Installation\n\nInstall the package via npm:\n\n```shell\nnpm install remixin\n```\n\nAnd then import it:\n\n```js\nimport { Mixin } from 'remixin';\n```\n\nAlternatively, download a browser-ready version from the unpkg CDN:\n\n```html\n\u003cscript src=\"https://unpkg.com/underscore\"\u003e\u003c/script\u003e \u003c!-- creates window._ --\u003e\n\u003cscript src=\"https://unpkg.com/remixin\"\u003e\u003c/script\u003e \u003c!-- creates window.remixin --\u003e\n```\n\n([Underscore.js][underscore] is a dependency and needs to be included first.)\n\n## Usage\n\n- Create a new mixin using `mixin = new Mixin(modifiers)`\n- Apply a mixin to an object, using `mixin.applyTo(object)`\n- Pass options to a mixin which has a custom apply method using `mixin.applyTo(object, options)`\n- Curry options into a mixin using `curried = mixin.withOptions(options)`\n- Combine mixins by using `combined = new Mixin(mixin1, [mixin2, ...], modifiers)`\n\n### Modifiers\n\nWhen defining a mixin, there are several key words to define method modifiers:\n\n- `before`: `{Object.\u003cString,Function\u003e}`\n  - defines methods to be executed before the original function. It has the same function signature (it is given the\n    same arguments list) as the original, but can not modify the arguments passed to the original, nor change whether\n    the function is executed.\n- `after`: `{Object.\u003cString,Function\u003e}`\n  - The same as `before`, this has the same signature, but can not modify the return value of the function.\n- `around`: `{Object.\u003cString,Function\u003e}`\n  - defines methods to be executed 'around' the original. The original function is passed as the first argument,\n    followed by the original arguments. The modifier function may change the arguments to be passed to the original,\n    may modify the return value, and even can decide not to execute the original. Given the power that this provides,\n    use with care!\n- `requires`: `{Array.\u003cString\u003e}`\n  - an array of property names which must exist on the target object (or its prototype). Basically defines an expected\n    interface.\n- `requirePrototype`: `{Object}`\n  - this prototype should be present on the target object's prototype chain. can be used to specify what 'class'\n    target should be or from what prototype it should inherit from.\n- `override`: `{Object.\u003cString,*\u003e}`\n  - properties or methods which specifically should override the values already defined on the target object.\n- `defaults`: `{Object.\u003cString,*\u003e}`\n  - properties or methods which should be applied to the target object only if they do not already exist on that\n    object. Properties defined in the prototype chain will be overridden.\n- `merge`: `{Object.\u003cString,Array|Object|String}`\n  - a map of objects, arrays or strings to apply to the target object, merging with existing properties if they already\n    exist. The merge strategy used depends on the data type used in the mixin:\n    - Arrays are concatenated, ensuring uniqueness.\n    - Objects are extended without replacing existing keys. That is, it uses `_.extend({}, mixin.obj, target.obj)`.\n    - Strings are treated like space-separated token lists: concatenated, ensuring uniqueness.\n\nAll other keys are copied onto the target object unless that key already exists. If overriding these keys is desired,\nthen it should be defined in the `override` block. If a default implementation is desired, then it should be defined in\nthe `defaults` block.\n\nIncorrect use of these modifiers will throw an error if `Mixin.debug` is set to `true`. For example, if a field declared in `requires` is not found, or if a `before` is applied on a non-function. By default, `Mixin.debug` is `false`.\n\n### Custom `applyTo`\n\nIf custom code is required for your mixin, then defining a key named `applyTo` allows a custom method to be executed\nwhen the mixin is applied. This method is passed two arguments: the target object and any options defined by the\ncalling code:\n\n```js\nzoomable = new Mixin({\n applyTo(obj, options) {\n   this.extend(obj, {\n     zoom() {\n       this.width *= options.zoomRatio;\n       this.height *= options.zoomRatio;\n     }\n   });\n }\n});\n\nzoomable.applyTo(MyCanvasObject.prototype, { zoomRatio: 2 });\n```\n\nAll of the standard modifier names (eg: after, around, before) are available in the context, as well as `extend` to add\nnew properties.\n\n### Currying options\n\nTaking the example from above, sometimes it's more convenient to have the options curried into the mixin already. For\nthis, use `.withOptions` which will return a new mixin with those options stored. For example:\n\n```js\nvar standardDPI = zoomable.withOptions({ zoomRatio: 1});\nvar highDPI = zoomable.withOptions({ zoomRatio: 2 });\n```\n\n### Combining mixins\n\nSometimes, one mixin will necessitate the target object also having another mixin. For example, you might have a mixin\nwhich gives a View the behaviour of a drop-down menu. Drop-down menus have some shared behaviour with other overlays,\nsuch as modal dialogues. These can be combined into a single mixin, to hide the implementation from the class which\nrequires the combined behaviour:\n\n```js\noverlay = new Mixin({\n  merge: {\n    events: {\n      'click .closeButton': 'onCloseClick'\n    }\n  },\n  show() { ... },\n  hide() { ... },\n  onCloseClick() {\n    this.hide();\n  }\n});\n\ndropDownMenu = new Mixin(overlay, {\n  after: {\n    onCloseClick() {\n      this.parentButton.focus();\n    }\n  }\n});\n\nProfileButton = View.extend({ ... });\ndropDownMenu.applyTo(ProfileButton.prototype);\n```\n\nAny number of mixins can be combined into one:\n\n```js\nmegaMixin = new Mixin(mixin1, mixin2, mixin3, mixin4, {});\n```\n\n## Development\n\nTo build the source:\n\n```shell\nmake\n```\n\nTo run the tests:\n\n```shell\nmake test\n```\n\nTo see a coverage report:\n\n```shell\nmake coverage\n```\n\n[npm]: https://www.npmjs.org/package/remixin\n[npm badge]: https://img.shields.io/npm/v/remixin.svg\n[travis]: https://travis-ci.org/soundcloud/remixin\n[travis badge]: https://img.shields.io/travis/soundcloud/remixin.svg\n[advice]: https://github.com/flightjs/flight/blob/master/lib/advice.js\n[blog]: https://javascriptweblog.wordpress.com/2011/05/31/a-fresh-look-at-javascript-mixins/\n[joose]: http://joose.it/\n[slides]: https://speakerdeck.com/anguscroll/how-we-learned-to-stop-worrying-and-love-javascript\n[soundcloud]: https://soundcloud.com\n[underscore]: https://underscorejs.org\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsoundcloud%2Fremixin","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fsoundcloud%2Fremixin","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsoundcloud%2Fremixin/lists"}