diff --git a/plugins/glab/README.md b/plugins/glab/README.md new file mode 100644 index 000000000..a38c82dd7 --- /dev/null +++ b/plugins/glab/README.md @@ -0,0 +1,93 @@ +# glab plugin + +This plugin adds support for the [GitLab CLI (`glab`)](https://gitlab.com/gitlab-org/cli), a tool to interact with GitLab from the terminal. + +## Features + +- **Shell completion**: enables `zsh` completions for `glab` automatically if it is installed. +- **Environment setup**: loads `GITLAB_HOST` and `GITLAB_TOKEN` from `~/.netrc` if they are not already set. +- **Aliases**: provides convenient shortcuts for common GitLab CLI commands. +- **Helper functions**: adds extra functions for common GitLab workflows, including merge requests, issues, CI/CD pipelines, repositories, and releases. + +## Aliases + +| Alias | Command | Description | +|------------ |------------------ |-------------------------------- | +| `gl` | `glab` | Shortcut for `glab` | +| `glmr` | `glab mr` | Manage merge requests | +| `glissue` | `glab issue` | Manage issues | +| `glrepo` | `glab repo` | Manage repositories | +| `glci` | `glab ci` | Manage CI pipelines | +| `glprj` | `glab project` | Manage projects | +| `glrelease` | `glab release` | Manage releases | + +## Helper functions + +### Merge Requests +- `glmr-open []` + Opens a merge request in the browser. If `` is not specified, opens the current branch MR. + +- `glmr-checkout ` + Checks out the merge request branch locally. + +- `glmr-merge ` + Merges a merge request and optionally removes the source branch. + +- `glmr-list []` + Lists merge requests assigned to you. Additional `glab mr list` arguments can be passed. + +### Issues +- `glissue-new []` + Creates a new issue. If a title is provided, it is used; otherwise an interactive prompt is opened. + +- `glissue-close <issue>` + Closes the specified issue. + +- `glissue-list [<args>]` + Lists open issues assigned to you. Additional `glab issue list` arguments can be passed. + +### CI/CD +- `glci-status [<args>]` + Opens the current CI pipeline status in the browser. + +- `glci-retry <pipeline>` + Retries the specified pipeline. + +- `glci-latest` + Shows the latest pipeline. + +### Repositories +- `glrepo-clone <project>` + Clones a repository. + +- `glrepo-list [<args>]` + Lists all repositories you are a member of. + +- `glrepo-open <project>` + Opens a repository in the browser. + +- `glrepo-starred [<args>]` + Lists your starred repositories. + +### Releases +- `glrelease-create "<title>" "<tag>"` + Creates a new release with the given title and tag. + +### Search +- `glsearch <keyword>` + Searches for merge requests and issues matching the keyword. + +## Environment variables + +The plugin attempts to set the following variables if they are not already defined: + +- `GITLAB_HOST` — taken from the first `machine` entry in `~/.netrc`. +- `GITLAB_TOKEN` — the corresponding `password` from `~/.netrc`. + +## Usage + +1. Install [`glab`](https://gitlab.com/gitlab-org/cli#installation). +2. Enable the plugin in your `.zshrc`: + +```zsh +plugins=(git glab) \ No newline at end of file diff --git a/plugins/glab/glab.plugin.zsh b/plugins/glab/glab.plugin.zsh new file mode 100644 index 000000000..ad04c7bd9 --- /dev/null +++ b/plugins/glab/glab.plugin.zsh @@ -0,0 +1,145 @@ +# Oh My Zsh plugin for GitLab CLI (glab) + +# --- Environment setup --- +# Load GITLAB_HOST and GITLAB_TOKEN from ~/.netrc if not already set +if [ -z "$GITLAB_HOST" ] || [ -z "$GITLAB_TOKEN" ]; then + if [ -f "$HOME/.netrc" ]; then + __glab_machine=$(awk '/^machine/{print $2; exit}' "$HOME/.netrc") + __glab_pass=$(awk -v host="$__glab_machine" '$2==host{getline; getline; if($1=="password") print $2}' "$HOME/.netrc") + + if [ -n "$__glab_machine" ] && [ -n "$__glab_pass" ]; then + export GITLAB_HOST="$__glab_machine" + export GITLAB_TOKEN="$__glab_pass" + fi + fi +fi +unset __glab_machine __glab_pass + +# --- Completions --- +if command -v glab >/dev/null 2>&1; then + eval "$(glab completion -s zsh 2>/dev/null || true)" +fi + +# --- Aliases --- +alias gl='glab' +alias glmr='glab mr' +alias glissue='glab issue' +alias glrepo='glab repo' +alias glci='glab ci' +alias glprj='glab project' +alias glrelease='glab release' + +# --- Merge Request Helper Functions --- + +# Open a merge request in browser +glmr-open() { + glab mr view --web "$@" +} + +# Checkout a merge request branch locally +glmr-checkout() { + glab mr checkout "$1" +} + +# Merge a merge request +glmr-merge() { + glab mr merge "$1" --remove-source-branch +} + +# List merge requests assigned to me +glmr-list() { + glab mr list --assignee "@me" "$@" +} + +# --- Issue Helper Functions --- + +# Create a new issue with optional title +glissue-new() { + if [ $# -eq 0 ]; then + glab issue create + else + glab issue create -t "$*" + fi +} + +# Close an issue +glissue-close() { + glab issue close "$1" +} + +# List open issues assigned to me +glissue-list() { + glab issue list --assignee "@me" "$@" +} + +# --- CI/CD Helper Functions --- + +# Show current CI pipeline status in browser +glci-status() { + glab ci view --web "$@" +} + +# Retry a pipeline +glci-retry() { + glab ci retry "$1" +} + +# View the latest pipeline +glci-latest() { + latest_id=$(glab ci list --limit 1 --json id -q '.[0].id') + glab ci view "$latest_id" +} + +# --- Repository Helper Functions --- + +# Clone a project +glrepo-clone() { + glab repo clone "$1" +} + +# List all projects I’m a member of +glrepo-list() { + glab repo list "$@" +} + +# Open a repository in browser +glrepo-open() { + glab repo view --web "$@" +} + +# List starred projects +glrepo-starred() { + glab repo list --starred "$@" +} + +# --- Release Helper Functions --- + +# Create a release: glrelease-create "Title" "Tag" +glrelease-create() { + if [ -z "$1" ]; then + echo "Usage: glrelease-create <tag> [release name]" + return 1 + fi + local tag="$1" + local name="${2:-$1}" # Use tag as name if no name provided + glab release create "$tag" --name "$name" +} + + +# --- Search Helper Function --- + +# Search merge requests and issues +glsearch() { + echo "Merge Requests:" + glab mr list --search "$1" + echo "" + echo "Issues:" + glab issue list --search "$1" +} + +# --- Optional Auto-completion for Custom Commands --- +# Example: completion for glmr-open +_glmr_open_completion() { + _arguments "1:merge-request ID:_glab_mr" +} +compdef _glmr_open_completion glmr-open