{"action":"created","comment":{"url":"https://api.github.com/repos/kubernetes/kubernetes/pulls/comments/84922232","pull_request_review_id":5668733,"id":84922232,"diff_hunk":"@@ -0,0 +1,229 @@\n+/*\n+Copyright 2016 The Kubernetes Authors.\n+\n+Licensed under the Apache License, Version 2.0 (the \"License\");\n+you may not use this file except in compliance with the License.\n+You may obtain a copy of the License at\n+\n+    http://www.apache.org/licenses/LICENSE-2.0\n+\n+Unless required by applicable law or agreed to in writing, software\n+distributed under the License is distributed on an \"AS IS\" BASIS,\n+WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n+See the License for the specific language governing permissions and\n+limitations under the License.\n+*/\n+\n+package version\n+\n+import (\n+\t\"bytes\"\n+\t\"fmt\"\n+\t\"regexp\"\n+\t\"strconv\"\n+\t\"strings\"\n+)\n+\n+// Version is an opqaue representation of a version number\n+type Version struct {\n+\tcomponents    []uint\n+\tsemver        bool\n+\tpreRelease    string\n+\tbuildMetadata string\n+}\n+\n+var (\n+\t// versionMatchRE splits a version string into numeric and \"extra\" parts\n+\tversionMatchRE = regexp.MustCompile(`^\\s*v?([0-9]+(?:\\.[0-9]+)*)(.*)*$`)\n+\t// extraMatchRE splits the \"extra\" part of versionMatchRE into semver pre-release and build metadata; it does not validate the \"no leading zeroes\" constraint for pre-release\n+\textraMatchRE = regexp.MustCompile(`^(?:-([0-9A-Za-z-]+(?:\\.[0-9A-Za-z-]+)*))?(?:\\+([0-9A-Za-z-]+(?:\\.[0-9A-Za-z-]+)*))?\\s*$`)\n+)\n+\n+func parse(str string, semver bool) (*Version, error) {\n+\tparts := versionMatchRE.FindStringSubmatch(str)\n+\tif parts == nil {\n+\t\treturn nil, fmt.Errorf(\"could not parse %q as version\", str)\n+\t}\n+\tnumbers, extra := parts[1], parts[2]\n+\n+\tcomponents := strings.Split(numbers, \".\")\n+\tif (semver && len(components) != 3) || (!semver && len(components) < 2) {","path":"pkg/util/version/version.go","position":50,"original_position":50,"commit_id":"c2a231372d114475b38386bea797acb44bce6ea4","original_commit_id":"c2a231372d114475b38386bea797acb44bce6ea4","user":{"login":"thockin","id":5595220,"avatar_url":"https://avatars.githubusercontent.com/u/5595220?v=3","gravatar_id":"","url":"https://api.github.com/users/thockin","html_url":"https://github.com/thockin","followers_url":"https://api.github.com/users/thockin/followers","following_url":"https://api.github.com/users/thockin/following{/other_user}","gists_url":"https://api.github.com/users/thockin/gists{/gist_id}","starred_url":"https://api.github.com/users/thockin/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/thockin/subscriptions","organizations_url":"https://api.github.com/users/thockin/orgs","repos_url":"https://api.github.com/users/thockin/repos","events_url":"https://api.github.com/users/thockin/events{/privacy}","received_events_url":"https://api.github.com/users/thockin/received_events","type":"User","site_admin":false},"body":"Our API versions don't fit the assumptions here anyway - v1beta1 is not semver compatibles in any way.  Not important","created_at":"2016-10-25T14:56:23Z","updated_at":"2016-10-25T14:56:23Z","html_url":"https://github.com/kubernetes/kubernetes/pull/35436#discussion_r84922232","pull_request_url":"https://api.github.com/repos/kubernetes/kubernetes/pulls/35436","_links":{"self":{"href":"https://api.github.com/repos/kubernetes/kubernetes/pulls/comments/84922232"},"html":{"href":"https://github.com/kubernetes/kubernetes/pull/35436#discussion_r84922232"},"pull_request":{"href":"https://api.github.com/repos/kubernetes/kubernetes/pulls/35436"}}},"pull_request":{"url":"https://api.github.com/repos/kubernetes/kubernetes/pulls/35436","id":90630727,"html_url":"https://github.com/kubernetes/kubernetes/pull/35436","diff_url":"https://github.com/kubernetes/kubernetes/pull/35436.diff","patch_url":"https://github.com/kubernetes/kubernetes/pull/35436.patch","issue_url":"https://api.github.com/repos/kubernetes/kubernetes/issues/35436","number":35436,"state":"open","locked":false,"title":"Add a package for handling version numbers (including non-\"Semantic\" versions)","user":{"login":"danwinship","id":96040,"avatar_url":"https://avatars.githubusercontent.com/u/96040?v=3","gravatar_id":"","url":"https://api.github.com/users/danwinship","html_url":"https://github.com/danwinship","followers_url":"https://api.github.com/users/danwinship/followers","following_url":"https://api.github.com/users/danwinship/following{/other_user}","gists_url":"https://api.github.com/users/danwinship/gists{/gist_id}","starred_url":"https://api.github.com/users/danwinship/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/danwinship/subscriptions","organizations_url":"https://api.github.com/users/danwinship/orgs","repos_url":"https://api.github.com/users/danwinship/repos","events_url":"https://api.github.com/users/danwinship/events{/privacy}","received_events_url":"https://api.github.com/users/danwinship/received_events","type":"User","site_admin":false},"body":"As noted in #32401, we are using Semantic Version-parsing libraries to parse version numbers that aren't necessarily \"Semantic\". Although, contrary to what I'd said there, it turns out that this wasn't actually currently a problem for the iptables code, because the regexp used to extract the version number out of the \"iptables --version\" output only pulled out three components, so given \"iptables v1.4.19.1\", it would have extracted just \"1.4.19\". Still, it could be a problem if they later release \"1.5\" rather than \"1.5.0\", or if we eventually need to *compare* against a 4-digit version number.\r\n\r\nAlso, as noted in #23854, we were also using two different semver libraries in different parts of the code (plus a wrapper around one of them in pkg/version).\r\n\r\nThis PR adds pkg/util/version, with code to parse and compare both semver and non-semver version strings, and then updates kubernetes to use it everywhere (including getting rid of a bunch of code duplication in kubelet by making utilversion.Version implement the kubecontainer.Version interface directly).\r\n\r\nIronically, this does not actually allow us to get rid of either of the vendored semver libraries, because we still have other dependencies that depend on each of them. (cadvisor uses blang/semver and etcd uses coreos/go-semver)\r\n\r\nfixes #32401, #23854\n\n<!-- Reviewable:start -->\n---\nThis change is [<img src=\"https://reviewable.kubernetes.io/review_button.svg\" height=\"34\" align=\"absmiddle\" alt=\"Reviewable\"/>](https://reviewable.kubernetes.io/reviews/kubernetes/kubernetes/35436)\n<!-- Reviewable:end -->\n","created_at":"2016-10-24T15:03:53Z","updated_at":"2016-10-25T14:56:23Z","closed_at":null,"merged_at":null,"merge_commit_sha":"91927a1a8d787adafa75d670fbcaee84651faf4a","assignee":{"login":"thockin","id":5595220,"avatar_url":"https://avatars.githubusercontent.com/u/5595220?v=3","gravatar_id":"","url":"https://api.github.com/users/thockin","html_url":"https://github.com/thockin","followers_url":"https://api.github.com/users/thockin/followers","following_url":"https://api.github.com/users/thockin/following{/other_user}","gists_url":"https://api.github.com/users/thockin/gists{/gist_id}","starred_url":"https://api.github.com/users/thockin/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/thockin/subscriptions","organizations_url":"https://api.github.com/users/thockin/orgs","repos_url":"https://api.github.com/users/thockin/repos","events_url":"https://api.github.com/users/thockin/events{/privacy}","received_events_url":"https://api.github.com/users/thockin/received_events","type":"User","site_admin":false},"assignees":[{"login":"thockin","id":5595220,"avatar_url":"https://avatars.githubusercontent.com/u/5595220?v=3","gravatar_id":"","url":"https://api.github.com/users/thockin","html_url":"https://github.com/thockin","followers_url":"https://api.github.com/users/thockin/followers","following_url":"https://api.github.com/users/thockin/following{/other_user}","gists_url":"https://api.github.com/users/thockin/gists{/gist_id}","starred_url":"https://api.github.com/users/thockin/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/thockin/subscriptions","organizations_url":"https://api.github.com/users/thockin/orgs","repos_url":"https://api.github.com/users/thockin/repos","events_url":"https://api.github.com/users/thockin/events{/privacy}","received_events_url":"https://api.github.com/users/thockin/received_events","type":"User","site_admin":false}],"milestone":null,"commits_url":"https://api.github.com/repos/kubernetes/kubernetes/pulls/35436/commits","review_comments_url":"https://api.github.com/repos/kubernetes/kubernetes/pulls/35436/comments","review_comment_url":"https://api.github.com/repos/kubernetes/kubernetes/pulls/comments{/number}","comments_url":"https://api.github.com/repos/kubernetes/kubernetes/issues/35436/comments","statuses_url":"https://api.github.com/repos/kubernetes/kubernetes/statuses/c2a231372d114475b38386bea797acb44bce6ea4","head":{"label":"danwinship:utilversion","ref":"utilversion","sha":"c2a231372d114475b38386bea797acb44bce6ea4","user":{"login":"danwinship","id":96040,"avatar_url":"https://avatars.githubusercontent.com/u/96040?v=3","gravatar_id":"","url":"https://api.github.com/users/danwinship","html_url":"https://github.com/danwinship","followers_url":"https://api.github.com/users/danwinship/followers","following_url":"https://api.github.com/users/danwinship/following{/other_user}","gists_url":"https://api.github.com/users/danwinship/gists{/gist_id}","starred_url":"https://api.github.com/users/danwinship/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/danwinship/subscriptions","organizations_url":"https://api.github.com/users/danwinship/orgs","repos_url":"https://api.github.com/users/danwinship/repos","events_url":"https://api.github.com/users/danwinship/events{/privacy}","received_events_url":"https://api.github.com/users/danwinship/received_events","type":"User","site_admin":false},"repo":{"id":40127975,"name":"kubernetes","full_name":"danwinship/kubernetes","owner":{"login":"danwinship","id":96040,"avatar_url":"https://avatars.githubusercontent.com/u/96040?v=3","gravatar_id":"","url":"https://api.github.com/users/danwinship","html_url":"https://github.com/danwinship","followers_url":"https://api.github.com/users/danwinship/followers","following_url":"https://api.github.com/users/danwinship/following{/other_user}","gists_url":"https://api.github.com/users/danwinship/gists{/gist_id}","starred_url":"https://api.github.com/users/danwinship/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/danwinship/subscriptions","organizations_url":"https://api.github.com/users/danwinship/orgs","repos_url":"https://api.github.com/users/danwinship/repos","events_url":"https://api.github.com/users/danwinship/events{/privacy}","received_events_url":"https://api.github.com/users/danwinship/received_events","type":"User","site_admin":false},"private":false,"html_url":"https://github.com/danwinship/kubernetes","description":"Container Cluster Manager from Google","fork":true,"url":"https://api.github.com/repos/danwinship/kubernetes","forks_url":"https://api.github.com/repos/danwinship/kubernetes/forks","keys_url":"https://api.github.com/repos/danwinship/kubernetes/keys{/key_id}","collaborators_url":"https://api.github.com/repos/danwinship/kubernetes/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/danwinship/kubernetes/teams","hooks_url":"https://api.github.com/repos/danwinship/kubernetes/hooks","issue_events_url":"https://api.github.com/repos/danwinship/kubernetes/issues/events{/number}","events_url":"https://api.github.com/repos/danwinship/kubernetes/events","assignees_url":"https://api.github.com/repos/danwinship/kubernetes/assignees{/user}","branches_url":"https://api.github.com/repos/danwinship/kubernetes/branches{/branch}","tags_url":"https://api.github.com/repos/danwinship/kubernetes/tags","blobs_url":"https://api.github.com/repos/danwinship/kubernetes/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/danwinship/kubernetes/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/danwinship/kubernetes/git/refs{/sha}","trees_url":"https://api.github.com/repos/danwinship/kubernetes/git/trees{/sha}","statuses_url":"https://api.github.com/repos/danwinship/kubernetes/statuses/{sha}","languages_url":"https://api.github.com/repos/danwinship/kubernetes/languages","stargazers_url":"https://api.github.com/repos/danwinship/kubernetes/stargazers","contributors_url":"https://api.github.com/repos/danwinship/kubernetes/contributors","subscribers_url":"https://api.github.com/repos/danwinship/kubernetes/subscribers","subscription_url":"https://api.github.com/repos/danwinship/kubernetes/subscription","commits_url":"https://api.github.com/repos/danwinship/kubernetes/commits{/sha}","git_commits_url":"https://api.github.com/repos/danwinship/kubernetes/git/commits{/sha}","comments_url":"https://api.github.com/repos/danwinship/kubernetes/comments{/number}","issue_comment_url":"https://api.github.com/repos/danwinship/kubernetes/issues/comments{/number}","contents_url":"https://api.github.com/repos/danwinship/kubernetes/contents/{+path}","compare_url":"https://api.github.com/repos/danwinship/kubernetes/compare/{base}...{head}","merges_url":"https://api.github.com/repos/danwinship/kubernetes/merges","archive_url":"https://api.github.com/repos/danwinship/kubernetes/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/danwinship/kubernetes/downloads","issues_url":"https://api.github.com/repos/danwinship/kubernetes/issues{/number}","pulls_url":"https://api.github.com/repos/danwinship/kubernetes/pulls{/number}","milestones_url":"https://api.github.com/repos/danwinship/kubernetes/milestones{/number}","notifications_url":"https://api.github.com/repos/danwinship/kubernetes/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/danwinship/kubernetes/labels{/name}","releases_url":"https://api.github.com/repos/danwinship/kubernetes/releases{/id}","deployments_url":"https://api.github.com/repos/danwinship/kubernetes/deployments","created_at":"2015-08-03T14:04:18Z","updated_at":"2016-01-25T14:02:40Z","pushed_at":"2016-10-24T15:58:16Z","git_url":"git://github.com/danwinship/kubernetes.git","ssh_url":"git@github.com:danwinship/kubernetes.git","clone_url":"https://github.com/danwinship/kubernetes.git","svn_url":"https://github.com/danwinship/kubernetes","homepage":"http://kubernetes.io","size":331450,"stargazers_count":0,"watchers_count":0,"language":"Go","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":"kubernetes:master","ref":"master","sha":"33ebe1f18b9cf5909931376f656e19e80ac9ac1c","user":{"login":"kubernetes","id":13629408,"avatar_url":"https://avatars.githubusercontent.com/u/13629408?v=3","gravatar_id":"","url":"https://api.github.com/users/kubernetes","html_url":"https://github.com/kubernetes","followers_url":"https://api.github.com/users/kubernetes/followers","following_url":"https://api.github.com/users/kubernetes/following{/other_user}","gists_url":"https://api.github.com/users/kubernetes/gists{/gist_id}","starred_url":"https://api.github.com/users/kubernetes/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/kubernetes/subscriptions","organizations_url":"https://api.github.com/users/kubernetes/orgs","repos_url":"https://api.github.com/users/kubernetes/repos","events_url":"https://api.github.com/users/kubernetes/events{/privacy}","received_events_url":"https://api.github.com/users/kubernetes/received_events","type":"Organization","site_admin":false},"repo":{"id":20580498,"name":"kubernetes","full_name":"kubernetes/kubernetes","owner":{"login":"kubernetes","id":13629408,"avatar_url":"https://avatars.githubusercontent.com/u/13629408?v=3","gravatar_id":"","url":"https://api.github.com/users/kubernetes","html_url":"https://github.com/kubernetes","followers_url":"https://api.github.com/users/kubernetes/followers","following_url":"https://api.github.com/users/kubernetes/following{/other_user}","gists_url":"https://api.github.com/users/kubernetes/gists{/gist_id}","starred_url":"https://api.github.com/users/kubernetes/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/kubernetes/subscriptions","organizations_url":"https://api.github.com/users/kubernetes/orgs","repos_url":"https://api.github.com/users/kubernetes/repos","events_url":"https://api.github.com/users/kubernetes/events{/privacy}","received_events_url":"https://api.github.com/users/kubernetes/received_events","type":"Organization","site_admin":false},"private":false,"html_url":"https://github.com/kubernetes/kubernetes","description":"Production-Grade Container Scheduling and Management","fork":false,"url":"https://api.github.com/repos/kubernetes/kubernetes","forks_url":"https://api.github.com/repos/kubernetes/kubernetes/forks","keys_url":"https://api.github.com/repos/kubernetes/kubernetes/keys{/key_id}","collaborators_url":"https://api.github.com/repos/kubernetes/kubernetes/collaborators{/collaborator}","teams_url":"https://api.github.com/repos/kubernetes/kubernetes/teams","hooks_url":"https://api.github.com/repos/kubernetes/kubernetes/hooks","issue_events_url":"https://api.github.com/repos/kubernetes/kubernetes/issues/events{/number}","events_url":"https://api.github.com/repos/kubernetes/kubernetes/events","assignees_url":"https://api.github.com/repos/kubernetes/kubernetes/assignees{/user}","branches_url":"https://api.github.com/repos/kubernetes/kubernetes/branches{/branch}","tags_url":"https://api.github.com/repos/kubernetes/kubernetes/tags","blobs_url":"https://api.github.com/repos/kubernetes/kubernetes/git/blobs{/sha}","git_tags_url":"https://api.github.com/repos/kubernetes/kubernetes/git/tags{/sha}","git_refs_url":"https://api.github.com/repos/kubernetes/kubernetes/git/refs{/sha}","trees_url":"https://api.github.com/repos/kubernetes/kubernetes/git/trees{/sha}","statuses_url":"https://api.github.com/repos/kubernetes/kubernetes/statuses/{sha}","languages_url":"https://api.github.com/repos/kubernetes/kubernetes/languages","stargazers_url":"https://api.github.com/repos/kubernetes/kubernetes/stargazers","contributors_url":"https://api.github.com/repos/kubernetes/kubernetes/contributors","subscribers_url":"https://api.github.com/repos/kubernetes/kubernetes/subscribers","subscription_url":"https://api.github.com/repos/kubernetes/kubernetes/subscription","commits_url":"https://api.github.com/repos/kubernetes/kubernetes/commits{/sha}","git_commits_url":"https://api.github.com/repos/kubernetes/kubernetes/git/commits{/sha}","comments_url":"https://api.github.com/repos/kubernetes/kubernetes/comments{/number}","issue_comment_url":"https://api.github.com/repos/kubernetes/kubernetes/issues/comments{/number}","contents_url":"https://api.github.com/repos/kubernetes/kubernetes/contents/{+path}","compare_url":"https://api.github.com/repos/kubernetes/kubernetes/compare/{base}...{head}","merges_url":"https://api.github.com/repos/kubernetes/kubernetes/merges","archive_url":"https://api.github.com/repos/kubernetes/kubernetes/{archive_format}{/ref}","downloads_url":"https://api.github.com/repos/kubernetes/kubernetes/downloads","issues_url":"https://api.github.com/repos/kubernetes/kubernetes/issues{/number}","pulls_url":"https://api.github.com/repos/kubernetes/kubernetes/pulls{/number}","milestones_url":"https://api.github.com/repos/kubernetes/kubernetes/milestones{/number}","notifications_url":"https://api.github.com/repos/kubernetes/kubernetes/notifications{?since,all,participating}","labels_url":"https://api.github.com/repos/kubernetes/kubernetes/labels{/name}","releases_url":"https://api.github.com/repos/kubernetes/kubernetes/releases{/id}","deployments_url":"https://api.github.com/repos/kubernetes/kubernetes/deployments","created_at":"2014-06-06T22:56:04Z","updated_at":"2016-10-25T14:50:13Z","pushed_at":"2016-10-25T14:48:09Z","git_url":"git://github.com/kubernetes/kubernetes.git","ssh_url":"git@github.com:kubernetes/kubernetes.git","clone_url":"https://github.com/kubernetes/kubernetes.git","svn_url":"https://github.com/kubernetes/kubernetes","homepage":"http://kubernetes.io","size":601994,"stargazers_count":17900,"watchers_count":17900,"language":"Go","has_issues":true,"has_downloads":true,"has_wiki":true,"has_pages":true,"forks_count":5827,"mirror_url":null,"open_issues_count":5112,"forks":5827,"open_issues":5112,"watchers":17900,"default_branch":"master"}},"_links":{"self":{"href":"https://api.github.com/repos/kubernetes/kubernetes/pulls/35436"},"html":{"href":"https://github.com/kubernetes/kubernetes/pull/35436"},"issue":{"href":"https://api.github.com/repos/kubernetes/kubernetes/issues/35436"},"comments":{"href":"https://api.github.com/repos/kubernetes/kubernetes/issues/35436/comments"},"review_comments":{"href":"https://api.github.com/repos/kubernetes/kubernetes/pulls/35436/comments"},"review_comment":{"href":"https://api.github.com/repos/kubernetes/kubernetes/pulls/comments{/number}"},"commits":{"href":"https://api.github.com/repos/kubernetes/kubernetes/pulls/35436/commits"},"statuses":{"href":"https://api.github.com/repos/kubernetes/kubernetes/statuses/c2a231372d114475b38386bea797acb44bce6ea4"}}}}
{"actor":{"display_login":"thockin"}}