{"action":"created","comment":{"url":"https://api.github.com/repos/fluid-project/infusion-docs/pulls/comments/43003386","id":43003386,"diff_hunk":"@@ -0,0 +1,236 @@\n+---\n+title: Promises\n+layout: default\n+category: Infusion\n+---\n+\n+# Infusion Promises API\n+\n+[Promises](https://en.wikipedia.org/wiki/Futures_and_promises) are a now widespread programming construct aiming to \n+simplify coding of complex workflows involving values which may be available asynchronously (perhaps as a result\n+of requiring I/O) or fallibly. JavaScript enjoys numerous competing libraries implementing this feature, such as \n+[when.js](https://github.com/cujojs/when), [Q](http://documentup.com/kriskowal/q) and [Bluebird](https://github.com/petkaantonov/bluebird)\n+as well as even multiple competing promise standards, such as [Promises/A+](https://promisesaplus.com/) and others from [CommonJS](http://wiki.commonjs.org/wiki/Promises).\n+Promises are even built into an upcoming version of the JavaScript language itself, [ES6](https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Global_Objects/Promise).\n+\n+Infusion required an extremely simple implementation which can evolve independently, as well as begin the process of merging with\n+the general declarative facilities of [Infusion IoC](HowToUseInfusionIoC.md) and hence become invisible as code. The implementation described here is a \n+transitional, mostly procedural system on its way to being summarised as configuration - as numerous Infusion features have\n+been in their turn over the years.\n+\n+## Notes on interoperability\n+\n+As commented [below](#commentary-on-requirements), Infusion promises have taken a different set of tradeoffs to many of those elsewhere in the industry. In terms of interoperability,\n+Infusion promises are at least universally recognised as a \"[foreign thenable](https://github.com/cujojs/when/blob/master/docs/api.md#when)\" and hence can be easily adapted into promises of any of the other libraries.\n+In terms of promise algorithms, since Infusion promises meet a weaker contract than usual, Infusion promises cannot safely be supplied to the promise\n+algorithms of other libraries without adaptation. However, promises from foreign libraries can easily be used within Infusion's algorithms.\n+\n+## Core Promises API\n+\n+### fluid.promise()\n+\n+* Returns: `{Promise}`\n+\n+Construct a fresh promise. This is the only point at which fresh promises are constructed within the core API.\n+\n+### promise.then(onResolve, onReject)\n+\n+Adds handlers to either or both of the `resolve` or `reject` actions of the promise. Note that if the promise has already been\n+rejected or resolved, the appropriate handler will be notified immediately on this registration.\n+\n+* `onResolve: {Function ({Any}) →  None}` A callback to receive the successfully resolved value of the promise\n+* `onReject: {Function ({Error}) →  None}` A callback to receive a rejection of the promise, in the case its resolution fails.\n+\n+### promise.resolve(value)\n+\n+Resolves the promise successfully, yielding the value `value` to any listeners which were previously registered as the first\n+argument of `promise.then`. Any further attempts to call either `resolve` or `reject` will signal an assertion failure.\n+\n+* `value: {Any}` The value to be supplied as the resolution value of the promise\n+\n+### promise.reject(error)\n+\n+Rejects the promise, yielding the error `error` to any listeners which were previously registered as the second \n+argument of `promise.then`. Any further attempts to call either `resolve` or `reject` will signal an assertion failure.\n+\n+* `error: {Object|Error}` The value to be supplied as the rejection reason for the promise. It is recommended that this be an\n+object with a boolean entry `isError: true` and a String `message` summarising the reason for the rejection. \n+\n+### promise.disposition\n+\n+The current disposition of the promise may be inspected at any time. This is a `String` value which encodes which, if any, of\n+`resolve` or `reject` have been received by the promise. At the fresh construction of the promise, the member `disposition` holds\n+the value `undefined`. If the promise has received `resolve`, `disposition` will hold the string `\"resolve\"`, or if the\n+promise has received `reject`, `disposition` will hold the string `\"reject\"`.\n+\n+### Commentary on core API\n+\n+This is 100% of the core implementation of Infusion promises. It puts us in a position to answer, in terms of familiar constructions\n+such as [events](InfusionEventSystem.md), the question \"What actually is a promise?\" (although not in itself the more important question\n+\"What can a promise be used for?\")\n+\n+A promise is\n+\n+* A linked pair of event firers, named `resolve` and `reject`\n+* At most one of these two events can be fired, at most one time in total\n+* Any listeners registered to either of the events after the point of firing will be able to recover the (unique) fired value at the point of registration\n+\n+Note that this description does not adequately account for the features of specification-conformant promises more widely used in the industry - since these\n+implement chaining and asynchronous behaviours which we do not implement.\n+\n+### Commentary on requirements\n+\n+As well as evolvability and enormous simplicity, we had a couple of other somewhat soft requirements - readability, and debuggability.\n+Modern promise specifications actually ***require*** that fresh promises are constructed at every chaining point, and that every\n+promise resolves asynchronously even if its resolving value is available synchronously. Our implementation guarantees that no promise is\n+constructed unless there is an explicit call to the constructor `fluid.promise()`. Thus it is easy to see at a glance exactly how many \n+promises are in play in a given piece of code. Secondly, our implementation will synchronously relay a value which is available\n+synchronously - this means that in the debugger, or other source of stack traces, the maximal size of stack will be visible to \n+account for the cause of the promise resolution.\n+\n+Plenty of arguments exist against these choices - in fact, these choices place us firmly in the category of people who \"don't really understand\n+promises and think of them as glorified ... callback aggregators\". In the meantime, we have work to do. Infusion is about the elimination of\n+code, and so we only have limited time to spend thinking about how to make the code we do have conform to a faulty ideal of what we dreamed\n+that the virtues of conventional, synchronous code might once have been. However, it's worth noting that there is at least [one virtue](#promise-accumulaterejectionreason-error-) of \n+conventional, synchronous code that is recaptured by no other promise system but ours. Also, this [github issue](https://github.com/promises-aplus/promises-spec/issues/4) attached to the \n+A+ promises specification is a useful source of convincing argumentation that the decision in favour of universally asynchronous resolution is flawed.\n+\n+As a further landmark for discussion, note that in terms of the following very illuminating [category theoretic](http://brianmckenna.org/blog/category_theory_promisesaplus) treatment of \n+promises (itself rejected by mainstream promises proponents), our `then` method is very definitely ***not*** \"the name for `flatMap`\". \n+Our `then` method is simply a \"glorified callback aggregator\".\n+\n+The implementation skeleton for Infusion's promises was taken from a code sample by John Hann (unscriptable) in this [gist](https://gist.github.com/unscriptable/814052) - full credit and thanks,\n+and please read the gist for some further commentary and coverage of limitations.\n+\n+\n+## Core Promises Utility API\n+\n+The library implements a few utilities without which it is inconvenient to use promises:\n+\n+### fluid.isPromise(totest)\n+\n+* `totest {Any}` An object to be checked for being a promise\n+* Returns: `{Boolean}` If `totest` has a member `then` of type `Function`, returns `true`.\n+\n+Determines whether an object is a promise, for our purposes. Any object with a member `then` of type `Function` passes this test.\n+This includes essentially every known variety, including jQuery promises. This test in fact identifies what in other libraries is\n+termed a \"foreign thenable\".\n+\n+### fluid.toPromise(value)\n+\n+* `value {Any}` A value to be converted (\"hoisted\") to a promise\n+* Returns: `{Promise}` If the supplied value is already a promise, it is returned unchanged. Otherwise a fresh promise is created with the value as resolution and returned.\n+\n+Coerces any value to a promise. If it is already a promise, it is returned unchanged. Otherwise, `toPromise` constructs a fresh promise resolving to the supplied value.\n+\n+\n+### fluid.promise.follow(source, target)\n+\n+* `source {Promise}` A promise which is to be followed in its resolution.\n+* `target {Promise}` A promise which will follow the `source` in its resolution. `target` will receive a call to `then` causing it to resolve when `source` resolves,\n+and reject when `source` rejects. \n+\n+Chains the resolution methods of one promise (target) so that they follow those of another (source).\n+That is, whenever source resolves, target will resolve, or when source rejects, target will reject, with the\n+same payloads in each case.\n+\n+### fluid.promise.map(source, func)\n+\n+Returns a promise whose resolved value is mapped from the source promise or value by the supplied function. If the input value is not a promise, it will\n+be converted first to a promise via `fluid.toPromise()`. If the input promise rejects, its rejection reason will be propagated unmapped. \n+\n+* `source {Object|Promise}` An object or promise whose value is to be mapped (if an object, will be converted first to a promise via `fluid.toPromise()`)\n+* `func {Function: ({Any})  →  Any}` A function which will map the resolved promise value\n+* Returns: `{Promise}` A promise for the resolved mapped value.\n+ \n+## Promise algorithms\n+\n+The only currently implemented promise algorithms are based around a core skeleton operating an array of promises in a linear sequence. These \n+are responsive to an additional element of our promises API, the  [`fluid.accumulateRejectionReason`](#promise.accumulaterejectionreason-error-) \"inverse API\" described below.\n+\n+### fluid.promise.sequence(sources[, options])\n+\n+* `sources {Array of {Any|Promise|Function:(options {Object}) →  Any|Promise}}` An array of sources of values or promises which will be evaluated in sequence.\n+* `options {Object}` [optional] A structure of options which will be supplied to function members of `sources`.  \n+\n+Accepts an array of values, promises, functions returning values or functions returning promises and evaluates them in sequence. Note that a standard name for a \"function returning a promise\" ","path":"src/documents/PromisesAPI.md","position":156,"original_position":156,"commit_id":"49d791bb36aa04b080a0e8f041ef82c7c9bcc019","original_commit_id":"49d791bb36aa04b080a0e8f041ef82c7c9bcc019","user":{"login":"acheetham","id":562946,"avatar_url":"https://avatars.githubusercontent.com/u/562946?v=3","gravatar_id":"","url":"https://api.github.com/users/acheetham","html_url":"https://github.com/acheetham","followers_url":"https://api.github.com/users/acheetham/followers","following_url":"https://api.github.com/users/acheetham/following{/other_user}","gists_url":"https://api.github.com/users/acheetham/gists{/gist_id}","starred_url":"https://api.github.com/users/acheetham/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/acheetham/subscriptions","organizations_url":"https://api.github.com/users/acheetham/orgs","repos_url":"https://api.github.com/users/acheetham/repos","events_url":"https://api.github.com/users/acheetham/events{/privacy}","received_events_url":"https://api.github.com/users/acheetham/received_events","type":"User","site_admin":false},"body":"The explanation of what this function does is a bit lacking. The sources are \"evaluated\" – what does that mean, particularly in the case when they're not Promises or functions?","created_at":"2015-10-26T14:56:52Z","updated_at":"2015-10-26T14:56:52Z","html_url":"https://github.com/fluid-project/infusion-docs/pull/77#discussion_r43003386","pull_request_url":"https://api.github.com/repos/fluid-project/infusion-docs/pulls/77","_links":{"self":{"href":"https://api.github.com/repos/fluid-project/infusion-docs/pulls/comments/43003386"},"html":{"href":"https://github.com/fluid-project/infusion-docs/pull/77#discussion_r43003386"},"pull_request":{"href":"https://api.github.com/repos/fluid-project/infusion-docs/pulls/77"}}},"pull_request":{"url":"https://api.github.com/repos/fluid-project/infusion-docs/pulls/77","id":48000073,"html_url":"https://github.com/fluid-project/infusion-docs/pull/77","diff_url":"https://github.com/fluid-project/infusion-docs/pull/77.diff","patch_url":"https://github.com/fluid-project/infusion-docs/pull/77.patch","issue_url":"https://api.github.com/repos/fluid-project/infusion-docs/issues/77","number":77,"state":"open","locked":false,"title":"FLUID-5791:  Comprehensive documentation for the Core API, Promises API, jqUnit API, IoC API and API for use in node.js","user":{"login":"amb26","id":561418,"avatar_url":"https://avatars.githubusercontent.com/u/561418?v=3","gravatar_id":"","url":"https://api.github.com/users/amb26","html_url":"https://github.com/amb26","followers_url":"https://api.github.com/users/amb26/followers","following_url":"https://api.github.com/users/amb26/following{/other_user}","gists_url":"https://api.github.com/users/amb26/gists{/gist_id}","starred_url":"https://api.github.com/users/amb26/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/amb26/subscriptions","organizations_url":"https://api.github.com/users/amb26/orgs","repos_url":"https://api.github.com/users/amb26/repos","events_url":"https://api.github.com/users/amb26/events{/privacy}","received_events_url":"https://api.github.com/users/amb26/received_events","type":"User","site_admin":false},"body":"together with various updates for consistency, as well as fixes for CSS ToC height issue and implementation of \"hover to link\" functionality as per github's own support for rendering .md files","created_at":"2015-10-18T02:22:02Z","updated_at":"2015-10-26T14:56:52Z","closed_at":null,"merged_at":null,"merge_commit_sha":"2739b497fe5a30ecfd207c0ddfc7cbb1149b13ec","assignee":null,"milestone":null,"commits_url":"https://api.github.com/repos/fluid-project/infusion-docs/pulls/77/commits","review_comments_url":"https://api.github.com/repos/fluid-project/infusion-docs/pulls/77/comments","review_comment_url":"https://api.github.com/repos/fluid-project/infusion-docs/pulls/comments{/number}","comments_url":"https://api.github.com/repos/fluid-project/infusion-docs/issues/77/comments","statuses_url":"https://api.github.com/repos/fluid-project/infusion-docs/statuses/49d791bb36aa04b080a0e8f041ef82c7c9bcc019","head":{"label":"amb26:FLUID-5791","ref":"FLUID-5791","sha":"49d791bb36aa04b080a0e8f041ef82c7c9bcc019","user":{"login":"amb26","id":561418,"avatar_url":"https://avatars.githubusercontent.com/u/561418?v=3","gravatar_id":"","url":"https://api.github.com/users/amb26","html_url":"https://github.com/amb26","followers_url":"https://api.github.com/users/amb26/followers","following_url":"https://api.github.com/users/amb26/following{/other_user}","gists_url":"https://api.github.com/users/amb26/gists{/gist_id}","starred_url":"https://api.github.com/users/amb26/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/amb26/subscriptions","organizations_url":"https://api.github.com/users/amb26/orgs","repos_url":"https://api.github.com/users/amb26/repos","events_url":"https://api.github.com/users/amb26/events{/privacy}","received_events_url":"https://api.github.com/users/amb26/received_events","type":"User","site_admin":false},"repo":{"id":22699996,"name":"infusion-docs","full_name":"amb26/infusion-docs","owner":{"login":"amb26","id":561418,"avatar_url":"https://avatars.githubusercontent.com/u/561418?v=3","gravatar_id":"","url":"https://api.github.com/users/amb26","html_url":"https://github.com/amb26","followers_url":"https://api.github.com/users/amb26/followers","following_url":"https://api.github.com/users/amb26/following{/other_user}","gists_url":"https://api.github.com/users/amb26/gists{/gist_id}","starred_url":"https://api.github.com/users/amb26/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/amb26/subscriptions","organizations_url":"https://api.github.com/users/amb26/orgs","repos_url":"https://api.github.com/users/amb26/repos","events_url":"https://api.github.com/users/amb26/events{/privacy}","received_events_url":"https://api.github.com/users/amb26/received_events","type":"User","site_admin":false},"private":false,"html_url":"https://github.com/amb26/infusion-docs","description":"Documentation space for Infusion","fork":true,"url":"https://api.github.com/repos/amb26/infusion-docs","forks_url":"https://api.github.com/repos/amb26/infusion-docs/forks","keys_url":"https://api.github.com/repos/amb26/infusion-docs/keys{/key_id}","collaborators_url":"https://api.github.com/repos/amb26/infusion-docs/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/amb26/infusion-docs/teams","hooks_url":"https://api.github.com/repos/amb26/infusion-docs/hooks","issue_events_url":"https://api.github.com/repos/amb26/infusion-docs/issues/events{/number}","events_url":"https://api.github.com/repos/amb26/infusion-docs/events","assignees_url":"https://api.github.com/repos/amb26/infusion-docs/assignees{/user}","branches_url":"https://api.github.com/repos/amb26/infusion-docs/branches{/branch}","tags_url":"https://api.github.com/repos/amb26/infusion-docs/tags","blobs_url":"https://api.github.com/repos/amb26/infusion-docs/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/amb26/infusion-docs/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/amb26/infusion-docs/git/refs{/sha}","trees_url":"https://api.github.com/repos/amb26/infusion-docs/git/trees{/sha}","statuses_url":"https://api.github.com/repos/amb26/infusion-docs/statuses/{sha}","languages_url":"https://api.github.com/repos/amb26/infusion-docs/languages","stargazers_url":"https://api.github.com/repos/amb26/infusion-docs/stargazers","contributors_url":"https://api.github.com/repos/amb26/infusion-docs/contributors","subscribers_url":"https://api.github.com/repos/amb26/infusion-docs/subscribers","subscription_url":"https://api.github.com/repos/amb26/infusion-docs/subscription","commits_url":"https://api.github.com/repos/amb26/infusion-docs/commits{/sha}","git_commits_url":"https://api.github.com/repos/amb26/infusion-docs/git/commits{/sha}","comments_url":"https://api.github.com/repos/amb26/infusion-docs/comments{/number}","issue_comment_url":"https://api.github.com/repos/amb26/infusion-docs/issues/comments{/number}","contents_url":"https://api.github.com/repos/amb26/infusion-docs/contents/{+path}","compare_url":"https://api.github.com/repos/amb26/infusion-docs/compare/{base}...{head}","merges_url":"https://api.github.com/repos/amb26/infusion-docs/merges","archive_url":"https://api.github.com/repos/amb26/infusion-docs/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/amb26/infusion-docs/downloads","issues_url":"https://api.github.com/repos/amb26/infusion-docs/issues{/number}","pulls_url":"https://api.github.com/repos/amb26/infusion-docs/pulls{/number}","milestones_url":"https://api.github.com/repos/amb26/infusion-docs/milestones{/number}","notifications_url":"https://api.github.com/repos/amb26/infusion-docs/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/amb26/infusion-docs/labels{/name}","releases_url":"https://api.github.com/repos/amb26/infusion-docs/releases{/id}","created_at":"2014-08-06T22:13:06Z","updated_at":"2014-06-29T09:31:28Z","pushed_at":"2015-10-18T03:05:05Z","git_url":"git://github.com/amb26/infusion-docs.git","ssh_url":"git@github.com:amb26/infusion-docs.git","clone_url":"https://github.com/amb26/infusion-docs.git","svn_url":"https://github.com/amb26/infusion-docs","homepage":null,"size":4000,"stargazers_count":0,"watchers_count":0,"language":null,"has_issues":false,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":0,"forks":0,"open_issues":0,"watchers":0,"default_branch":"master"}},"base":{"label":"fluid-project:master","ref":"master","sha":"70127a172d812ad1f7721642e45196eedc77f6d8","user":{"login":"fluid-project","id":560119,"avatar_url":"https://avatars.githubusercontent.com/u/560119?v=3","gravatar_id":"","url":"https://api.github.com/users/fluid-project","html_url":"https://github.com/fluid-project","followers_url":"https://api.github.com/users/fluid-project/followers","following_url":"https://api.github.com/users/fluid-project/following{/other_user}","gists_url":"https://api.github.com/users/fluid-project/gists{/gist_id}","starred_url":"https://api.github.com/users/fluid-project/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/fluid-project/subscriptions","organizations_url":"https://api.github.com/users/fluid-project/orgs","repos_url":"https://api.github.com/users/fluid-project/repos","events_url":"https://api.github.com/users/fluid-project/events{/privacy}","received_events_url":"https://api.github.com/users/fluid-project/received_events","type":"Organization","site_admin":false},"repo":{"id":18303292,"name":"infusion-docs","full_name":"fluid-project/infusion-docs","owner":{"login":"fluid-project","id":560119,"avatar_url":"https://avatars.githubusercontent.com/u/560119?v=3","gravatar_id":"","url":"https://api.github.com/users/fluid-project","html_url":"https://github.com/fluid-project","followers_url":"https://api.github.com/users/fluid-project/followers","following_url":"https://api.github.com/users/fluid-project/following{/other_user}","gists_url":"https://api.github.com/users/fluid-project/gists{/gist_id}","starred_url":"https://api.github.com/users/fluid-project/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/fluid-project/subscriptions","organizations_url":"https://api.github.com/users/fluid-project/orgs","repos_url":"https://api.github.com/users/fluid-project/repos","events_url":"https://api.github.com/users/fluid-project/events{/privacy}","received_events_url":"https://api.github.com/users/fluid-project/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/fluid-project/infusion-docs","description":"Documentation space for Infusion","fork":false,"url":"https://api.github.com/repos/fluid-project/infusion-docs","forks_url":"https://api.github.com/repos/fluid-project/infusion-docs/forks","keys_url":"https://api.github.com/repos/fluid-project/infusion-docs/keys{/key_id}","collaborators_url":"https://api.github.com/repos/fluid-project/infusion-docs/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/fluid-project/infusion-docs/teams","hooks_url":"https://api.github.com/repos/fluid-project/infusion-docs/hooks","issue_events_url":"https://api.github.com/repos/fluid-project/infusion-docs/issues/events{/number}","events_url":"https://api.github.com/repos/fluid-project/infusion-docs/events","assignees_url":"https://api.github.com/repos/fluid-project/infusion-docs/assignees{/user}","branches_url":"https://api.github.com/repos/fluid-project/infusion-docs/branches{/branch}","tags_url":"https://api.github.com/repos/fluid-project/infusion-docs/tags","blobs_url":"https://api.github.com/repos/fluid-project/infusion-docs/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/fluid-project/infusion-docs/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/fluid-project/infusion-docs/git/refs{/sha}","trees_url":"https://api.github.com/repos/fluid-project/infusion-docs/git/trees{/sha}","statuses_url":"https://api.github.com/repos/fluid-project/infusion-docs/statuses/{sha}","languages_url":"https://api.github.com/repos/fluid-project/infusion-docs/languages","stargazers_url":"https://api.github.com/repos/fluid-project/infusion-docs/stargazers","contributors_url":"https://api.github.com/repos/fluid-project/infusion-docs/contributors","subscribers_url":"https://api.github.com/repos/fluid-project/infusion-docs/subscribers","subscription_url":"https://api.github.com/repos/fluid-project/infusion-docs/subscription","commits_url":"https://api.github.com/repos/fluid-project/infusion-docs/commits{/sha}","git_commits_url":"https://api.github.com/repos/fluid-project/infusion-docs/git/commits{/sha}","comments_url":"https://api.github.com/repos/fluid-project/infusion-docs/comments{/number}","issue_comment_url":"https://api.github.com/repos/fluid-project/infusion-docs/issues/comments{/number}","contents_url":"https://api.github.com/repos/fluid-project/infusion-docs/contents/{+path}","compare_url":"https://api.github.com/repos/fluid-project/infusion-docs/compare/{base}...{head}","merges_url":"https://api.github.com/repos/fluid-project/infusion-docs/merges","archive_url":"https://api.github.com/repos/fluid-project/infusion-docs/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/fluid-project/infusion-docs/downloads","issues_url":"https://api.github.com/repos/fluid-project/infusion-docs/issues{/number}","pulls_url":"https://api.github.com/repos/fluid-project/infusion-docs/pulls{/number}","milestones_url":"https://api.github.com/repos/fluid-project/infusion-docs/milestones{/number}","notifications_url":"https://api.github.com/repos/fluid-project/infusion-docs/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/fluid-project/infusion-docs/labels{/name}","releases_url":"https://api.github.com/repos/fluid-project/infusion-docs/releases{/id}","created_at":"2014-03-31T18:22:31Z","updated_at":"2015-04-30T15:50:58Z","pushed_at":"2015-10-18T03:05:06Z","git_url":"git://github.com/fluid-project/infusion-docs.git","ssh_url":"git@github.com:fluid-project/infusion-docs.git","clone_url":"https://github.com/fluid-project/infusion-docs.git","svn_url":"https://github.com/fluid-project/infusion-docs","homepage":null,"size":5224,"stargazers_count":1,"watchers_count":1,"language":"JavaScript","has_issues":true,"has_downloads":true,"has_wiki":true,"has_pages":true,"forks_count":15,"mirror_url":null,"open_issues_count":4,"forks":15,"open_issues":4,"watchers":1,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/fluid-project/infusion-docs/pulls/77"},"html":{"href":"https://github.com/fluid-project/infusion-docs/pull/77"},"issue":{"href":"https://api.github.com/repos/fluid-project/infusion-docs/issues/77"},"comments":{"href":"https://api.github.com/repos/fluid-project/infusion-docs/issues/77/comments"},"review_comments":{"href":"https://api.github.com/repos/fluid-project/infusion-docs/pulls/77/comments"},"review_comment":{"href":"https://api.github.com/repos/fluid-project/infusion-docs/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/fluid-project/infusion-docs/pulls/77/commits"},"statuses":{"href":"https://api.github.com/repos/fluid-project/infusion-docs/statuses/49d791bb36aa04b080a0e8f041ef82c7c9bcc019"}}}}