{"id":13832299,"url":"https://github.com/cmtt/dijs","last_synced_at":"2025-07-09T16:35:06.894Z","repository":{"id":15726972,"uuid":"18465238","full_name":"cmtt/dijs","owner":"cmtt","description":"JavaScript dependency injection for Node and browser environments.","archived":true,"fork":false,"pushed_at":"2016-07-03T13:25:10.000Z","size":98,"stargazers_count":50,"open_issues_count":0,"forks_count":2,"subscribers_count":3,"default_branch":"master","last_synced_at":"2024-04-26T18:04:27.102Z","etag":null,"topics":["dependency-injection","javascript","javascript-dependency-injection"],"latest_commit_sha":null,"homepage":null,"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/cmtt.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":"2014-04-05T11:11:51.000Z","updated_at":"2024-02-21T09:38:01.000Z","dependencies_parsed_at":"2022-08-25T11:50:12.903Z","dependency_job_id":null,"html_url":"https://github.com/cmtt/dijs","commit_stats":null,"previous_names":[],"tags_count":5,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/cmtt%2Fdijs","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/cmtt%2Fdijs/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/cmtt%2Fdijs/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/cmtt%2Fdijs/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/cmtt","download_url":"https://codeload.github.com/cmtt/dijs/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":225575308,"owners_count":17490737,"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":["dependency-injection","javascript","javascript-dependency-injection"],"created_at":"2024-08-04T10:01:58.759Z","updated_at":"2024-11-20T14:30:48.561Z","avatar_url":"https://github.com/cmtt.png","language":"JavaScript","readme":"# dijs\n\n\u003cdiv\u003e\n  \u003ca href=\"https://travis-ci.org/cmtt/dijs\"\u003e\n    \u003cimg src=\"https://img.shields.io/travis/cmtt/dijs.svg?style=flat-square\" alt=\"Build Status\"\u003e\n  \u003c/a\u003e\n  \u003ca href=\"https://www.npmjs.org/package/dijs\"\u003e\n    \u003cimg src=\"https://img.shields.io/npm/v/dijs.svg?style=flat-square\" alt=\"npm version\"\u003e\n  \u003c/a\u003e\n  \u003ca href=\"http://spdx.org/licenses/MIT\"\u003e\n    \u003cimg src=\"https://img.shields.io/npm/l/dijs.svg?style=flat-square\" alt=\"npm licence\"\u003e\n  \u003c/a\u003e\n  \u003ca href=\"https://coveralls.io/github/cmtt/dijs\"\u003e\n    \u003cimg src=\"https://img.shields.io/coveralls/cmtt/dijs/master.svg?style=flat-square\" alt=\"Code coverage\"\u003e\n  \u003c/a\u003e\n  \u003ca href=\"http://www.ecma-international.org/ecma-262/6.0/\"\u003e\n    \u003cimg src=\"https://img.shields.io/badge/ES-2015-F0DB4F.svg?style=flat-square\" alt=\"ECMAScript 2015\"\u003e\n  \u003c/a\u003e\n\u003c/div\u003e\n\ndijs is a dependency injection framework for Node.js and browser environments.\n\nIt is inspired by [AngularJS](http://www.angularjs.org/) 1.x and allows to\nchoose between synchronous and asynchronous (using callbacks and promises)\nresolution patterns in an non-opinionated way.\n\nFeatured on [DailyJS](http://dailyjs.com/2014/05/25/angular-roundup/).\n\n# Example\n\n````js\n  const Di = require('dijs');\n\n  class TestClass {\n    constructor (PI, RAD_TO_DEG) {\n      this.PI = PI;\n      this.RAD_TO_DEG = RAD_TO_DEG;\n    }\n\n    deg (value) {\n      return value * this.RAD_TO_DEG;\n    }\n  }\n\n  // Initialize a new dijs instance. By default, this will use \"CallbackMethod\",\n  // thus the first argument is \"null\" (instead providing another method).\n  // The $provide and $resolve method expect callback functions.\n\n  let instance = new Di(null)\n  // Provides a constant\n  .$provideValue('PI', Math.PI)\n  // Providing a constant using dependencies\n  .$provide('RAD_TO_DEG', (PI, callback) =\u003e callback(null, (180 / PI)))\n  .$resolve((err) =\u003e {\n    if (err) {\n      throw err;\n    }\n    let AnnotatedTestClass = instance.$annotate(TestClass);\n    let a = new AnnotatedTestClass();\n\n    // logs 180\n    console.log(a.deg(Math.PI));\n  });\n\n````\n# Options\n\n## assign\n\nBy default, all provided values are being set on the dijs instance. This\nbehavior can be turned off:\n\n````js\n  const Di = require('dijs');\n  let d = new Di(null, 'Math', { assign : false });\n\n  d.$provide('PI', function (callback) {\n    callback(null, Math.PI);\n  });\n  d.$resolve(function (err) {\n    if (err) {\n      throw err;\n    }\n    console.log(`d.PI is undefined`, d.PI === undefined);\n    console.log(`d.$get(\"PI\") equals Math.PI`, d.$get('PI') === Math.PI);\n  });\n});\n````\n\n# Usage\n\n## new Di(Method, name, options)\n\nReturns a new dijs instance with the given method (CallbackMethod is the\ndefault one).\n\n## Instance methods\n\n### $annotate(classFn)\n\nReturns a class which will be initialized with the dependencies stated in\nclassFn's constructor. When classFn is a function, its parameters are being\nresolved to matching dependencies.\n\nThis method must called after $resolve().\n\n### $get(id)\n\nReturns the (previously provided) sub-module specified by a dot-delimited id.\n\n### $inject(arg)\n\nCalls a function with (already-provided) dependencies. It is required to call\n$resolve beforehand.\n\nDependant on the current resolution method, this function is synchronous or\nasynchronous\n\n### $provide(key, object, passthrough)\n\nProvides a module in the namespace with the given key.\n\nIf passthrough is set, the object will be just passed through, no dependencies\nare looked up this way.\n\n### $provideValue(key, object)\n\nProvides a value in the namespace with the given key (shortcut for $provide\nusing passthrough).\n\n### $resolve()\n\nResolves the dependency graph.\n\nThis method might take a callback function (in case of the default\nCallbackMethod) or return a promise with PromiseMethod.\n\n### $set(id, value)\n\nSets a value in the namespace, specified by a dot-delimited path.\n\n# Resolution methods\n\nBy default, dijs uses the asynchronous CallbackMethod in order to resolve\ndependencies. Require them as follwing:\n\n````js\nconst Di = require('dijs');\nconst SyncMethod = require('dijs/methods/sync');\nconst PromiseMethod = require('dijs/methods/promise');\n````\n\n## CallbackMethod\n\nAsynchronous providing and resolving dependencies using Node.js-style callback\nfunctions.\n\nIt is expected that the last parameter of your callback functions is called\n\"callback\", \"cb\" or \"next\".\n\nThis function takes an error (or a falsy value like null) as first argument. The\nsecond argument should be the provided value.\n\n````js\n  let d = new Di();\n  d.$provide('PI', (callback) =\u003e { // alternative names: cb or next\n    callback(null, Math.PI);\n  });\n\n  d.$resolve((err) =\u003e {\n    if (err) {\n      return done(err);\n    }\n    assert.equal(d.PI, Math.PI);\n    done();\n  });\n````\n\n## PromiseMethod\n\nProvides and resolves dependencies using the ES2015 Promise API.\n\n````js\n  let d = new Di();\n  d.$provide('PI', Promise.resolve(Math.PI));\n  d.$provide('2PI', (PI) =\u003e Promise.resolve(2 * Math.PI));\n  d.$resolve().then(() =\u003e {\n    assert.equal(d['2PI'], 2 * Math.PI);\n    done();\n  }, (err) =\u003e {\n    done(err);\n  });\n````\n\n## SyncMethod\n\nSynchronous way to provide and resolve depdencies.\n\n````js\n  let d = new Di(SyncMethod);\n  d.$provide('PI', Math.PI);\n  d.$provide('2PI', (PI) =\u003e 2 * Math.PI);\n  d.$resolve();\n  assert.equal(d['2PI'], 2 * Math.PI);\n````\n\n# Reference\n\n## Notation\n\nIf you don't pass a value through, you can choose between the function and the\narray notation to describe the module's dependencies. In any case, you will need\nto pass a function whose return value gets stored in the namespace. Its\nparameters describe its dependencies.\n\n### function notation\n\nTo describe a dependency, you can pass a function whose parameters declare the\nother modules on which it should depend.\n\nNote: You cannot inject dot-delimited dependencies with this notation.\n\n````js\n  var mod = new Di();\n  mod.$provide('Pi',Math.PI, true);\n  mod.$provide('2Pi', function (Pi, callback) { callback(null, return 2*Pi); });\n  // ...\n````\n\n### array notation (minification-safe)\n\nWhen your code is going to be minified or if you are about to make use of nested\nnamespaces, the array notation is safer to use. All dependencies are listed as\nstrings in the first part of the array, the last argument must be the actual\nmodule function.\n\n````js\n  var mod = new Di();\n  mod.$provide('Math.Pi',Math.PI, true);\n  mod.$provide('2Pi', ['Math.Pi', function (Pi, callback) {\n    callback(null, 2*Pi);\n  }]);\n  // ...\n````\n\n#### notation with \"$inject\" (minification-safe)\n\nAn alternative way is to provide a \"$inject\" property when using $annotate or\n$provide. This requires minification tools being in use not to mangle this key:\n\n````js\n\n  class TestClass {\n    constructor (pi) {\n      this.RAD_TO_DEG = (180 / pi);\n    }\n\n    deg (value) {\n      return value * this.RAD_TO_DEG;\n    }\n  }\n\n  TestClass['$inject'] = ['PI'];\n\n  var mod = new Di();\n  mod.$provideValue('PI', Math.PI);\n  mod.$resolve((err) =\u003e {\n    if (err) { throw err; }\n    let WrappedTestClass = mod.$annotate(TestClass);\n    let instance = new WrappedTestClass();\n    console.log(instance.deg(Math.PI * 2)); // 360\n  });\n\n  ````\n\n# Namespacing\n\nEach dijs instance has a new namespace instance at its core. Namespaces provide\ngetter/setter methods for sub-paths:\n\n````js\n  var Namespace = require('dijs/lib/namespace');\n  var namespace = new Namespace('home');\n  namespace.floor = { chair : true };\n  assert.deepEqual(namespace.$get('home.floor'), { chair : true})\n  namespace.$set('home.floor.chairColor', 'blue');\n  assert.deepEqual(namespace.floor, { chair: true, chairColor: 'blue' });\n````\n\nPlease note that dijs assigns all namespace values to instances. You can disable\nthis behavior using the \"assign\" option (see above).\n\n# Usage in the browser\n\nBundled versions are available in the dist/ folder.\n\nYou can create a minified build with Google's Closure compiler by running\n````make```` in the project directory.\n\n# License\n\nMIT (see LICENSE)\n","funding_links":[],"categories":["JavaScript"],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fcmtt%2Fdijs","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fcmtt%2Fdijs","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fcmtt%2Fdijs/lists"}