Skip to content

Commit

Permalink
Introduce acquire-repository command
Browse files Browse the repository at this point in the history
First of all, `acquire-repository` is a former `configure-repository`
command with several improvements:
1. We aks user only about name and email. All other configurations have
to be set by default as it provides us full control on user repository.
2. Aliases are installed for local repository only. And we don't install
aliases which have to be applied only once (like init,
acquire-repository, etc.).

Second, `testtee` command is introduced along with recommendations for
its usage.
  • Loading branch information
extsoft committed Jul 26, 2019
1 parent 3d4aa45 commit 0884c5b
Show file tree
Hide file tree
Showing 14 changed files with 193 additions and 130 deletions.
10 changes: 6 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -51,12 +51,14 @@ Also, there are several optional addons which can be useful in some circumstance
#### Writing tests
1. **Use `setup()` or `teardown()`** bats methods only in the tests.
2. Use **`check` instead of bats `run`** to execute a command to be tested.
3. If `addons-fake` or `addons-git` is used, call `clean-fake` or `clean-git` within a `teardown()` method.
3. Use **`testtee`** to execute any real command within a test which should not be tested.
4. If `addons-fake` or `addons-git` is used, call `clean-fake` or `clean-git` within a `teardown()` method.

#### Assertions
- `[ "${lines[0]}" = "+ the space " ]` for a output line (index starts from 0)
- `[ "$status" -eq 2 ]` for a command status
- `[ "${#lines[@]}" -eq 0 ]` for an empty command output
- `[[ "${lines[0]}" = "+ the space " ]]` for an output line (index starts from 0)
- `[[ "$status" -eq 2 ]]` for a command status
- `[[ "${#lines[@]}" -eq 0 ]]` for a length of command output
- `[[ "${lines[@]}" =~ "exact string" ]]` for an output line within whole output

#### Test name template
Use the following test name template - `'<command args>': <describe what will be tested>` like
Expand Down
31 changes: 25 additions & 6 deletions docs/commands.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
`git elegant <command>` where `<command>` is one of

- `acquire-repository`
- `clone-repository`
- `init-repository`
- `start-work`
Expand All @@ -8,7 +9,28 @@
- `accept-work`
- `pull`
- `clear-local`
- `configure-repository`

# `acquire-repository`
Configures current repository using `git config --local`. It includes:
- defining a user identity (name and email)
- applying git settings which are required for correct work of Elegant git
- shortening Elegant git commands for `work`-related (`git elegant <command>` `=>` `git <command>`)

```bash
usage: git elegant acquire-repository
```

A sequence of original `git` commands:
```bash
git config --local user.name {provided name}
git config --local user.email {provided email}
# "|" char starts non-message lines while writing commit message
git config --local core.commentChar |
# Remove whitespaces when apply a patch
git config --local apply.whitespace fix
# Shortening Elegant git commands for work-related commands
git config --local "alias.<command>" "elegant <command>"
```

# `clone-repository`
Clones a repository into a new directory and runs its configuration.
Expand All @@ -21,7 +43,7 @@ A sequence of original `git` commands:
```bash
git clone <URL>
cd <repo root directory>
# execute commands provided by `git elegant configure-repository`
# execute commands provided by `git elegant acquire-repository`
```

# `init-repository`
Expand All @@ -34,7 +56,7 @@ usage: git elegant init-repository
A sequence of original `git` commands:
```bash
git init
# execute commands provided by `git elegant configure-repository`
# execute commands provided by `git elegant acquire-repository`
```

# `start-work`
Expand Down Expand Up @@ -107,8 +129,5 @@ Downloads new updates for a local branch.
# `clear-local`
Removes all local branches which don't have remote tracking branches.

# `configure-repository`
Defines some settings for _local_ `git config`.

# `commands`
Displays all available commands.
76 changes: 76 additions & 0 deletions libexec/git-elegant-acquire-repository
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
#!/usr/bin/env bash
#set -e

_user_name_key="user.name"
_user_name_default=$(git config "$_user_name_key" || echo '')
_user_name_message="What is your user name?"

_user_email_key="user.email"
_user_email_default=$(git config "$_user_email_key" || echo '')
_user_email_message="What is your user email?"

