From 314a5ecec0d716dffcebebd03580b5ae42e9c68e Mon Sep 17 00:00:00 2001 From: "Nathan J. Mehl" Date: Tue, 12 Jul 2016 17:05:43 -0700 Subject: [PATCH] allow overriding the default truncation length for mysql usernames see https://github.com/hashicorp/vault/issues/1605 --- builtin/logical/mysql/path_role_create.go | 11 +++++++++-- builtin/logical/mysql/path_roles.go | 17 +++++++++++++++-- website/source/docs/secrets/mysql/index.html.md | 14 ++++++++++++++ 3 files changed, 38 insertions(+), 4 deletions(-) diff --git a/builtin/logical/mysql/path_role_create.go b/builtin/logical/mysql/path_role_create.go index 4d0553176..734b34ced 100644 --- a/builtin/logical/mysql/path_role_create.go +++ b/builtin/logical/mysql/path_role_create.go @@ -31,6 +31,7 @@ func pathRoleCreate(b *backend) *framework.Path { func (b *backend) pathRoleCreateRead( req *logical.Request, data *framework.FieldData) (*logical.Response, error) { name := data.Get("name").(string) + var usernameLength int // Get the role role, err := b.Role(req.Storage, name) @@ -52,8 +53,14 @@ func (b *backend) pathRoleCreateRead( // Generate our username and password. MySQL limits user to 16 characters displayName := name - if len(displayName) > 10 { - displayName = displayName[:10] + ul, ok := data.GetOk("username_length") + if ok == true { + usernameLength = ul.(int) + } else { + usernameLength = 10 + } + if len(displayName) > usernameLength { + displayName = displayName[:usernameLength] } userUUID, err := uuid.GenerateUUID() if err != nil { diff --git a/builtin/logical/mysql/path_roles.go b/builtin/logical/mysql/path_roles.go index d7d621a90..998e2ad2d 100644 --- a/builtin/logical/mysql/path_roles.go +++ b/builtin/logical/mysql/path_roles.go @@ -34,6 +34,11 @@ func pathRoles(b *backend) *framework.Path { Type: framework.TypeString, Description: "SQL string to create a user. See help for more info.", }, + + "username_length": &framework.FieldSchema{ + Type: framework.TypeInt, + Description: "number of characters to truncate generated mysql usernames to (default 10)", + }, }, Callbacks: map[logical.Operation]framework.OperationFunc{ @@ -105,6 +110,7 @@ func (b *backend) pathRoleCreate( req *logical.Request, data *framework.FieldData) (*logical.Response, error) { name := data.Get("name").(string) sql := data.Get("sql").(string) + username_length := data.Get("username_length").(int) // Get our connection db, err := b.DB(req.Storage) @@ -127,7 +133,8 @@ func (b *backend) pathRoleCreate( // Store it entry, err := logical.StorageEntryJSON("role/"+name, &roleEntry{ - SQL: sql, + SQL: sql, + USERNAME_LENGTH: username_length, }) if err != nil { return nil, err @@ -139,7 +146,8 @@ func (b *backend) pathRoleCreate( } type roleEntry struct { - SQL string `json:"sql"` + SQL string `json:"sql"` + USERNAME_LENGTH int `json:"username_length"` } const pathRoleHelpSyn = ` @@ -165,4 +173,9 @@ Example of a decent SQL query to use: Note the above user would be able to access anything in db1. Please see the MySQL manual on the GRANT command to learn how to do more fine grained access. + +The "username_length" parameter determines how many characters of the +role name will be used in creating the generated mysql username; the +default is 10. Note that mysql versions prior to 5.8 have a 16 character +total limit on usernames. ` diff --git a/website/source/docs/secrets/mysql/index.html.md b/website/source/docs/secrets/mysql/index.html.md index 6e0ea3609..bf43f5fd6 100644 --- a/website/source/docs/secrets/mysql/index.html.md +++ b/website/source/docs/secrets/mysql/index.html.md @@ -105,6 +105,13 @@ that trusted operators can manage the role definitions, and both users and applications are restricted in the credentials they are allowed to read. +Optionally, you may configure the number of character from the role +name that are truncated to form the mysql usernamed interpolated into +the `{{name}}` field: the default is 10. Note that versions of +mysql prior to 5.8 have a 16 character total limit on user names, so +it is probably not safe to increase this above the default on versions +prior to that. + ## API ### /mysql/config/connection @@ -234,6 +241,13 @@ allowed to read. Must be semi-colon separated. The '{{name}}' and '{{password}}' values will be substituted. +
  • + username_length + optional + Determines how many characters from the role name will be used + to form the mysql username interpolated into the '{{name}}' field + of the sql parameter. +