{"action":"created","issue":{"url":"https://api.github.com/repos/gravitational/teleport/issues/415","repository_url":"https://api.github.com/repos/gravitational/teleport","labels_url":"https://api.github.com/repos/gravitational/teleport/issues/415/labels{/name}","comments_url":"https://api.github.com/repos/gravitational/teleport/issues/415/comments","events_url":"https://api.github.com/repos/gravitational/teleport/issues/415/events","html_url":"https://github.com/gravitational/teleport/pull/415","id":154627426,"number":415,"title":"Multi-role and multi-use provisioning tokens","user":{"login":"kontsevoy","id":461020,"avatar_url":"https://avatars.githubusercontent.com/u/461020?v=3","gravatar_id":"","url":"https://api.github.com/users/kontsevoy","html_url":"https://github.com/kontsevoy","followers_url":"https://api.github.com/users/kontsevoy/followers","following_url":"https://api.github.com/users/kontsevoy/following{/other_user}","gists_url":"https://api.github.com/users/kontsevoy/gists{/gist_id}","starred_url":"https://api.github.com/users/kontsevoy/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/kontsevoy/subscriptions","organizations_url":"https://api.github.com/users/kontsevoy/orgs","repos_url":"https://api.github.com/users/kontsevoy/repos","events_url":"https://api.github.com/users/kontsevoy/events{/privacy}","received_events_url":"https://api.github.com/users/kontsevoy/received_events","type":"User","site_admin":false},"labels":[],"state":"open","locked":false,"assignee":{"login":"klizhentas","id":13717,"avatar_url":"https://avatars.githubusercontent.com/u/13717?v=3","gravatar_id":"","url":"https://api.github.com/users/klizhentas","html_url":"https://github.com/klizhentas","followers_url":"https://api.github.com/users/klizhentas/followers","following_url":"https://api.github.com/users/klizhentas/following{/other_user}","gists_url":"https://api.github.com/users/klizhentas/gists{/gist_id}","starred_url":"https://api.github.com/users/klizhentas/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/klizhentas/subscriptions","organizations_url":"https://api.github.com/users/klizhentas/orgs","repos_url":"https://api.github.com/users/klizhentas/repos","events_url":"https://api.github.com/users/klizhentas/events{/privacy}","received_events_url":"https://api.github.com/users/klizhentas/received_events","type":"User","site_admin":false},"milestone":null,"comments":5,"created_at":"2016-05-13T03:37:01Z","updated_at":"2016-05-15T01:36:23Z","closed_at":null,"pull_request":{"url":"https://api.github.com/repos/gravitational/teleport/pulls/415","html_url":"https://github.com/gravitational/teleport/pull/415","diff_url":"https://github.com/gravitational/teleport/pull/415.diff","patch_url":"https://github.com/gravitational/teleport/pull/415.patch"},"body":"## Problem\r\n\r\nTeleport was designed to be overly strict when it comes to adding nodes to the cluster. A user would have to generate a token first, then specify this token when launching `teleport` daemon with `node` role. This made it difficult to stand up multiple servers from a single Ansible script, use Vagrant, use AWS AMIs, etc. A less paranoid, static configuration was needed.\r\n\r\nAnother problem was that Teleport tokens only allowed new nodes to be added to the cluster. There was no way to create a token which would allow a new server to become assume role \"node\" and a \"proxy\" role at the same time.\r\n\r\nThe changes below address both of these issues.\r\n\r\n## Configuration changes\r\n\r\n`teleport.yaml` now has only one place to specify `auth_token` and it's in the global \"teleport\" section as opposed to individual \"proxy/node\" sections. This is possible because the same token can now be used for multiple roles.\r\n\r\nAlso, the `auth_service` section there is a new setting: `cluster_name`. It will be used in future versions of Teleport to connect trusting clusters together.\r\n\r\n## Multi-use Tokens\r\n\r\n- Generated tokens can be used multiple times up to TTL.\r\n- By default all tokens have a TTL of 30 minutes, but a new `--ttl` flag for `tctl nodes add` can override that.\r\n- `tctl nodes add` gets a new roles flag, example: `--roles=node,proxy` this allows new nodes to assume both \"node\" and \"proxy\" roles.\r\n\r\n## Static Tokens\r\n\r\nFor even less paranoid, Teleport auth now allows to specify a list of static tokens which will always be used to provision new nodes and they never expire.\r\n\r\nConsider this teleport `auth` configuration (teleport.yaml):\r\n```yaml\r\nteleport:\r\n  nodename: auth-a\r\n  log:\r\n    output: stderr\r\n    severity: INFO\r\n\r\nauth_service:\r\n  enabled: yes\r\n  cluster_name: cluster-a.local.com\r\n  listen_addr: 0.0.0.0:3025\r\n  # Notice how you can pre-define tokens for adding servers with different roles\r\n  tokens: \r\n  - \"proxy,role:cai8ohV7eem2OhcathuTh4oo\"\r\n  - \"auth:Hoqu8tai7ailo2PiKoree9no\"\r\n\r\nssh_service:\r\n  enabled: no\r\n\r\nproxy_service:\r\n  enabled: no\r\n```\r\n\r\nThe config file for the node (which also runs proxy) which wants to join to this cluster:\r\n```yaml\r\nteleport:\r\n  nodename: proxy-node\r\n  auth_servers: [\"10.0.10.10:3025\"]\r\n  auth_token: \"cai8ohV7eem2OhcathuTh4oo\"\r\n\r\nauth_service:\r\n  enabled: no\r\n  listen_addr: 0.0.0.0:3025\r\n\r\nssh_service:\r\n  enabled: yes\r\n\r\nproxy_service:\r\n  enabled: yes\r\n```\r\n\r\n## Other Changes\r\n\r\n`auth` server is now manually handling TTL, this results in nice and clear error messages. So instead of \"invalid parameter\" when adding nodes with tokens, users will see:\r\n\r\n- XXX cannot join the cluster as 'proxy': token is invalid\r\n- XXX cannot join the cluster as 'proxy': token has expired\r\n- XXX cannot join the cluster as 'proxy': the token does not allow 'proxy' role\r\n\r\nAlso cleaned up `tctl` --help pages and added a nicer 6-node Vagrant recipe to easier test various deployment scenarios.\r\n\r\n\r\nCloses #406\r\nCloses #379\r\nCloses #307"},"comment":{"url":"https://api.github.com/repos/gravitational/teleport/issues/comments/219261027","html_url":"https://github.com/gravitational/teleport/pull/415#issuecomment-219261027","issue_url":"https://api.github.com/repos/gravitational/teleport/issues/415","id":219261027,"user":{"login":"kontsevoy","id":461020,"avatar_url":"https://avatars.githubusercontent.com/u/461020?v=3","gravatar_id":"","url":"https://api.github.com/users/kontsevoy","html_url":"https://github.com/kontsevoy","followers_url":"https://api.github.com/users/kontsevoy/followers","following_url":"https://api.github.com/users/kontsevoy/following{/other_user}","gists_url":"https://api.github.com/users/kontsevoy/gists{/gist_id}","starred_url":"https://api.github.com/users/kontsevoy/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/kontsevoy/subscriptions","organizations_url":"https://api.github.com/users/kontsevoy/orgs","repos_url":"https://api.github.com/users/kontsevoy/repos","events_url":"https://api.github.com/users/kontsevoy/events{/privacy}","received_events_url":"https://api.github.com/users/kontsevoy/received_events","type":"User","site_admin":false},"created_at":"2016-05-15T01:36:23Z","updated_at":"2016-05-15T01:36:23Z","body":"I do not think your suggestions for handling errors are helpful. The reason these changes were made was to improve end-user experience. Teleport in general has a tendency to ignore errors: it bubbles up the low level errors (like \"file does not exist\" or \"closed socket\") all the way to the UI.\r\n\r\nA user is then left without any helpful information whatsoever. Trying to add a node? \"Closed socket!\" Trying to list servers? \"too many open files\", etc. From a end-user perspective this is about as valuable as not handling errors at all.\r\n\r\nThese changes aim to:\r\n- Log a _helpful_ message to Teleport log for an admin.\r\n- Send a human-readable error via the wire to the calling client.\r\n\r\nAll of these changes were forced by real-world usability testing. \r\n\r\nI am not saying Teleport has a faulty error handling. I am saying that Teleport error handling is optimized for SaaS-like environment when errors are shipped into an external structured log and analyzed later by developers. \r\n\r\nThis approach does not provide an acceptable user experience for installable  software like Teleport which \"speaks\" via CLI errors and user-readable log messages (and developers aren't around)"}}