{"action":"created","comment":{"url":"https://api.github.com/repos/makenotion/alloy/pulls/comments/28186796","id":28186796,"diff_hunk":"@@ -0,0 +1,178 @@\n+import { path as sysPath, ramda as R } from \"../../vendor/npm\";\n+import BuildWatcher from \"../service/BuildWatcher\";\n+import Config from \"../config/Config\";\n+import Properties from \"../config/Properties\";\n+\n+/**\n+ * Enumeration of Alloy statuses.\n+ */\n+export enum Status {\n+  STOPPED,\n+  STARTED\n+}\n+\n+/**\n+ * Alloy API.\n+ *\n+ * @author Joel Ong (joelo@google.com)\n+ */\n+export default class Alloy {\n+  private config: Config;\n+  private cwd: string;\n+  private status: Status;\n+  private watcher: BuildWatcher;\n+\n+  /**\n+   * @param config configuration to initialize this Alloy instance with,\n+   *     accepts a Config, Object, or JSON string.\n+   * @param cwd working directory to which source paths in the initial\n+   *     configuration are relative.\n+   */\n+  constructor(config: Config|Object|string, cwd: string) {\n+    this.cwd = sysPath.normalize(cwd);\n+    this.status = Status.STOPPED;\n+    this.setConfig(config);\n+  }\n+\n+  /**\n+   * Performs a build with the current Alloy configuration.\n+   */\n+  public build(): void {\n+    // TODO(joeloyj): Implement.\n+    throw new Error(\"Not implemented.\");\n+  }\n+\n+  /**\n+   * Reconfigures this Alloy instance with the given configuration.\n+   * Alloy will be restarted if it is already running.\n+   */\n+  public reconfigure(config: Config|Object|string): void {\n+    let isRunning: boolean = this.status == Status.STARTED;\n+    // Stop Alloy if it is running.\n+    if (isRunning) {\n+      this.stop();\n+    }\n+\n+    // Reconfigure alloy.\n+    this.setConfig(config);\n+\n+    // Restart Alloy if it was previously running.\n+    if (isRunning) {\n+      this.start();\n+    }\n+  }\n+\n+  /**\n+   * Starts this Alloy instance, monitoring for file changes and triggering\n+   * automatic builds as configured.\n+   */\n+  public start(): void {\n+    if (this.watcher === undefined) {\n+      this.watcher = new BuildWatcher();\n+    }\n+    this.status = Status.STARTED;\n+    let sources: string[] = this.config.getSources();\n+    let excluded: string[] = this.config.getExcluded();\n+    // Watch source paths.\n+    if (sources.length > 0) {\n+      this.watcher.watch(sources, this.cwd);\n+    }\n+    // Unwatch excluded paths.\n+    if (excluded.length > 0) {\n+      this.watcher.unwatch(excluded, this.cwd);\n+    }\n+    // Exclude build output directory from watched sources.\n+    if (this.config.isConfigured(Properties.BUILD_DIRECTORY)) {\n+      let out =\n+          sysPath.normalize(this.config.getString(Properties.BUILD_DIRECTORY));\n+      this.watcher.unwatch([out + \"/**/*\"], this.cwd);\n+    }\n+  }\n+\n+  /**\n+   * Stops this Alloy instance. Files will no longer be monitored for\n+   * automatic building.\n+   */\n+  public stop(): void {\n+    if (this.watcher) {\n+      this.watcher.exit();\n+      this.watcher = undefined;\n+    }\n+    this.status = Status.STOPPED;\n+  }\n+\n+  /**\n+   * Adds the given paths to the list of sources monitored by this\n+   * Alloy instance.\n+   */\n+  public addSources(paths: string[], cwd?: string): void {\n+    // TODO(joeloyj): Reconcile logic here with BuildWatcher and Config.\n+    // Normalize working directory if provided.\n+    if (cwd !== undefined) {\n+      cwd = sysPath.normalize(cwd);\n+    }\n+    for (let p of paths) {\n+      // Resolve path if the specified working directory is different from the\n+      // one initially provided for this Alloy instance.\n+      if (cwd !== undefined && cwd !== this.cwd) {\n+        p = sysPath.resolve(cwd, p);\n+      }\n+      // Add path to config if it doesn't already exist.\n+      this.config.add(Properties.SOURCES, p);\n+    }\n+    // Watch new paths.\n+    this.watcher.watch(paths, cwd);\n+  }\n+\n+  /**\n+   * Excludes the given paths from the list of sources monitored by this\n+   * Alloy instance. Paths must either be fully specified, or a working\n+   * directory must be provided. Accepts anymatch-compatible paths.\n+   * @see https://github.com/es128/anymatch\n+   */\n+  public exclude(paths: string[], cwd?: string): void {\n+    // TODO(joeloyj): Reconcile logic here with BuildWatcher and Config.\n+    // Normalize working directory if provided.\n+    if (cwd !== undefined) {\n+      cwd = sysPath.normalize(cwd);\n+    }\n+    for (let p of paths) {\n+      // Resolve path if a working directory was specified.\n+      if (cwd !== undefined) {\n+        p = sysPath.resolve(cwd, p);\n+      }\n+      // Add excluded path to config if it doesn't already exist.\n+      this.config.add(Properties.EXCLUDE, p);\n+    }\n+    // Unwatch new paths.\n+    this.watcher.unwatch(paths, cwd);\n+  }\n+\n+  /**\n+   * Returns the configuration of this Alloy instance.\n+   */\n+  public getConfig(): Object {\n+    return this.config.getConfig();\n+  }\n+\n+  /**\n+   * Returns the status of this Alloy instance.\n+   */\n+  public getStatus(): Status {\n+    return this.status;\n+  }\n+\n+  /**\n+   * Sets the configuration of this Alloy instance.\n+   *\n+   * @param config configuration to initialize this Alloy instance with,\n+   *     accepts a Config, Object, or JSON string.\n+   */\n+  private setConfig(config: string|Config|Object) {\n+    if (config instanceof Config) {","path":"source/api/Alloy.ts","position":172,"original_position":172,"commit_id":"91302bd3b8f297f3f761ee398d936cf1fed51b58","original_commit_id":"91302bd3b8f297f3f761ee398d936cf1fed51b58","user":{"login":"icetraxx","id":4329071,"avatar_url":"https://avatars.githubusercontent.com/u/4329071?v=3","gravatar_id":"","url":"https://api.github.com/users/icetraxx","html_url":"https://github.com/icetraxx","followers_url":"https://api.github.com/users/icetraxx/followers","following_url":"https://api.github.com/users/icetraxx/following{/other_user}","gists_url":"https://api.github.com/users/icetraxx/gists{/gist_id}","starred_url":"https://api.github.com/users/icetraxx/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/icetraxx/subscriptions","organizations_url":"https://api.github.com/users/icetraxx/orgs","repos_url":"https://api.github.com/users/icetraxx/repos","events_url":"https://api.github.com/users/icetraxx/events{/privacy}","received_events_url":"https://api.github.com/users/icetraxx/received_events","type":"User","site_admin":false},"body":"This is a side effect of polymorphic stuff.","created_at":"2015-04-10T22:58:44Z","updated_at":"2015-04-10T22:58:44Z","html_url":"https://github.com/makenotion/alloy/pull/29#discussion_r28186796","pull_request_url":"https://api.github.com/repos/makenotion/alloy/pulls/29","_links":{"self":{"href":"https://api.github.com/repos/makenotion/alloy/pulls/comments/28186796"},"html":{"href":"https://github.com/makenotion/alloy/pull/29#discussion_r28186796"},"pull_request":{"href":"https://api.github.com/repos/makenotion/alloy/pulls/29"}}},"pull_request":{"url":"https://api.github.com/repos/makenotion/alloy/pulls/29","id":32922674,"html_url":"https://github.com/makenotion/alloy/pull/29","diff_url":"https://github.com/makenotion/alloy/pull/29.diff","patch_url":"https://github.com/makenotion/alloy/pull/29.patch","issue_url":"https://api.github.com/repos/makenotion/alloy/issues/29","number":29,"state":"open","locked":false,"title":"Initial implementation for Alloy API","user":{"login":"joeloyj","id":1968309,"avatar_url":"https://avatars.githubusercontent.com/u/1968309?v=3","gravatar_id":"","url":"https://api.github.com/users/joeloyj","html_url":"https://github.com/joeloyj","followers_url":"https://api.github.com/users/joeloyj/followers","following_url":"https://api.github.com/users/joeloyj/following{/other_user}","gists_url":"https://api.github.com/users/joeloyj/gists{/gist_id}","starred_url":"https://api.github.com/users/joeloyj/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/joeloyj/subscriptions","organizations_url":"https://api.github.com/users/joeloyj/orgs","repos_url":"https://api.github.com/users/joeloyj/repos","events_url":"https://api.github.com/users/joeloyj/events{/privacy}","received_events_url":"https://api.github.com/users/joeloyj/received_events","type":"User","site_admin":false},"body":"https://github.com/makenotion/alloy/issues/9","created_at":"2015-04-09T03:35:58Z","updated_at":"2015-04-10T22:58:44Z","closed_at":null,"merged_at":null,"merge_commit_sha":"4763f694d3ab2098c3deea8df4bb165bd3d444cb","assignee":{"login":"icetraxx","id":4329071,"avatar_url":"https://avatars.githubusercontent.com/u/4329071?v=3","gravatar_id":"","url":"https://api.github.com/users/icetraxx","html_url":"https://github.com/icetraxx","followers_url":"https://api.github.com/users/icetraxx/followers","following_url":"https://api.github.com/users/icetraxx/following{/other_user}","gists_url":"https://api.github.com/users/icetraxx/gists{/gist_id}","starred_url":"https://api.github.com/users/icetraxx/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/icetraxx/subscriptions","organizations_url":"https://api.github.com/users/icetraxx/orgs","repos_url":"https://api.github.com/users/icetraxx/repos","events_url":"https://api.github.com/users/icetraxx/events{/privacy}","received_events_url":"https://api.github.com/users/icetraxx/received_events","type":"User","site_admin":false},"milestone":{"url":"https://api.github.com/repos/makenotion/alloy/milestones/1","html_url":"https://github.com/makenotion/alloy/milestones/Early%20Alpha%20Release%20(v0.1.0)","labels_url":"https://api.github.com/repos/makenotion/alloy/milestones/1/labels","id":1045726,"number":1,"title":"Early Alpha Release (v0.1.0)","description":"A working version of Alloy.","creator":{"login":"icetraxx","id":4329071,"avatar_url":"https://avatars.githubusercontent.com/u/4329071?v=3","gravatar_id":"","url":"https://api.github.com/users/icetraxx","html_url":"https://github.com/icetraxx","followers_url":"https://api.github.com/users/icetraxx/followers","following_url":"https://api.github.com/users/icetraxx/following{/other_user}","gists_url":"https://api.github.com/users/icetraxx/gists{/gist_id}","starred_url":"https://api.github.com/users/icetraxx/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/icetraxx/subscriptions","organizations_url":"https://api.github.com/users/icetraxx/orgs","repos_url":"https://api.github.com/users/icetraxx/repos","events_url":"https://api.github.com/users/icetraxx/events{/privacy}","received_events_url":"https://api.github.com/users/icetraxx/received_events","type":"User","site_admin":false},"open_issues":8,"closed_issues":8,"state":"open","created_at":"2015-03-30T22:22:18Z","updated_at":"2015-04-09T03:37:28Z","due_on":"2015-04-10T07:00:00Z","closed_at":null},"commits_url":"https://api.github.com/repos/makenotion/alloy/pulls/29/commits","review_comments_url":"https://api.github.com/repos/makenotion/alloy/pulls/29/comments","review_comment_url":"https://api.github.com/repos/makenotion/alloy/pulls/comments{/number}","comments_url":"https://api.github.com/repos/makenotion/alloy/issues/29/comments","statuses_url":"https://api.github.com/repos/makenotion/alloy/statuses/91302bd3b8f297f3f761ee398d936cf1fed51b58","head":{"label":"makenotion:api","ref":"api","sha":"91302bd3b8f297f3f761ee398d936cf1fed51b58","user":{"login":"makenotion","id":4792552,"avatar_url":"https://avatars.githubusercontent.com/u/4792552?v=3","gravatar_id":"","url":"https://api.github.com/users/makenotion","html_url":"https://github.com/makenotion","followers_url":"https://api.github.com/users/makenotion/followers","following_url":"https://api.github.com/users/makenotion/following{/other_user}","gists_url":"https://api.github.com/users/makenotion/gists{/gist_id}","starred_url":"https://api.github.com/users/makenotion/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/makenotion/subscriptions","organizations_url":"https://api.github.com/users/makenotion/orgs","repos_url":"https://api.github.com/users/makenotion/repos","events_url":"https://api.github.com/users/makenotion/events{/privacy}","received_events_url":"https://api.github.com/users/makenotion/received_events","type":"Organization","site_admin":false},"repo":{"id":32611512,"name":"alloy","full_name":"makenotion/alloy","owner":{"login":"makenotion","id":4792552,"avatar_url":"https://avatars.githubusercontent.com/u/4792552?v=3","gravatar_id":"","url":"https://api.github.com/users/makenotion","html_url":"https://github.com/makenotion","followers_url":"https://api.github.com/users/makenotion/followers","following_url":"https://api.github.com/users/makenotion/following{/other_user}","gists_url":"https://api.github.com/users/makenotion/gists{/gist_id}","starred_url":"https://api.github.com/users/makenotion/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/makenotion/subscriptions","organizations_url":"https://api.github.com/users/makenotion/orgs","repos_url":"https://api.github.com/users/makenotion/repos","events_url":"https://api.github.com/users/makenotion/events{/privacy}","received_events_url":"https://api.github.com/users/makenotion/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/makenotion/alloy","description":"The anti-build system for the Web and Node.","fork":false,"url":"https://api.github.com/repos/makenotion/alloy","forks_url":"https://api.github.com/repos/makenotion/alloy/forks","keys_url":"https://api.github.com/repos/makenotion/alloy/keys{/key_id}","collaborators_url":"https://api.github.com/repos/makenotion/alloy/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/makenotion/alloy/teams","hooks_url":"https://api.github.com/repos/makenotion/alloy/hooks","issue_events_url":"https://api.github.com/repos/makenotion/alloy/issues/events{/number}","events_url":"https://api.github.com/repos/makenotion/alloy/events","assignees_url":"https://api.github.com/repos/makenotion/alloy/assignees{/user}","branches_url":"https://api.github.com/repos/makenotion/alloy/branches{/branch}","tags_url":"https://api.github.com/repos/makenotion/alloy/tags","blobs_url":"https://api.github.com/repos/makenotion/alloy/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/makenotion/alloy/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/makenotion/alloy/git/refs{/sha}","trees_url":"https://api.github.com/repos/makenotion/alloy/git/trees{/sha}","statuses_url":"https://api.github.com/repos/makenotion/alloy/statuses/{sha}","languages_url":"https://api.github.com/repos/makenotion/alloy/languages","stargazers_url":"https://api.github.com/repos/makenotion/alloy/stargazers","contributors_url":"https://api.github.com/repos/makenotion/alloy/contributors","subscribers_url":"https://api.github.com/repos/makenotion/alloy/subscribers","subscription_url":"https://api.github.com/repos/makenotion/alloy/subscription","commits_url":"https://api.github.com/repos/makenotion/alloy/commits{/sha}","git_commits_url":"https://api.github.com/repos/makenotion/alloy/git/commits{/sha}","comments_url":"https://api.github.com/repos/makenotion/alloy/comments{/number}","issue_comment_url":"https://api.github.com/repos/makenotion/alloy/issues/comments{/number}","contents_url":"https://api.github.com/repos/makenotion/alloy/contents/{+path}","compare_url":"https://api.github.com/repos/makenotion/alloy/compare/{base}...{head}","merges_url":"https://api.github.com/repos/makenotion/alloy/merges","archive_url":"https://api.github.com/repos/makenotion/alloy/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/makenotion/alloy/downloads","issues_url":"https://api.github.com/repos/makenotion/alloy/issues{/number}","pulls_url":"https://api.github.com/repos/makenotion/alloy/pulls{/number}","milestones_url":"https://api.github.com/repos/makenotion/alloy/milestones{/number}","notifications_url":"https://api.github.com/repos/makenotion/alloy/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/makenotion/alloy/labels{/name}","releases_url":"https://api.github.com/repos/makenotion/alloy/releases{/id}","created_at":"2015-03-20T23:03:33Z","updated_at":"2015-04-10T16:49:33Z","pushed_at":"2015-04-10T05:54:45Z","git_url":"git://github.com/makenotion/alloy.git","ssh_url":"git@github.com:makenotion/alloy.git","clone_url":"https://github.com/makenotion/alloy.git","svn_url":"https://github.com/makenotion/alloy","homepage":"","size":383,"stargazers_count":2,"watchers_count":2,"language":"TypeScript","has_issues":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":16,"forks":0,"open_issues":16,"watchers":2,"default_branch":"develop"}},"base":{"label":"makenotion:develop","ref":"develop","sha":"771e17437a6dc217877dc3bb956a555d51fdd3a4","user":{"login":"makenotion","id":4792552,"avatar_url":"https://avatars.githubusercontent.com/u/4792552?v=3","gravatar_id":"","url":"https://api.github.com/users/makenotion","html_url":"https://github.com/makenotion","followers_url":"https://api.github.com/users/makenotion/followers","following_url":"https://api.github.com/users/makenotion/following{/other_user}","gists_url":"https://api.github.com/users/makenotion/gists{/gist_id}","starred_url":"https://api.github.com/users/makenotion/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/makenotion/subscriptions","organizations_url":"https://api.github.com/users/makenotion/orgs","repos_url":"https://api.github.com/users/makenotion/repos","events_url":"https://api.github.com/users/makenotion/events{/privacy}","received_events_url":"https://api.github.com/users/makenotion/received_events","type":"Organization","site_admin":false},"repo":{"id":32611512,"name":"alloy","full_name":"makenotion/alloy","owner":{"login":"makenotion","id":4792552,"avatar_url":"https://avatars.githubusercontent.com/u/4792552?v=3","gravatar_id":"","url":"https://api.github.com/users/makenotion","html_url":"https://github.com/makenotion","followers_url":"https://api.github.com/users/makenotion/followers","following_url":"https://api.github.com/users/makenotion/following{/other_user}","gists_url":"https://api.github.com/users/makenotion/gists{/gist_id}","starred_url":"https://api.github.com/users/makenotion/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/makenotion/subscriptions","organizations_url":"https://api.github.com/users/makenotion/orgs","repos_url":"https://api.github.com/users/makenotion/repos","events_url":"https://api.github.com/users/makenotion/events{/privacy}","received_events_url":"https://api.github.com/users/makenotion/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/makenotion/alloy","description":"The anti-build system for the Web and Node.","fork":false,"url":"https://api.github.com/repos/makenotion/alloy","forks_url":"https://api.github.com/repos/makenotion/alloy/forks","keys_url":"https://api.github.com/repos/makenotion/alloy/keys{/key_id}","collaborators_url":"https://api.github.com/repos/makenotion/alloy/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/makenotion/alloy/teams","hooks_url":"https://api.github.com/repos/makenotion/alloy/hooks","issue_events_url":"https://api.github.com/repos/makenotion/alloy/issues/events{/number}","events_url":"https://api.github.com/repos/makenotion/alloy/events","assignees_url":"https://api.github.com/repos/makenotion/alloy/assignees{/user}","branches_url":"https://api.github.com/repos/makenotion/alloy/branches{/branch}","tags_url":"https://api.github.com/repos/makenotion/alloy/tags","blobs_url":"https://api.github.com/repos/makenotion/alloy/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/makenotion/alloy/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/makenotion/alloy/git/refs{/sha}","trees_url":"https://api.github.com/repos/makenotion/alloy/git/trees{/sha}","statuses_url":"https://api.github.com/repos/makenotion/alloy/statuses/{sha}","languages_url":"https://api.github.com/repos/makenotion/alloy/languages","stargazers_url":"https://api.github.com/repos/makenotion/alloy/stargazers","contributors_url":"https://api.github.com/repos/makenotion/alloy/contributors","subscribers_url":"https://api.github.com/repos/makenotion/alloy/subscribers","subscription_url":"https://api.github.com/repos/makenotion/alloy/subscription","commits_url":"https://api.github.com/repos/makenotion/alloy/commits{/sha}","git_commits_url":"https://api.github.com/repos/makenotion/alloy/git/commits{/sha}","comments_url":"https://api.github.com/repos/makenotion/alloy/comments{/number}","issue_comment_url":"https://api.github.com/repos/makenotion/alloy/issues/comments{/number}","contents_url":"https://api.github.com/repos/makenotion/alloy/contents/{+path}","compare_url":"https://api.github.com/repos/makenotion/alloy/compare/{base}...{head}","merges_url":"https://api.github.com/repos/makenotion/alloy/merges","archive_url":"https://api.github.com/repos/makenotion/alloy/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/makenotion/alloy/downloads","issues_url":"https://api.github.com/repos/makenotion/alloy/issues{/number}","pulls_url":"https://api.github.com/repos/makenotion/alloy/pulls{/number}","milestones_url":"https://api.github.com/repos/makenotion/alloy/milestones{/number}","notifications_url":"https://api.github.com/repos/makenotion/alloy/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/makenotion/alloy/labels{/name}","releases_url":"https://api.github.com/repos/makenotion/alloy/releases{/id}","created_at":"2015-03-20T23:03:33Z","updated_at":"2015-04-10T16:49:33Z","pushed_at":"2015-04-10T05:54:45Z","git_url":"git://github.com/makenotion/alloy.git","ssh_url":"git@github.com:makenotion/alloy.git","clone_url":"https://github.com/makenotion/alloy.git","svn_url":"https://github.com/makenotion/alloy","homepage":"","size":383,"stargazers_count":2,"watchers_count":2,"language":"TypeScript","has_issues":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":0,"mirror_url":null,"open_issues_count":16,"forks":0,"open_issues":16,"watchers":2,"default_branch":"develop"}},"_links":{"self":{"href":"https://api.github.com/repos/makenotion/alloy/pulls/29"},"html":{"href":"https://github.com/makenotion/alloy/pull/29"},"issue":{"href":"https://api.github.com/repos/makenotion/alloy/issues/29"},"comments":{"href":"https://api.github.com/repos/makenotion/alloy/issues/29/comments"},"review_comments":{"href":"https://api.github.com/repos/makenotion/alloy/pulls/29/comments"},"review_comment":{"href":"https://api.github.com/repos/makenotion/alloy/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/makenotion/alloy/pulls/29/commits"},"statuses":{"href":"https://api.github.com/repos/makenotion/alloy/statuses/91302bd3b8f297f3f761ee398d936cf1fed51b58"}}}}