{"action":"created","comment":{"url":"https://api.github.com/repos/projectatomic/osbs-client/pulls/comments/63777552","id":63777552,"diff_hunk":"@@ -382,6 +382,45 @@ def wait_for_new_build_config_instance(self, build_config_id, prev_version):\n \n         raise OsbsResponseException(\"New BuildConfig instance not found\")\n \n+    def stream_logs(self, build_id):\n+        \"\"\"\n+        stream logs from build\n+\n+        :param build_id: str\n+        :return: iterator\n+        \"\"\"\n+        kwargs = {'follow': 1}\n+\n+        # If connection is closed within this many seconds, give up:\n+        min_idle_timeout = 60\n+\n+        while True:\n+            buildlogs_url = self._build_url(\"builds/%s/log/\" % build_id,\n+                                            **kwargs)\n+            response = self._get(buildlogs_url, stream=1,\n+                                 headers={'Connection': 'close'})\n+            check_response(response)\n+\n+            # Stream logs, but be careful of the connection closing\n+            # due to idle timeout. In that case, try again until the\n+            # call returns more quickly than a reasonable timeout\n+            # would be set to.\n+            last_activity = time.time()\n+\n+            for line in response.iter_lines():\n+                last_activity = time.time()\n+                yield line\n+\n+            idle = time.time() - last_activity\n+            logger.debug(\"connection closed after %ds\", idle)\n+            if idle < min_idle_timeout:\n+                # Finish output\n+                raise StopIteration\n+\n+            since = int(idle - 1)\n+            logger.debug(\"fetching logs starting from %ds ago\", since)\n+            kwargs['sinceSeconds'] = since","path":"osbs/core.py","position":41,"original_position":41,"commit_id":"e8892f7ab6a6b450a5362b07d39b680f8764e126","original_commit_id":"e8892f7ab6a6b450a5362b07d39b680f8764e126","user":{"login":"twaugh","id":6985468,"avatar_url":"https://avatars.githubusercontent.com/u/6985468?v=3","gravatar_id":"","url":"https://api.github.com/users/twaugh","html_url":"https://github.com/twaugh","followers_url":"https://api.github.com/users/twaugh/followers","following_url":"https://api.github.com/users/twaugh/following{/other_user}","gists_url":"https://api.github.com/users/twaugh/gists{/gist_id}","starred_url":"https://api.github.com/users/twaugh/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/twaugh/subscriptions","organizations_url":"https://api.github.com/users/twaugh/orgs","repos_url":"https://api.github.com/users/twaugh/repos","events_url":"https://api.github.com/users/twaugh/events{/privacy}","received_events_url":"https://api.github.com/users/twaugh/received_events","type":"User","site_admin":false},"body":"No. `sinceSeconds` indicates the number of seconds in past to start fetching logs from, i.e. it's a relative time.","created_at":"2016-05-18T20:38:35Z","updated_at":"2016-05-18T20:38:35Z","html_url":"https://github.com/projectatomic/osbs-client/pull/421#discussion_r63777552","pull_request_url":"https://api.github.com/repos/projectatomic/osbs-client/pulls/421","_links":{"self":{"href":"https://api.github.com/repos/projectatomic/osbs-client/pulls/comments/63777552"},"html":{"href":"https://github.com/projectatomic/osbs-client/pull/421#discussion_r63777552"},"pull_request":{"href":"https://api.github.com/repos/projectatomic/osbs-client/pulls/421"}}},"pull_request":{"url":"https://api.github.com/repos/projectatomic/osbs-client/pulls/421","id":70569997,"html_url":"https://github.com/projectatomic/osbs-client/pull/421","diff_url":"https://github.com/projectatomic/osbs-client/pull/421.diff","patch_url":"https://github.com/projectatomic/osbs-client/pull/421.patch","issue_url":"https://api.github.com/repos/projectatomic/osbs-client/issues/421","number":421,"state":"open","locked":false,"title":"handle connection being closed while streaming logs","user":{"login":"twaugh","id":6985468,"avatar_url":"https://avatars.githubusercontent.com/u/6985468?v=3","gravatar_id":"","url":"https://api.github.com/users/twaugh","html_url":"https://github.com/twaugh","followers_url":"https://api.github.com/users/twaugh/followers","following_url":"https://api.github.com/users/twaugh/following{/other_user}","gists_url":"https://api.github.com/users/twaugh/gists{/gist_id}","starred_url":"https://api.github.com/users/twaugh/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/twaugh/subscriptions","organizations_url":"https://api.github.com/users/twaugh/orgs","repos_url":"https://api.github.com/users/twaugh/repos","events_url":"https://api.github.com/users/twaugh/events{/privacy}","received_events_url":"https://api.github.com/users/twaugh/received_events","type":"User","site_admin":false},"body":"When the connection is closed, if the time since the last activity is less than a minute, finish.\r\n\r\nOtherwise, ask again for logs starting from just after we last saw activity.","created_at":"2016-05-18T17:42:51Z","updated_at":"2016-05-18T20:38:35Z","closed_at":null,"merged_at":null,"merge_commit_sha":"b6109a269abe8fddb8a4b6963b29172839715248","assignee":null,"milestone":null,"commits_url":"https://api.github.com/repos/projectatomic/osbs-client/pulls/421/commits","review_comments_url":"https://api.github.com/repos/projectatomic/osbs-client/pulls/421/comments","review_comment_url":"https://api.github.com/repos/projectatomic/osbs-client/pulls/comments{/number}","comments_url":"https://api.github.com/repos/projectatomic/osbs-client/issues/421/comments","statuses_url":"https://api.github.com/repos/projectatomic/osbs-client/statuses/e8892f7ab6a6b450a5362b07d39b680f8764e126","head":{"label":"projectatomic:logs-retry-on-connection-close","ref":"logs-retry-on-connection-close","sha":"e8892f7ab6a6b450a5362b07d39b680f8764e126","user":{"login":"projectatomic","id":6852258,"avatar_url":"https://avatars.githubusercontent.com/u/6852258?v=3","gravatar_id":"","url":"https://api.github.com/users/projectatomic","html_url":"https://github.com/projectatomic","followers_url":"https://api.github.com/users/projectatomic/followers","following_url":"https://api.github.com/users/projectatomic/following{/other_user}","gists_url":"https://api.github.com/users/projectatomic/gists{/gist_id}","starred_url":"https://api.github.com/users/projectatomic/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/projectatomic/subscriptions","organizations_url":"https://api.github.com/users/projectatomic/orgs","repos_url":"https://api.github.com/users/projectatomic/repos","events_url":"https://api.github.com/users/projectatomic/events{/privacy}","received_events_url":"https://api.github.com/users/projectatomic/received_events","type":"Organization","site_admin":false},"repo":{"id":31409916,"name":"osbs-client","full_name":"projectatomic/osbs-client","owner":{"login":"projectatomic","id":6852258,"avatar_url":"https://avatars.githubusercontent.com/u/6852258?v=3","gravatar_id":"","url":"https://api.github.com/users/projectatomic","html_url":"https://github.com/projectatomic","followers_url":"https://api.github.com/users/projectatomic/followers","following_url":"https://api.github.com/users/projectatomic/following{/other_user}","gists_url":"https://api.github.com/users/projectatomic/gists{/gist_id}","starred_url":"https://api.github.com/users/projectatomic/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/projectatomic/subscriptions","organizations_url":"https://api.github.com/users/projectatomic/orgs","repos_url":"https://api.github.com/users/projectatomic/repos","events_url":"https://api.github.com/users/projectatomic/events{/privacy}","received_events_url":"https://api.github.com/users/projectatomic/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/projectatomic/osbs-client","description":"client for OpenShift Build Service","fork":false,"url":"https://api.github.com/repos/projectatomic/osbs-client","forks_url":"https://api.github.com/repos/projectatomic/osbs-client/forks","keys_url":"https://api.github.com/repos/projectatomic/osbs-client/keys{/key_id}","collaborators_url":"https://api.github.com/repos/projectatomic/osbs-client/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/projectatomic/osbs-client/teams","hooks_url":"https://api.github.com/repos/projectatomic/osbs-client/hooks","issue_events_url":"https://api.github.com/repos/projectatomic/osbs-client/issues/events{/number}","events_url":"https://api.github.com/repos/projectatomic/osbs-client/events","assignees_url":"https://api.github.com/repos/projectatomic/osbs-client/assignees{/user}","branches_url":"https://api.github.com/repos/projectatomic/osbs-client/branches{/branch}","tags_url":"https://api.github.com/repos/projectatomic/osbs-client/tags","blobs_url":"https://api.github.com/repos/projectatomic/osbs-client/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/projectatomic/osbs-client/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/projectatomic/osbs-client/git/refs{/sha}","trees_url":"https://api.github.com/repos/projectatomic/osbs-client/git/trees{/sha}","statuses_url":"https://api.github.com/repos/projectatomic/osbs-client/statuses/{sha}","languages_url":"https://api.github.com/repos/projectatomic/osbs-client/languages","stargazers_url":"https://api.github.com/repos/projectatomic/osbs-client/stargazers","contributors_url":"https://api.github.com/repos/projectatomic/osbs-client/contributors","subscribers_url":"https://api.github.com/repos/projectatomic/osbs-client/subscribers","subscription_url":"https://api.github.com/repos/projectatomic/osbs-client/subscription","commits_url":"https://api.github.com/repos/projectatomic/osbs-client/commits{/sha}","git_commits_url":"https://api.github.com/repos/projectatomic/osbs-client/git/commits{/sha}","comments_url":"https://api.github.com/repos/projectatomic/osbs-client/comments{/number}","issue_comment_url":"https://api.github.com/repos/projectatomic/osbs-client/issues/comments{/number}","contents_url":"https://api.github.com/repos/projectatomic/osbs-client/contents/{+path}","compare_url":"https://api.github.com/repos/projectatomic/osbs-client/compare/{base}...{head}","merges_url":"https://api.github.com/repos/projectatomic/osbs-client/merges","archive_url":"https://api.github.com/repos/projectatomic/osbs-client/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/projectatomic/osbs-client/downloads","issues_url":"https://api.github.com/repos/projectatomic/osbs-client/issues{/number}","pulls_url":"https://api.github.com/repos/projectatomic/osbs-client/pulls{/number}","milestones_url":"https://api.github.com/repos/projectatomic/osbs-client/milestones{/number}","notifications_url":"https://api.github.com/repos/projectatomic/osbs-client/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/projectatomic/osbs-client/labels{/name}","releases_url":"https://api.github.com/repos/projectatomic/osbs-client/releases{/id}","deployments_url":"https://api.github.com/repos/projectatomic/osbs-client/deployments","created_at":"2015-02-27T08:20:07Z","updated_at":"2016-04-19T08:44:26Z","pushed_at":"2016-05-18T17:42:52Z","git_url":"git://github.com/projectatomic/osbs-client.git","ssh_url":"git@github.com:projectatomic/osbs-client.git","clone_url":"https://github.com/projectatomic/osbs-client.git","svn_url":"https://github.com/projectatomic/osbs-client","homepage":null,"size":1206,"stargazers_count":11,"watchers_count":11,"language":"Python","has_issues":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":15,"mirror_url":null,"open_issues_count":43,"forks":15,"open_issues":43,"watchers":11,"default_branch":"master"}},"base":{"label":"projectatomic:master","ref":"master","sha":"b4f5afb16685860a4a90fc7cf6ec00010350cb05","user":{"login":"projectatomic","id":6852258,"avatar_url":"https://avatars.githubusercontent.com/u/6852258?v=3","gravatar_id":"","url":"https://api.github.com/users/projectatomic","html_url":"https://github.com/projectatomic","followers_url":"https://api.github.com/users/projectatomic/followers","following_url":"https://api.github.com/users/projectatomic/following{/other_user}","gists_url":"https://api.github.com/users/projectatomic/gists{/gist_id}","starred_url":"https://api.github.com/users/projectatomic/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/projectatomic/subscriptions","organizations_url":"https://api.github.com/users/projectatomic/orgs","repos_url":"https://api.github.com/users/projectatomic/repos","events_url":"https://api.github.com/users/projectatomic/events{/privacy}","received_events_url":"https://api.github.com/users/projectatomic/received_events","type":"Organization","site_admin":false},"repo":{"id":31409916,"name":"osbs-client","full_name":"projectatomic/osbs-client","owner":{"login":"projectatomic","id":6852258,"avatar_url":"https://avatars.githubusercontent.com/u/6852258?v=3","gravatar_id":"","url":"https://api.github.com/users/projectatomic","html_url":"https://github.com/projectatomic","followers_url":"https://api.github.com/users/projectatomic/followers","following_url":"https://api.github.com/users/projectatomic/following{/other_user}","gists_url":"https://api.github.com/users/projectatomic/gists{/gist_id}","starred_url":"https://api.github.com/users/projectatomic/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/projectatomic/subscriptions","organizations_url":"https://api.github.com/users/projectatomic/orgs","repos_url":"https://api.github.com/users/projectatomic/repos","events_url":"https://api.github.com/users/projectatomic/events{/privacy}","received_events_url":"https://api.github.com/users/projectatomic/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/projectatomic/osbs-client","description":"client for OpenShift Build Service","fork":false,"url":"https://api.github.com/repos/projectatomic/osbs-client","forks_url":"https://api.github.com/repos/projectatomic/osbs-client/forks","keys_url":"https://api.github.com/repos/projectatomic/osbs-client/keys{/key_id}","collaborators_url":"https://api.github.com/repos/projectatomic/osbs-client/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/projectatomic/osbs-client/teams","hooks_url":"https://api.github.com/repos/projectatomic/osbs-client/hooks","issue_events_url":"https://api.github.com/repos/projectatomic/osbs-client/issues/events{/number}","events_url":"https://api.github.com/repos/projectatomic/osbs-client/events","assignees_url":"https://api.github.com/repos/projectatomic/osbs-client/assignees{/user}","branches_url":"https://api.github.com/repos/projectatomic/osbs-client/branches{/branch}","tags_url":"https://api.github.com/repos/projectatomic/osbs-client/tags","blobs_url":"https://api.github.com/repos/projectatomic/osbs-client/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/projectatomic/osbs-client/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/projectatomic/osbs-client/git/refs{/sha}","trees_url":"https://api.github.com/repos/projectatomic/osbs-client/git/trees{/sha}","statuses_url":"https://api.github.com/repos/projectatomic/osbs-client/statuses/{sha}","languages_url":"https://api.github.com/repos/projectatomic/osbs-client/languages","stargazers_url":"https://api.github.com/repos/projectatomic/osbs-client/stargazers","contributors_url":"https://api.github.com/repos/projectatomic/osbs-client/contributors","subscribers_url":"https://api.github.com/repos/projectatomic/osbs-client/subscribers","subscription_url":"https://api.github.com/repos/projectatomic/osbs-client/subscription","commits_url":"https://api.github.com/repos/projectatomic/osbs-client/commits{/sha}","git_commits_url":"https://api.github.com/repos/projectatomic/osbs-client/git/commits{/sha}","comments_url":"https://api.github.com/repos/projectatomic/osbs-client/comments{/number}","issue_comment_url":"https://api.github.com/repos/projectatomic/osbs-client/issues/comments{/number}","contents_url":"https://api.github.com/repos/projectatomic/osbs-client/contents/{+path}","compare_url":"https://api.github.com/repos/projectatomic/osbs-client/compare/{base}...{head}","merges_url":"https://api.github.com/repos/projectatomic/osbs-client/merges","archive_url":"https://api.github.com/repos/projectatomic/osbs-client/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/projectatomic/osbs-client/downloads","issues_url":"https://api.github.com/repos/projectatomic/osbs-client/issues{/number}","pulls_url":"https://api.github.com/repos/projectatomic/osbs-client/pulls{/number}","milestones_url":"https://api.github.com/repos/projectatomic/osbs-client/milestones{/number}","notifications_url":"https://api.github.com/repos/projectatomic/osbs-client/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/projectatomic/osbs-client/labels{/name}","releases_url":"https://api.github.com/repos/projectatomic/osbs-client/releases{/id}","deployments_url":"https://api.github.com/repos/projectatomic/osbs-client/deployments","created_at":"2015-02-27T08:20:07Z","updated_at":"2016-04-19T08:44:26Z","pushed_at":"2016-05-18T17:42:52Z","git_url":"git://github.com/projectatomic/osbs-client.git","ssh_url":"git@github.com:projectatomic/osbs-client.git","clone_url":"https://github.com/projectatomic/osbs-client.git","svn_url":"https://github.com/projectatomic/osbs-client","homepage":null,"size":1206,"stargazers_count":11,"watchers_count":11,"language":"Python","has_issues":true,"has_downloads":true,"has_wiki":true,"has_pages":false,"forks_count":15,"mirror_url":null,"open_issues_count":43,"forks":15,"open_issues":43,"watchers":11,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/projectatomic/osbs-client/pulls/421"},"html":{"href":"https://github.com/projectatomic/osbs-client/pull/421"},"issue":{"href":"https://api.github.com/repos/projectatomic/osbs-client/issues/421"},"comments":{"href":"https://api.github.com/repos/projectatomic/osbs-client/issues/421/comments"},"review_comments":{"href":"https://api.github.com/repos/projectatomic/osbs-client/pulls/421/comments"},"review_comment":{"href":"https://api.github.com/repos/projectatomic/osbs-client/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/projectatomic/osbs-client/pulls/421/commits"},"statuses":{"href":"https://api.github.com/repos/projectatomic/osbs-client/statuses/e8892f7ab6a6b450a5362b07d39b680f8764e126"}}}}