_core_comment_char_key="core.commentChar"
_core_comment_char_default="|"

_apply_whitespace_key="apply.whitespace"
_apply_whitespace_default="fix"

__ask_question() {
# usage: __ask_options <prefix>
# it makes available ANSWER available
message=$(eval "echo -n \$${1}_message")
echo -n "$message"
default=$(eval "echo -n \$${1}_default")
if [[ -n "$default" ]]; then echo -n " {$default}"; fi
echo -n ": "
read answer
export ANSWER=${answer:-$default}
}

__interactive-configuration() {
FUNCTIONS=$@
for f in ${FUNCTIONS[@]}; do
unset ANSWER
while [ -z "${ANSWER}" ]; do
__ask_question ${f}
if [[ -n "${ANSWER}" ]]; then
boxtee git config --local $(eval "echo -n \$${f}_key") "${ANSWER}"
fi
done
done
}

__mandatory-configuration() {
FUNCTIONS=$@
for config in ${FUNCTIONS[@]}; do
key=$(eval "echo -n \$${config}_key")
value=$(eval "echo -n \$${config}_default")
boxtee git config --local ${key} ${value}
done
}
__remove-old-aliases() {
old_aliases=($(git config --get-regexp ^alias\. | grep "elegant " | cut -f 1 -d " "))
if [[ ${#old_aliases[@]} -ne 0 ]]; then
for old in ${old_aliases[@]}; do
git config --local --unset ${old}
done
box "${#old_aliases[@]} git aliases were removed that contained 'elegant git' reference."
else
box "There are no git aliases which contain 'elegant git' reference."
fi
}

__aliases-configuration() {
for command in ${@}; do
local alias=${command}
local origin="elegant ${command}"
boxtee git config --local "alias.${alias}" "${origin}"
done
}

default() {
__interactive-configuration _user_name _user_email
__mandatory-configuration _core_comment_char _apply_whitespace
__remove-old-aliases
__aliases-configuration "pull" "clear-local" $(git elegant commands | grep work)
}
2 changes: 1 addition & 1 deletion libexec/git-elegant-clone-repository
Original file line number Diff line number Diff line change
Expand Up @@ -5,5 +5,5 @@ default() {
_error-if-empty "$1" "Cloneable URL is not set."
boxtee git clone "$1"
cd $(basename -s .git $1)
git elegant configure-repository
git elegant acquire-repository
}
2 changes: 1 addition & 1 deletion libexec/git-elegant-commands
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
set -e

default() {
echo "acquire-repository"
echo "clone-repository"
echo "init-repository"
echo "start-work"
Expand All @@ -10,6 +11,5 @@ default() {
echo "accept-work"
echo "pull"
echo "clear-local"
echo "configure-repository"
echo "commands"
}
58 changes: 0 additions & 58 deletions libexec/git-elegant-configure-repository

This file was deleted.

2 changes: 1 addition & 1 deletion libexec/git-elegant-init-repository
Original file line number Diff line number Diff line change
Expand Up @@ -3,5 +3,5 @@ set -e

default() {
boxtee git init
git elegant configure-repository
git elegant acquire-repository
}
10 changes: 10 additions & 0 deletions tests/addons-common.bash
Original file line number Diff line number Diff line change
Expand Up @@ -14,3 +14,13 @@ check(){
echo "> stdout+stderr: '$line'"
done
}

testtee() {
# Prints given command and executes it.
# It's useful as when a test is failed,
# then you can see a command in the log.
#
# usage: testtee [ags]...
echo "$(basename ${BASH_SOURCE[0]}): $@"
eval "$@"
}
29 changes: 10 additions & 19 deletions tests/addons-git.bash
Original file line number Diff line number Diff line change
Expand Up @@ -4,37 +4,28 @@ set -e
GIT_REPO_DIR="/tmp/elegant-git-repo"
FILE_TO_MODIFY=file

_gilog(){
echo "$(basename ${BASH_SOURCE[0]}): $@"
}

_ex() {
_gilog "$@"
eval "$@"
}

init-repo() {
if [ -n "$GIT_REPO_DIR" ]; then
_ex mkdir -p $GIT_REPO_DIR
_ex cd $GIT_REPO_DIR
_ex git init
_ex git config --local user.email "\"[email protected]\""
_ex git config --local user.name "\"Elegant Git\""
_ex touch $FILE_TO_MODIFY
_ex git add .
_ex git commit -m "\"Add $FILE_TO_MODIFY\""
testtee mkdir -p $GIT_REPO_DIR
testtee cd $GIT_REPO_DIR
testtee git init
testtee git config --local user.email "\"[email protected]\""
testtee git config --local user.name "\"Elegant Git\""
testtee touch $FILE_TO_MODIFY
testtee git add .
testtee git commit -m "\"Add $FILE_TO_MODIFY\""
else
exit 1
fi
}

add-unst-change(){
_ex "echo -e \"$@\" >> $FILE_TO_MODIFY"
testtee "echo -e \"$@\" >> $FILE_TO_MODIFY"
}

add-st-change(){
add-unst-change "$@"
_ex git add $FILE_TO_MODIFY
testtee git add $FILE_TO_MODIFY
}

clean-git() {
Expand Down
60 changes: 60 additions & 0 deletions tests/git-elegant-acquire-repository.bats
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
#!/usr/bin/env bats

load addons-common
load addons-read
load addons-fake
load addons-git

fake-preconditions() {
fake-pass git "config user.name" "UserName"
fake-pass git "config user.email" "UserEmail"

}
setup() {
init-repo
}

teardown() {
clean-fake
clean-git
}

@test "'acquire-repository': all configurations work as expected" {
check git-elegant acquire-repository
[[ ${#lines[@]} -eq 35 ]]
[[ "${status}" -eq 0 ]]
}

@test "'acquire-repository': interactive configuration works as expected" {
check git-elegant acquire-repository
[[ "${lines[@]}" =~ "What is your user name? {Elegant Git}: " ]]
[[ "${lines[@]}" =~ "What is your user email? {[email protected]}: " ]]
}

@test "'acquire-repository': mandatory configuration works as expected" {
check git-elegant acquire-repository
[[ "${lines[@]}" =~ "== git config --local core.commentChar | ==" ]]
[[ "${lines[@]}" =~ "== git config --local apply.whitespace fix ==" ]]
}

@test "'acquire-repository': aliases configuration works as expected" {
check git-elegant acquire-repository
[[ "${lines[@]}" =~ "== git config --local alias.start-work elegant start-work ==" ]]
[[ "${lines[@]}" =~ "== git config --local alias.save-work elegant save-work ==" ]]
[[ "${lines[@]}" =~ "== git config --local alias.deliver-work elegant deliver-work ==" ]]
[[ "${lines[@]}" =~ "== git config --local alias.accept-work elegant accept-work ==" ]]
}

@test "'acquire-repository': removing existing git aliases works as expected when aliases available" {
testtee git config --local "alias.aaa" "\"elegant aaa\""
testtee git config --local "alias.bbb" "\"elegant bbb\""
check git-elegant acquire-repository
[[ "$status" -eq 0 ]]
[[ "${lines[@]}" =~ "== 2 git aliases were removed that contained 'elegant git' reference. ==" ]]
}

@test "'acquire-repository': removing existing git aliases works as expected when aliases are absent" {
check git-elegant acquire-repository
[[ "${status}" -eq 0 ]]
[[ "${lines[@]}" =~ "== There are no git aliases which contain 'elegant git' reference. ==" ]]
}
2 changes: 1 addition & 1 deletion tests/git-elegant-clone-repository.bats
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ load addons-fake
setup() {
fake-pass git clone-repository
fake-pass git "clone https://github.com/extsoft/elegant-git.git"
fake-pass git "elegant configure-repository"
fake-pass git "elegant acquire-repository"
}

teardown() {
Expand Down
2 changes: 1 addition & 1 deletion tests/git-elegant-commands.bats
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ teardown() {

@test "'commands': print all available commands" {
COMMANDS=(
"acquire-repository"
"clone-repository"
"init-repository"
"start-work"
Expand All @@ -17,7 +18,6 @@ teardown() {
"accept-work"
"pull"
"clear-local"
"configure-repository"
"commands"
)
check git-elegant commands
Expand Down
Loading

0 comments on commit 0884c5b

Please sign in to comment.