Merge branch 'nd/per-worktree-config'
A fourth class of configuration files (in addition to the traditional "system wide", "per user in the $HOME directory" and "per repository in the $GIT_DIR/config") has been introduced so that different worktrees that share the same repository (hence the same $GIT_DIR/config file) can use different customization. * nd/per-worktree-config: worktree: add per-worktree config files t1300: extract and use test_cmp_config()maint
commit
8c758f9a67
|
@ -2,8 +2,9 @@ CONFIGURATION FILE
|
||||||
------------------
|
------------------
|
||||||
|
|
||||||
The Git configuration file contains a number of variables that affect
|
The Git configuration file contains a number of variables that affect
|
||||||
the Git commands' behavior. The `.git/config` file in each repository
|
the Git commands' behavior. The files `.git/config` and optionally
|
||||||
is used to store the configuration for that repository, and
|
`config.worktree` (see `extensions.worktreeConfig` below) in each
|
||||||
|
repository are used to store the configuration for that repository, and
|
||||||
`$HOME/.gitconfig` is used to store a per-user configuration as
|
`$HOME/.gitconfig` is used to store a per-user configuration as
|
||||||
fallback values for the `.git/config` file. The file `/etc/gitconfig`
|
fallback values for the `.git/config` file. The file `/etc/gitconfig`
|
||||||
can be used to store a system-wide default configuration.
|
can be used to store a system-wide default configuration.
|
||||||
|
@ -291,6 +292,13 @@ include::config/advice.txt[]
|
||||||
|
|
||||||
include::config/core.txt[]
|
include::config/core.txt[]
|
||||||
|
|
||||||
|
extensions.worktreeConfig::
|
||||||
|
If set, by default "git config" reads from both "config" and
|
||||||
|
"config.worktree" file from GIT_DIR in that order. In
|
||||||
|
multiple working directory mode, "config" file is shared while
|
||||||
|
"config.worktree" is per-working directory (i.e., it's in
|
||||||
|
GIT_COMMON_DIR/worktrees/<id>/config.worktree)
|
||||||
|
|
||||||
include::config/add.txt[]
|
include::config/add.txt[]
|
||||||
|
|
||||||
include::config/alias.txt[]
|
include::config/alias.txt[]
|
||||||
|
|
|
@ -45,13 +45,15 @@ unset an existing `--type` specifier with `--no-type`.
|
||||||
|
|
||||||
When reading, the values are read from the system, global and
|
When reading, the values are read from the system, global and
|
||||||
repository local configuration files by default, and options
|
repository local configuration files by default, and options
|
||||||
`--system`, `--global`, `--local` and `--file <filename>` can be
|
`--system`, `--global`, `--local`, `--worktree` and
|
||||||
used to tell the command to read from only that location (see <<FILES>>).
|
`--file <filename>` can be used to tell the command to read from only
|
||||||
|
that location (see <<FILES>>).
|
||||||
|
|
||||||
When writing, the new value is written to the repository local
|
When writing, the new value is written to the repository local
|
||||||
configuration file by default, and options `--system`, `--global`,
|
configuration file by default, and options `--system`, `--global`,
|
||||||
`--file <filename>` can be used to tell the command to write to
|
`--worktree`, `--file <filename>` can be used to tell the command to
|
||||||
that location (you can say `--local` but that is the default).
|
write to that location (you can say `--local` but that is the
|
||||||
|
default).
|
||||||
|
|
||||||
This command will fail with non-zero status upon error. Some exit
|
This command will fail with non-zero status upon error. Some exit
|
||||||
codes are:
|
codes are:
|
||||||
|
@ -131,6 +133,11 @@ from all available files.
|
||||||
+
|
+
|
||||||
See also <<FILES>>.
|
See also <<FILES>>.
|
||||||
|
|
||||||
|
--worktree::
|
||||||
|
Similar to `--local` except that `.git/config.worktree` is
|
||||||
|
read from or written to if `extensions.worktreeConfig` is
|
||||||
|
present. If not it's the same as `--local`.
|
||||||
|
|
||||||
-f config-file::
|
-f config-file::
|
||||||
--file config-file::
|
--file config-file::
|
||||||
Use the given config file instead of the one specified by GIT_CONFIG.
|
Use the given config file instead of the one specified by GIT_CONFIG.
|
||||||
|
@ -281,6 +288,10 @@ $XDG_CONFIG_HOME/git/config::
|
||||||
$GIT_DIR/config::
|
$GIT_DIR/config::
|
||||||
Repository specific configuration file.
|
Repository specific configuration file.
|
||||||
|
|
||||||
|
$GIT_DIR/config.worktree::
|
||||||
|
This is optional and is only searched when
|
||||||
|
`extensions.worktreeConfig` is present in $GIT_DIR/config.
|
||||||
|
|
||||||
If no further options are given, all reading options will read all of these
|
If no further options are given, all reading options will read all of these
|
||||||
files that are available. If the global or the system-wide configuration
|
files that are available. If the global or the system-wide configuration
|
||||||
file are not available they will be ignored. If the repository configuration
|
file are not available they will be ignored. If the repository configuration
|
||||||
|
@ -299,9 +310,10 @@ configuration file. Note that this also affects options like `--replace-all`
|
||||||
and `--unset`. *'git config' will only ever change one file at a time*.
|
and `--unset`. *'git config' will only ever change one file at a time*.
|
||||||
|
|
||||||
You can override these rules either by command-line options or by environment
|
You can override these rules either by command-line options or by environment
|
||||||
variables. The `--global` and the `--system` options will limit the file used
|
variables. The `--global`, `--system` and `--worktree` options will limit
|
||||||
to the global or system-wide file respectively. The `GIT_CONFIG` environment
|
the file used to the global, system-wide or per-worktree file respectively.
|
||||||
variable has a similar effect, but you can specify any filename you want.
|
The `GIT_CONFIG` environment variable has a similar effect, but you
|
||||||
|
can specify any filename you want.
|
||||||
|
|
||||||
|
|
||||||
ENVIRONMENT
|
ENVIRONMENT
|
||||||
|
|
|
@ -204,6 +204,36 @@ working trees, it can be used to identify worktrees. For example if
|
||||||
you only have two working trees, at "/abc/def/ghi" and "/abc/def/ggg",
|
you only have two working trees, at "/abc/def/ghi" and "/abc/def/ggg",
|
||||||
then "ghi" or "def/ghi" is enough to point to the former working tree.
|
then "ghi" or "def/ghi" is enough to point to the former working tree.
|
||||||
|
|
||||||
|
CONFIGURATION FILE
|
||||||
|
------------------
|
||||||
|
By default, the repository "config" file is shared across all working
|
||||||
|
trees. If the config variables `core.bare` or `core.worktree` are
|
||||||
|
already present in the config file, they will be applied to the main
|
||||||
|
working trees only.
|
||||||
|
|
||||||
|
In order to have configuration specific to working trees, you can turn
|
||||||
|
on "worktreeConfig" extension, e.g.:
|
||||||
|
|
||||||
|
------------
|
||||||
|
$ git config extensions.worktreeConfig true
|
||||||
|
------------
|
||||||
|
|
||||||
|
In this mode, specific configuration stays in the path pointed by `git
|
||||||
|
rev-parse --git-path config.worktree`. You can add or update
|
||||||
|
configuration in this file with `git config --worktree`. Older Git
|
||||||
|
versions will refuse to access repositories with this extension.
|
||||||
|
|
||||||
|
Note that in this file, the exception for `core.bare` and `core.worktree`
|
||||||
|
is gone. If you have them in $GIT_DIR/config before, you must move
|
||||||
|
them to the `config.worktree` of the main working tree. You may also
|
||||||
|
take this opportunity to review and move other configuration that you
|
||||||
|
do not want to share to all working trees:
|
||||||
|
|
||||||
|
- `core.worktree` and `core.bare` should never be shared
|
||||||
|
|
||||||
|
- `core.sparseCheckout` is recommended per working tree, unless you
|
||||||
|
are sure you always use sparse checkout for all working trees.
|
||||||
|
|
||||||
DETAILS
|
DETAILS
|
||||||
-------
|
-------
|
||||||
Each linked working tree has a private sub-directory in the repository's
|
Each linked working tree has a private sub-directory in the repository's
|
||||||
|
@ -253,6 +283,9 @@ to `/path/main/.git/worktrees/test-next` then a file named
|
||||||
`test-next` entry from being pruned. See
|
`test-next` entry from being pruned. See
|
||||||
linkgit:gitrepository-layout[5] for details.
|
linkgit:gitrepository-layout[5] for details.
|
||||||
|
|
||||||
|
When extensions.worktreeConfig is enabled, the config file
|
||||||
|
`.git/worktrees/<id>/config.worktree` is read after `.git/config` is.
|
||||||
|
|
||||||
LIST OUTPUT FORMAT
|
LIST OUTPUT FORMAT
|
||||||
------------------
|
------------------
|
||||||
The worktree list command has two output formats. The default format shows the
|
The worktree list command has two output formats. The default format shows the
|
||||||
|
|
|
@ -143,6 +143,11 @@ config::
|
||||||
if $GIT_COMMON_DIR is set and "$GIT_COMMON_DIR/config" will be
|
if $GIT_COMMON_DIR is set and "$GIT_COMMON_DIR/config" will be
|
||||||
used instead.
|
used instead.
|
||||||
|
|
||||||
|
config.worktree::
|
||||||
|
Working directory specific configuration file for the main
|
||||||
|
working directory in multiple working directory setup (see
|
||||||
|
linkgit:git-worktree[1]).
|
||||||
|
|
||||||
branches::
|
branches::
|
||||||
A slightly deprecated way to store shorthands to be used
|
A slightly deprecated way to store shorthands to be used
|
||||||
to specify a URL to 'git fetch', 'git pull' and 'git push'.
|
to specify a URL to 'git fetch', 'git pull' and 'git push'.
|
||||||
|
@ -275,6 +280,9 @@ worktrees/<id>/locked::
|
||||||
or manually by `git worktree prune`. The file may contain a string
|
or manually by `git worktree prune`. The file may contain a string
|
||||||
explaining why the repository is locked.
|
explaining why the repository is locked.
|
||||||
|
|
||||||
|
worktrees/<id>/config.worktree::
|
||||||
|
Working directory specific configuration file.
|
||||||
|
|
||||||
SEE ALSO
|
SEE ALSO
|
||||||
--------
|
--------
|
||||||
linkgit:git-init[1],
|
linkgit:git-init[1],
|
||||||
|
|
|
@ -5,6 +5,7 @@
|
||||||
#include "parse-options.h"
|
#include "parse-options.h"
|
||||||
#include "urlmatch.h"
|
#include "urlmatch.h"
|
||||||
#include "quote.h"
|
#include "quote.h"
|
||||||
|
#include "worktree.h"
|
||||||
|
|
||||||
static const char *const builtin_config_usage[] = {
|
static const char *const builtin_config_usage[] = {
|
||||||
N_("git config [<options>]"),
|
N_("git config [<options>]"),
|
||||||
|
@ -24,6 +25,7 @@ static char key_delim = ' ';
|
||||||
static char term = '\n';
|
static char term = '\n';
|
||||||
|
|
||||||
static int use_global_config, use_system_config, use_local_config;
|
static int use_global_config, use_system_config, use_local_config;
|
||||||
|
static int use_worktree_config;
|
||||||
static struct git_config_source given_config_source;
|
static struct git_config_source given_config_source;
|
||||||
static int actions, type;
|
static int actions, type;
|
||||||
static char *default_value;
|
static char *default_value;
|
||||||
|
@ -123,6 +125,7 @@ static struct option builtin_config_options[] = {
|
||||||
OPT_BOOL(0, "global", &use_global_config, N_("use global config file")),
|
OPT_BOOL(0, "global", &use_global_config, N_("use global config file")),
|
||||||
OPT_BOOL(0, "system", &use_system_config, N_("use system config file")),
|
OPT_BOOL(0, "system", &use_system_config, N_("use system config file")),
|
||||||
OPT_BOOL(0, "local", &use_local_config, N_("use repository config file")),
|
OPT_BOOL(0, "local", &use_local_config, N_("use repository config file")),
|
||||||
|
OPT_BOOL(0, "worktree", &use_worktree_config, N_("use per-worktree config file")),
|
||||||
OPT_STRING('f', "file", &given_config_source.file, N_("file"), N_("use given config file")),
|
OPT_STRING('f', "file", &given_config_source.file, N_("file"), N_("use given config file")),
|
||||||
OPT_STRING(0, "blob", &given_config_source.blob, N_("blob-id"), N_("read config from given blob object")),
|
OPT_STRING(0, "blob", &given_config_source.blob, N_("blob-id"), N_("read config from given blob object")),
|
||||||
OPT_GROUP(N_("Action")),
|
OPT_GROUP(N_("Action")),
|
||||||
|
@ -602,6 +605,7 @@ int cmd_config(int argc, const char **argv, const char *prefix)
|
||||||
PARSE_OPT_STOP_AT_NON_OPTION);
|
PARSE_OPT_STOP_AT_NON_OPTION);
|
||||||
|
|
||||||
if (use_global_config + use_system_config + use_local_config +
|
if (use_global_config + use_system_config + use_local_config +
|
||||||
|
use_worktree_config +
|
||||||
!!given_config_source.file + !!given_config_source.blob > 1) {
|
!!given_config_source.file + !!given_config_source.blob > 1) {
|
||||||
error(_("only one config file at a time"));
|
error(_("only one config file at a time"));
|
||||||
usage_builtin_config();
|
usage_builtin_config();
|
||||||
|
@ -645,7 +649,20 @@ int cmd_config(int argc, const char **argv, const char *prefix)
|
||||||
given_config_source.file = git_etc_gitconfig();
|
given_config_source.file = git_etc_gitconfig();
|
||||||
else if (use_local_config)
|
else if (use_local_config)
|
||||||
given_config_source.file = git_pathdup("config");
|
given_config_source.file = git_pathdup("config");
|
||||||
else if (given_config_source.file) {
|
else if (use_worktree_config) {
|
||||||
|
struct worktree **worktrees = get_worktrees(0);
|
||||||
|
if (repository_format_worktree_config)
|
||||||
|
given_config_source.file = git_pathdup("config.worktree");
|
||||||
|
else if (worktrees[0] && worktrees[1])
|
||||||
|
die(_("--worktree cannot be used with multiple "
|
||||||
|
"working trees unless the config\n"
|
||||||
|
"extension worktreeConfig is enabled. "
|
||||||
|
"Please read \"CONFIGURATION FILE\"\n"
|
||||||
|
"section in \"git help worktree\" for details"));
|
||||||
|
else
|
||||||
|
given_config_source.file = git_pathdup("config");
|
||||||
|
free_worktrees(worktrees);
|
||||||
|
} else if (given_config_source.file) {
|
||||||
if (!is_absolute_path(given_config_source.file) && prefix)
|
if (!is_absolute_path(given_config_source.file) && prefix)
|
||||||
given_config_source.file =
|
given_config_source.file =
|
||||||
prefix_filename(prefix, given_config_source.file);
|
prefix_filename(prefix, given_config_source.file);
|
||||||
|
|
2
cache.h
2
cache.h
|
@ -962,11 +962,13 @@ extern int grafts_replace_parents;
|
||||||
extern int repository_format_precious_objects;
|
extern int repository_format_precious_objects;
|
||||||
extern char *repository_format_partial_clone;
|
extern char *repository_format_partial_clone;
|
||||||
extern const char *core_partial_clone_filter_default;
|
extern const char *core_partial_clone_filter_default;
|
||||||
|
extern int repository_format_worktree_config;
|
||||||
|
|
||||||
struct repository_format {
|
struct repository_format {
|
||||||
int version;
|
int version;
|
||||||
int precious_objects;
|
int precious_objects;
|
||||||
char *partial_clone; /* value of extensions.partialclone */
|
char *partial_clone; /* value of extensions.partialclone */
|
||||||
|
int worktree_config;
|
||||||
int is_bare;
|
int is_bare;
|
||||||
int hash_algo;
|
int hash_algo;
|
||||||
char *work_tree;
|
char *work_tree;
|
||||||
|
|
11
config.c
11
config.c
|
@ -1695,6 +1695,17 @@ static int do_git_config_sequence(const struct config_options *opts,
|
||||||
if (repo_config && !access_or_die(repo_config, R_OK, 0))
|
if (repo_config && !access_or_die(repo_config, R_OK, 0))
|
||||||
ret += git_config_from_file(fn, repo_config, data);
|
ret += git_config_from_file(fn, repo_config, data);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Note: this should have a new scope, CONFIG_SCOPE_WORKTREE.
|
||||||
|
* But let's not complicate things before it's actually needed.
|
||||||
|
*/
|
||||||
|
if (repository_format_worktree_config) {
|
||||||
|
char *path = git_pathdup("config.worktree");
|
||||||
|
if (!access_or_die(path, R_OK, 0))
|
||||||
|
ret += git_config_from_file(fn, path, data);
|
||||||
|
free(path);
|
||||||
|
}
|
||||||
|
|
||||||
current_parsing_scope = CONFIG_SCOPE_CMDLINE;
|
current_parsing_scope = CONFIG_SCOPE_CMDLINE;
|
||||||
if (git_config_from_parameters(fn, data) < 0)
|
if (git_config_from_parameters(fn, data) < 0)
|
||||||
die(_("unable to parse command-line config"));
|
die(_("unable to parse command-line config"));
|
||||||
|
|
|
@ -33,6 +33,7 @@ int ref_paranoia = -1;
|
||||||
int repository_format_precious_objects;
|
int repository_format_precious_objects;
|
||||||
char *repository_format_partial_clone;
|
char *repository_format_partial_clone;
|
||||||
const char *core_partial_clone_filter_default;
|
const char *core_partial_clone_filter_default;
|
||||||
|
int repository_format_worktree_config;
|
||||||
const char *git_commit_encoding;
|
const char *git_commit_encoding;
|
||||||
const char *git_log_output_encoding;
|
const char *git_log_output_encoding;
|
||||||
const char *apply_default_whitespace;
|
const char *apply_default_whitespace;
|
||||||
|
|
40
setup.c
40
setup.c
|
@ -402,6 +402,20 @@ void setup_work_tree(void)
|
||||||
initialized = 1;
|
initialized = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int read_worktree_config(const char *var, const char *value, void *vdata)
|
||||||
|
{
|
||||||
|
struct repository_format *data = vdata;
|
||||||
|
|
||||||
|
if (strcmp(var, "core.bare") == 0) {
|
||||||
|
data->is_bare = git_config_bool(var, value);
|
||||||
|
} else if (strcmp(var, "core.worktree") == 0) {
|
||||||
|
if (!value)
|
||||||
|
return config_error_nonbool(var);
|
||||||
|
data->work_tree = xstrdup(value);
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
static int check_repo_format(const char *var, const char *value, void *vdata)
|
static int check_repo_format(const char *var, const char *value, void *vdata)
|
||||||
{
|
{
|
||||||
struct repository_format *data = vdata;
|
struct repository_format *data = vdata;
|
||||||
|
@ -423,16 +437,13 @@ static int check_repo_format(const char *var, const char *value, void *vdata)
|
||||||
if (!value)
|
if (!value)
|
||||||
return config_error_nonbool(var);
|
return config_error_nonbool(var);
|
||||||
data->partial_clone = xstrdup(value);
|
data->partial_clone = xstrdup(value);
|
||||||
} else
|
} else if (!strcmp(ext, "worktreeconfig"))
|
||||||
|
data->worktree_config = git_config_bool(var, value);
|
||||||
|
else
|
||||||
string_list_append(&data->unknown_extensions, ext);
|
string_list_append(&data->unknown_extensions, ext);
|
||||||
} else if (strcmp(var, "core.bare") == 0) {
|
|
||||||
data->is_bare = git_config_bool(var, value);
|
|
||||||
} else if (strcmp(var, "core.worktree") == 0) {
|
|
||||||
if (!value)
|
|
||||||
return config_error_nonbool(var);
|
|
||||||
data->work_tree = xstrdup(value);
|
|
||||||
}
|
}
|
||||||
return 0;
|
|
||||||
|
return read_worktree_config(var, value, vdata);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int check_repository_format_gently(const char *gitdir, struct repository_format *candidate, int *nongit_ok)
|
static int check_repository_format_gently(const char *gitdir, struct repository_format *candidate, int *nongit_ok)
|
||||||
|
@ -466,7 +477,20 @@ static int check_repository_format_gently(const char *gitdir, struct repository_
|
||||||
|
|
||||||
repository_format_precious_objects = candidate->precious_objects;
|
repository_format_precious_objects = candidate->precious_objects;
|
||||||
repository_format_partial_clone = candidate->partial_clone;
|
repository_format_partial_clone = candidate->partial_clone;
|
||||||
|
repository_format_worktree_config = candidate->worktree_config;
|
||||||
string_list_clear(&candidate->unknown_extensions, 0);
|
string_list_clear(&candidate->unknown_extensions, 0);
|
||||||
|
|
||||||
|
if (repository_format_worktree_config) {
|
||||||
|
/*
|
||||||
|
* pick up core.bare and core.worktree from per-worktree
|
||||||
|
* config if present
|
||||||
|
*/
|
||||||
|
strbuf_addf(&sb, "%s/config.worktree", gitdir);
|
||||||
|
git_config_from_file(read_worktree_config, sb.buf, candidate);
|
||||||
|
strbuf_release(&sb);
|
||||||
|
has_common = 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (!has_common) {
|
if (!has_common) {
|
||||||
if (candidate->is_bare != -1) {
|
if (candidate->is_bare != -1) {
|
||||||
is_bare_repository_cfg = candidate->is_bare;
|
is_bare_repository_cfg = candidate->is_bare;
|
||||||
|
|
|
@ -76,15 +76,11 @@ EOF
|
||||||
test_expect_success 'non-match result' 'test_cmp expect .git/config'
|
test_expect_success 'non-match result' 'test_cmp expect .git/config'
|
||||||
|
|
||||||
test_expect_success 'find mixed-case key by canonical name' '
|
test_expect_success 'find mixed-case key by canonical name' '
|
||||||
echo Second >expect &&
|
test_cmp_config Second cores.whatever
|
||||||
git config cores.whatever >actual &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success 'find mixed-case key by non-canonical name' '
|
test_expect_success 'find mixed-case key by non-canonical name' '
|
||||||
echo Second >expect &&
|
test_cmp_config Second CoReS.WhAtEvEr
|
||||||
git config CoReS.WhAtEvEr >actual &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success 'subsections are not canonicalized by git-config' '
|
test_expect_success 'subsections are not canonicalized by git-config' '
|
||||||
|
@ -94,12 +90,8 @@ test_expect_success 'subsections are not canonicalized by git-config' '
|
||||||
[section "SubSection"]
|
[section "SubSection"]
|
||||||
key = two
|
key = two
|
||||||
EOF
|
EOF
|
||||||
echo one >expect &&
|
test_cmp_config one section.subsection.key &&
|
||||||
git config section.subsection.key >actual &&
|
test_cmp_config two section.SubSection.key
|
||||||
test_cmp expect actual &&
|
|
||||||
echo two >expect &&
|
|
||||||
git config section.SubSection.key >actual &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
cat > .git/config <<\EOF
|
cat > .git/config <<\EOF
|
||||||
|
@ -212,9 +204,7 @@ test_expect_success 'really really mean test' '
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success 'get value' '
|
test_expect_success 'get value' '
|
||||||
echo alpha >expect &&
|
test_cmp_config alpha beta.haha
|
||||||
git config beta.haha >actual &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
cat > expect << EOF
|
cat > expect << EOF
|
||||||
|
@ -251,15 +241,11 @@ test_expect_success 'non-match' '
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success 'non-match value' '
|
test_expect_success 'non-match value' '
|
||||||
echo wow >expect &&
|
test_cmp_config wow --get nextsection.nonewline !for
|
||||||
git config --get nextsection.nonewline !for >actual &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success 'multi-valued get returns final one' '
|
test_expect_success 'multi-valued get returns final one' '
|
||||||
echo "wow2 for me" >expect &&
|
test_cmp_config "wow2 for me" --get nextsection.nonewline
|
||||||
git config --get nextsection.nonewline >actual &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success 'multi-valued get-all returns all' '
|
test_expect_success 'multi-valued get-all returns all' '
|
||||||
|
@ -520,21 +506,11 @@ test_expect_success 'editing stdin is an error' '
|
||||||
|
|
||||||
test_expect_success 'refer config from subdirectory' '
|
test_expect_success 'refer config from subdirectory' '
|
||||||
mkdir x &&
|
mkdir x &&
|
||||||
(
|
test_cmp_config -C x strasse --get --file ../other-config ein.bahn
|
||||||
cd x &&
|
|
||||||
echo strasse >expect &&
|
|
||||||
git config --get --file ../other-config ein.bahn >actual &&
|
|
||||||
test_cmp expect actual
|
|
||||||
)
|
|
||||||
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success 'refer config from subdirectory via --file' '
|
test_expect_success 'refer config from subdirectory via --file' '
|
||||||
(
|
test_cmp_config -C x strasse --file=../other-config --get ein.bahn
|
||||||
cd x &&
|
|
||||||
git config --file=../other-config --get ein.bahn >actual &&
|
|
||||||
test_cmp expect actual
|
|
||||||
)
|
|
||||||
'
|
'
|
||||||
|
|
||||||
cat > expect << EOF
|
cat > expect << EOF
|
||||||
|
@ -688,16 +664,13 @@ test_expect_success numbers '
|
||||||
|
|
||||||
test_expect_success '--int is at least 64 bits' '
|
test_expect_success '--int is at least 64 bits' '
|
||||||
git config giga.watts 121g &&
|
git config giga.watts 121g &&
|
||||||
echo 129922760704 >expect &&
|
echo >expect &&
|
||||||
git config --int --get giga.watts >actual &&
|
test_cmp_config 129922760704 --int --get giga.watts
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success 'invalid unit' '
|
test_expect_success 'invalid unit' '
|
||||||
git config aninvalid.unit "1auto" &&
|
git config aninvalid.unit "1auto" &&
|
||||||
echo 1auto >expect &&
|
test_cmp_config 1auto aninvalid.unit &&
|
||||||
git config aninvalid.unit >actual &&
|
|
||||||
test_cmp expect actual &&
|
|
||||||
test_must_fail git config --int --get aninvalid.unit 2>actual &&
|
test_must_fail git config --int --get aninvalid.unit 2>actual &&
|
||||||
test_i18ngrep "bad numeric config value .1auto. for .aninvalid.unit. in file .git/config: invalid unit" actual
|
test_i18ngrep "bad numeric config value .1auto. for .aninvalid.unit. in file .git/config: invalid unit" actual
|
||||||
'
|
'
|
||||||
|
@ -1039,9 +1012,7 @@ test_expect_success '--null --get-regexp' '
|
||||||
|
|
||||||
test_expect_success 'inner whitespace kept verbatim' '
|
test_expect_success 'inner whitespace kept verbatim' '
|
||||||
git config section.val "foo bar" &&
|
git config section.val "foo bar" &&
|
||||||
echo "foo bar" >expect &&
|
test_cmp_config "foo bar" section.val
|
||||||
git config section.val >actual &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success SYMLINKS 'symlinked configuration' '
|
test_expect_success SYMLINKS 'symlinked configuration' '
|
||||||
|
@ -1809,21 +1780,15 @@ big = 1M
|
||||||
EOF
|
EOF
|
||||||
|
|
||||||
test_expect_success 'identical modern --type specifiers are allowed' '
|
test_expect_success 'identical modern --type specifiers are allowed' '
|
||||||
git config --type=int --type=int core.big >actual &&
|
test_cmp_config 1048576 --type=int --type=int core.big
|
||||||
echo 1048576 >expect &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success 'identical legacy --type specifiers are allowed' '
|
test_expect_success 'identical legacy --type specifiers are allowed' '
|
||||||
git config --int --int core.big >actual &&
|
test_cmp_config 1048576 --int --int core.big
|
||||||
echo 1048576 >expect &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success 'identical mixed --type specifiers are allowed' '
|
test_expect_success 'identical mixed --type specifiers are allowed' '
|
||||||
git config --int --type=int core.big >actual &&
|
test_cmp_config 1048576 --int --type=int core.big
|
||||||
echo 1048576 >expect &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success 'non-identical modern --type specifiers are not allowed' '
|
test_expect_success 'non-identical modern --type specifiers are not allowed' '
|
||||||
|
@ -1842,21 +1807,15 @@ test_expect_success 'non-identical mixed --type specifiers are not allowed' '
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success '--type allows valid type specifiers' '
|
test_expect_success '--type allows valid type specifiers' '
|
||||||
echo "true" >expect &&
|
test_cmp_config true --type=bool core.foo
|
||||||
git config --type=bool core.foo >actual &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success '--no-type unsets type specifiers' '
|
test_expect_success '--no-type unsets type specifiers' '
|
||||||
echo "10" >expect &&
|
test_cmp_config 10 --type=bool --no-type core.number
|
||||||
git config --type=bool --no-type core.number >actual &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success 'unset type specifiers may be reset to conflicting ones' '
|
test_expect_success 'unset type specifiers may be reset to conflicting ones' '
|
||||||
echo 1048576 >expect &&
|
test_cmp_config 1048576 --type=bool --no-type --type=int core.big
|
||||||
git config --type=bool --no-type --type=int core.big >actual &&
|
|
||||||
test_cmp expect actual
|
|
||||||
'
|
'
|
||||||
|
|
||||||
test_expect_success '--type rejects unknown specifiers' '
|
test_expect_success '--type rejects unknown specifiers' '
|
||||||
|
|
|
@ -0,0 +1,79 @@
|
||||||
|
#!/bin/sh
|
||||||
|
|
||||||
|
test_description="config file in multi worktree"
|
||||||
|
|
||||||
|
. ./test-lib.sh
|
||||||
|
|
||||||
|
test_expect_success 'setup' '
|
||||||
|
test_commit start
|
||||||
|
'
|
||||||
|
|
||||||
|
test_expect_success 'config --worktree in single worktree' '
|
||||||
|
git config --worktree foo.bar true &&
|
||||||
|
test_cmp_config true foo.bar
|
||||||
|
'
|
||||||
|
|
||||||
|
test_expect_success 'add worktrees' '
|
||||||
|
git worktree add wt1 &&
|
||||||
|
git worktree add wt2
|
||||||
|
'
|
||||||
|
|
||||||
|
test_expect_success 'config --worktree without extension' '
|
||||||
|
test_must_fail git config --worktree foo.bar false
|
||||||
|
'
|
||||||
|
|
||||||
|
test_expect_success 'enable worktreeConfig extension' '
|
||||||
|
git config extensions.worktreeConfig true &&
|
||||||
|
test_cmp_config true extensions.worktreeConfig
|
||||||
|
'
|
||||||
|
|
||||||
|
test_expect_success 'config is shared as before' '
|
||||||
|
git config this.is shared &&
|
||||||
|
test_cmp_config shared this.is &&
|
||||||
|
test_cmp_config -C wt1 shared this.is &&
|
||||||
|
test_cmp_config -C wt2 shared this.is
|
||||||
|
'
|
||||||
|
|
||||||
|
test_expect_success 'config is shared (set from another worktree)' '
|
||||||
|
git -C wt1 config that.is also-shared &&
|
||||||
|
test_cmp_config also-shared that.is &&
|
||||||
|
test_cmp_config -C wt1 also-shared that.is &&
|
||||||
|
test_cmp_config -C wt2 also-shared that.is
|
||||||
|
'
|
||||||
|
|
||||||
|
test_expect_success 'config private to main worktree' '
|
||||||
|
git config --worktree this.is for-main &&
|
||||||
|
test_cmp_config for-main this.is &&
|
||||||
|
test_cmp_config -C wt1 shared this.is &&
|
||||||
|
test_cmp_config -C wt2 shared this.is
|
||||||
|
'
|
||||||
|
|
||||||
|
test_expect_success 'config private to linked worktree' '
|
||||||
|
git -C wt1 config --worktree this.is for-wt1 &&
|
||||||
|
test_cmp_config for-main this.is &&
|
||||||
|
test_cmp_config -C wt1 for-wt1 this.is &&
|
||||||
|
test_cmp_config -C wt2 shared this.is
|
||||||
|
'
|
||||||
|
|
||||||
|
test_expect_success 'core.bare no longer for main only' '
|
||||||
|
test_config core.bare true &&
|
||||||
|
test "$(git rev-parse --is-bare-repository)" = true &&
|
||||||
|
test "$(git -C wt1 rev-parse --is-bare-repository)" = true &&
|
||||||
|
test "$(git -C wt2 rev-parse --is-bare-repository)" = true
|
||||||
|
'
|
||||||
|
|
||||||
|
test_expect_success 'per-worktree core.bare is picked up' '
|
||||||
|
git -C wt1 config --worktree core.bare true &&
|
||||||
|
test "$(git rev-parse --is-bare-repository)" = false &&
|
||||||
|
test "$(git -C wt1 rev-parse --is-bare-repository)" = true &&
|
||||||
|
test "$(git -C wt2 rev-parse --is-bare-repository)" = false
|
||||||
|
'
|
||||||
|
|
||||||
|
test_expect_success 'config.worktree no longer read without extension' '
|
||||||
|
git config --unset extensions.worktreeConfig &&
|
||||||
|
test_cmp_config shared this.is &&
|
||||||
|
test_cmp_config -C wt1 shared this.is &&
|
||||||
|
test_cmp_config -C wt2 shared this.is
|
||||||
|
'
|
||||||
|
|
||||||
|
test_done
|
|
@ -747,6 +747,29 @@ test_cmp() {
|
||||||
$GIT_TEST_CMP "$@"
|
$GIT_TEST_CMP "$@"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# Check that the given config key has the expected value.
|
||||||
|
#
|
||||||
|
# test_cmp_config [-C <dir>] <expected-value>
|
||||||
|
# [<git-config-options>...] <config-key>
|
||||||
|
#
|
||||||
|
# for example to check that the value of core.bar is foo
|
||||||
|
#
|
||||||
|
# test_cmp_config foo core.bar
|
||||||
|
#
|
||||||
|
test_cmp_config() {
|
||||||
|
local GD &&
|
||||||
|
if test "$1" = "-C"
|
||||||
|
then
|
||||||
|
shift &&
|
||||||
|
GD="-C $1" &&
|
||||||
|
shift
|
||||||
|
fi &&
|
||||||
|
printf "%s\n" "$1" >expect.config &&
|
||||||
|
shift &&
|
||||||
|
git $GD config "$@" >actual.config &&
|
||||||
|
test_cmp expect.config actual.config
|
||||||
|
}
|
||||||
|
|
||||||
# test_cmp_bin - helper to compare binary files
|
# test_cmp_bin - helper to compare binary files
|
||||||
|
|
||||||
test_cmp_bin() {
|
test_cmp_bin() {
|
||||||
|
|
Loading…
Reference in New Issue