-user.email::
- Your email address to be recorded in any newly created commits.
- Can be overridden by the `GIT_AUTHOR_EMAIL`, `GIT_COMMITTER_EMAIL`, and
- `EMAIL` environment variables. See linkgit:git-commit-tree[1].
-
user.name::
- Your full name to be recorded in any newly created commits.
- Can be overridden by the `GIT_AUTHOR_NAME` and `GIT_COMMITTER_NAME`
- environment variables. See linkgit:git-commit-tree[1].
+user.email::
+author.name::
+author.email::
+committer.name::
+committer.email::
+ The `user.name` and `user.email` variables determine what ends
+ up in the `author` and `committer` field of commit
+ objects.
+ If you need the `author` or `committer` to be different, the
+ `author.name`, `author.email`, `committer.name` or
+ `committer.email` variables can be set.
+ Also, all of these can be overridden by the `GIT_AUTHOR_NAME`,
+ `GIT_AUTHOR_EMAIL`, `GIT_COMMITTER_NAME`,
+ `GIT_COMMITTER_EMAIL` and `EMAIL` environment variables.
+ See linkgit:git-commit-tree[1] for more information.
user.useConfigOnly::
Instruct Git to avoid trying to guess defaults for `user.email`
origin = make_origin(commit, path);
- ident = fmt_ident("Not Committed Yet", "not.committed.yet", NULL, 0);
+ ident = fmt_ident("Not Committed Yet", "not.committed.yet",
+ WANT_BLANK_IDENT, NULL, 0);
strbuf_addstr(&msg, "tree 0000000000000000000000000000000000000000\n");
for (parent = commit->parents; parent; parent = parent->next)
strbuf_addf(&msg, "parent %s\n",
}
author = fmt_ident(state->author_name, state->author_email,
+ WANT_AUTHOR_IDENT,
state->ignore_date ? NULL : state->author_date,
IDENT_STRICT);
set_ident_var(&date, strbuf_detach(&date_buf, NULL));
}
- strbuf_addstr(author_ident, fmt_ident(name, email, date, IDENT_STRICT));
+ strbuf_addstr(author_ident, fmt_ident(name, email, WANT_AUTHOR_IDENT, date,
+ IDENT_STRICT));
assert_split_ident(&author, author_ident);
export_one("GIT_AUTHOR_NAME", author.name_begin, author.name_end, 0);
export_one("GIT_AUTHOR_EMAIL", author.mail_begin, author.mail_end, 0);
#define IDENT_STRICT 1
#define IDENT_NO_DATE 2
#define IDENT_NO_NAME 4
+
+enum want_ident {
+ WANT_BLANK_IDENT,
+ WANT_AUTHOR_IDENT,
+ WANT_COMMITTER_IDENT
+};
+
extern const char *git_author_info(int);
extern const char *git_committer_info(int);
-extern const char *fmt_ident(const char *name, const char *email, const char *date_str, int);
-extern const char *fmt_name(const char *name, const char *email);
+extern const char *fmt_ident(const char *name, const char *email,
+ enum want_ident whose_ident,
+ const char *date_str, int);
+extern const char *fmt_name(enum want_ident);
extern const char *ident_default_name(void);
extern const char *ident_default_email(void);
extern const char *git_editor(void);
if (starts_with(var, "core."))
return git_default_core_config(var, value, cb);
- if (starts_with(var, "user."))
+ if (starts_with(var, "user.") ||
+ starts_with(var, "author.") ||
+ starts_with(var, "committer."))
return git_ident_config(var, value, cb);
if (starts_with(var, "i18n."))
static struct strbuf git_default_name = STRBUF_INIT;
static struct strbuf git_default_email = STRBUF_INIT;
static struct strbuf git_default_date = STRBUF_INIT;
+static struct strbuf git_author_name = STRBUF_INIT;
+static struct strbuf git_author_email = STRBUF_INIT;
+static struct strbuf git_committer_name = STRBUF_INIT;
+static struct strbuf git_committer_email = STRBUF_INIT;
static int default_email_is_bogus;
static int default_name_is_bogus;
"\n");
const char *fmt_ident(const char *name, const char *email,
- const char *date_str, int flag)
+ enum want_ident whose_ident, const char *date_str, int flag)
{
static struct strbuf ident = STRBUF_INIT;
int strict = (flag & IDENT_STRICT);
int want_date = !(flag & IDENT_NO_DATE);
int want_name = !(flag & IDENT_NO_NAME);
+ if (!email) {
+ if (whose_ident == WANT_AUTHOR_IDENT && git_author_email.len)
+ email = git_author_email.buf;
+ else if (whose_ident == WANT_COMMITTER_IDENT && git_committer_email.len)
+ email = git_committer_email.buf;
+ }
if (!email) {
if (strict && ident_use_config_only
&& !(ident_config_given & IDENT_MAIL_GIVEN)) {
if (want_name) {
int using_default = 0;
+ if (!name) {
+ if (whose_ident == WANT_AUTHOR_IDENT && git_author_name.len)
+ name = git_author_name.buf;
+ else if (whose_ident == WANT_COMMITTER_IDENT &&
+ git_committer_name.len)
+ name = git_committer_name.buf;
+ }
if (!name) {
if (strict && ident_use_config_only
&& !(ident_config_given & IDENT_NAME_GIVEN)) {
return ident.buf;
}
-const char *fmt_name(const char *name, const char *email)
+const char *fmt_name(enum want_ident whose_ident)
{
- return fmt_ident(name, email, NULL, IDENT_STRICT | IDENT_NO_DATE);
+ char *name = NULL;
+ char *email = NULL;
+
+ switch (whose_ident) {
+ case WANT_BLANK_IDENT:
+ break;
+ case WANT_AUTHOR_IDENT:
+ name = getenv("GIT_AUTHOR_NAME");
+ email = getenv("GIT_AUTHOR_EMAIL");
+ break;
+ case WANT_COMMITTER_IDENT:
+ name = getenv("GIT_COMMITTER_NAME");
+ email = getenv("GIT_COMMITTER_EMAIL");
+ break;
+ }
+ return fmt_ident(name, email, whose_ident, NULL,
+ IDENT_STRICT | IDENT_NO_DATE);
}
const char *git_author_info(int flag)
author_ident_explicitly_given |= IDENT_MAIL_GIVEN;
return fmt_ident(getenv("GIT_AUTHOR_NAME"),
getenv("GIT_AUTHOR_EMAIL"),
+ WANT_AUTHOR_IDENT,
getenv("GIT_AUTHOR_DATE"),
flag);
}
committer_ident_explicitly_given |= IDENT_MAIL_GIVEN;
return fmt_ident(getenv("GIT_COMMITTER_NAME"),
getenv("GIT_COMMITTER_EMAIL"),
+ WANT_COMMITTER_IDENT,
getenv("GIT_COMMITTER_DATE"),
flag);
}
return ident_is_sufficient(author_ident_explicitly_given);
}
-int git_ident_config(const char *var, const char *value, void *data)
+static int set_ident(const char *var, const char *value)
{
- if (!strcmp(var, "user.useconfigonly")) {
- ident_use_config_only = git_config_bool(var, value);
+ if (!strcmp(var, "author.name")) {
+ if (!value)
+ return config_error_nonbool(var);
+ strbuf_reset(&git_author_name);
+ strbuf_addstr(&git_author_name, value);
+ author_ident_explicitly_given |= IDENT_NAME_GIVEN;
+ ident_config_given |= IDENT_NAME_GIVEN;
+ return 0;
+ }
+
+ if (!strcmp(var, "author.email")) {
+ if (!value)
+ return config_error_nonbool(var);
+ strbuf_reset(&git_author_email);
+ strbuf_addstr(&git_author_email, value);
+ author_ident_explicitly_given |= IDENT_MAIL_GIVEN;
+ ident_config_given |= IDENT_MAIL_GIVEN;
+ return 0;
+ }
+
+ if (!strcmp(var, "committer.name")) {
+ if (!value)
+ return config_error_nonbool(var);
+ strbuf_reset(&git_committer_name);
+ strbuf_addstr(&git_committer_name, value);
+ committer_ident_explicitly_given |= IDENT_NAME_GIVEN;
+ ident_config_given |= IDENT_NAME_GIVEN;
+ return 0;
+ }
+
+ if (!strcmp(var, "committer.email")) {
+ if (!value)
+ return config_error_nonbool(var);
+ strbuf_reset(&git_committer_email);
+ strbuf_addstr(&git_committer_email, value);
+ committer_ident_explicitly_given |= IDENT_MAIL_GIVEN;
+ ident_config_given |= IDENT_MAIL_GIVEN;
return 0;
}
return 0;
}
+int git_ident_config(const char *var, const char *value, void *data)
+{
+ if (!strcmp(var, "user.useconfigonly")) {
+ ident_use_config_only = git_config_bool(var, value);
+ return 0;
+ }
+
+ return set_ident(var, value);
+}
+
static int buf_cmp(const char *a_begin, const char *a_end,
const char *b_begin, const char *b_end)
{
*/
if (ctx.need_8bit_cte >= 0 && opt->add_signoff)
ctx.need_8bit_cte =
- has_non_ascii(fmt_name(getenv("GIT_COMMITTER_NAME"),
- getenv("GIT_COMMITTER_EMAIL")));
+ has_non_ascii(fmt_name(WANT_COMMITTER_IDENT));
ctx.date_mode = opt->date_mode;
ctx.date_mode_explicit = opt->date_mode_explicit;
ctx.abbrev = opt->diffopt.abbrev;
}
strbuf_reset(&out);
- strbuf_addstr(&out, fmt_ident(name, email, date, 0));
+ strbuf_addstr(&out, fmt_ident(name, email, WANT_AUTHOR_IDENT, date, 0));
strbuf_swap(buf, &out);
strbuf_release(&out);
free(name);
int has_footer;
strbuf_addstr(&sob, sign_off_header);
- strbuf_addstr(&sob, fmt_name(getenv("GIT_COMMITTER_NAME"),
- getenv("GIT_COMMITTER_EMAIL")));
+ strbuf_addstr(&sob, fmt_name(WANT_COMMITTER_IDENT));
strbuf_addch(&sob, '\n');
if (!ignore_footer)
test_must_fail git rebase -p master
'
+test_expect_success 'author.name overrides user.name' '
+ test_config user.name user &&
+ test_config user.email user@example.com &&
+ test_config author.name author &&
+ test_commit author-name-override-user &&
+ echo author user@example.com > expected-author &&
+ echo user user@example.com > expected-committer &&
+ git log --format="%an %ae" -1 > actual-author &&
+ git log --format="%cn %ce" -1 > actual-committer &&
+ test_cmp expected-author actual-author &&
+ test_cmp expected-committer actual-committer
+'
+
+test_expect_success 'author.email overrides user.email' '
+ test_config user.name user &&
+ test_config user.email user@example.com &&
+ test_config author.email author@example.com &&
+ test_commit author-email-override-user &&
+ echo user author@example.com > expected-author &&
+ echo user user@example.com > expected-committer &&
+ git log --format="%an %ae" -1 > actual-author &&
+ git log --format="%cn %ce" -1 > actual-committer &&
+ test_cmp expected-author actual-author &&
+ test_cmp expected-committer actual-committer
+'
+
+test_expect_success 'committer.name overrides user.name' '
+ test_config user.name user &&
+ test_config user.email user@example.com &&
+ test_config committer.name committer &&
+ test_commit committer-name-override-user &&
+ echo user user@example.com > expected-author &&
+ echo committer user@example.com > expected-committer &&
+ git log --format="%an %ae" -1 > actual-author &&
+ git log --format="%cn %ce" -1 > actual-committer &&
+ test_cmp expected-author actual-author &&
+ test_cmp expected-committer actual-committer
+'
+
+test_expect_success 'committer.email overrides user.email' '
+ test_config user.name user &&
+ test_config user.email user@example.com &&
+ test_config committer.email committer@example.com &&
+ test_commit committer-email-override-user &&
+ echo user user@example.com > expected-author &&
+ echo user committer@example.com > expected-committer &&
+ git log --format="%an %ae" -1 > actual-author &&
+ git log --format="%cn %ce" -1 > actual-committer &&
+ test_cmp expected-author actual-author &&
+ test_cmp expected-committer actual-committer
+'
+
+test_expect_success 'author and committer environment variables override config settings' '
+ test_config user.name user &&
+ test_config user.email user@example.com &&
+ test_config author.name author &&
+ test_config author.email author@example.com &&
+ test_config committer.name committer &&
+ test_config committer.email committer@example.com &&
+ GIT_AUTHOR_NAME=env_author && export GIT_AUTHOR_NAME &&
+ GIT_AUTHOR_EMAIL=env_author@example.com && export GIT_AUTHOR_EMAIL &&
+ GIT_COMMITTER_NAME=env_commit && export GIT_COMMITTER_NAME &&
+ GIT_COMMITTER_EMAIL=env_commit@example.com && export GIT_COMMITTER_EMAIL &&
+ test_commit env-override-conf &&
+ echo env_author env_author@example.com > expected-author &&
+ echo env_commit env_commit@example.com > expected-committer &&
+ git log --format="%an %ae" -1 > actual-author &&
+ git log --format="%cn %ce" -1 > actual-committer &&
+ sane_unset GIT_AUTHOR_NAME GIT_AUTHOR_EMAIL &&
+ sane_unset GIT_COMMITTER_NAME GIT_COMMITTER_EMAIL &&
+ test_cmp expected-author actual-author &&
+ test_cmp expected-committer actual-committer
+'
+
test_done