├── .editorconfig ├── .github ├── CODEOWNERS ├── ISSUE_TEMPLATE │ ├── 01_bug_report.yml │ ├── 02_feature_request.yml │ ├── 03_codebase_improvement.yml │ ├── 04_documentation.yml │ └── config.yml ├── PULL_REQUEST_TEMPLATE.md ├── dependabot.yml ├── labeler.yml └── workflows │ ├── assign.yml │ ├── labeler.yml │ ├── lock.yml │ ├── pr-labels.yml │ ├── rebase.yml │ ├── stale.yml │ ├── sync-labels.yml │ ├── trunk-check.yml │ ├── zsh-n.yml │ └── zunit.yml ├── .trunk ├── config │ ├── .markdownlint.yaml │ └── svgo.config.js └── trunk.yaml ├── .vscode └── settings.json ├── LICENSE ├── docs ├── CONTRIBUTING.md ├── README.md ├── images │ ├── logo.png │ ├── logo.svg │ └── logo_source.tar.gz └── man │ └── zi.1 ├── lib ├── _zi ├── templates │ ├── example-script │ └── zsh.gitignore ├── zcompile └── zsh │ ├── additional.zsh │ ├── autoload.zsh │ ├── git-process-output.zsh │ ├── install.zsh │ ├── rpm2cpio.zsh │ ├── side.zsh │ └── single-line.zsh └── zi.zsh /.editorconfig: -------------------------------------------------------------------------------- 1 | # Space or Tabs? 2 | # https://stackoverflow.com/questions/35649847/objective-reasons-for-using-spaces-instead-of-tabs-for-indentation 3 | # https://stackoverflow.com/questions/12093748/how-to-use-tabs-instead-of-spaces-in-a-shell-script 4 | # https://github.com/editorconfig/editorconfig-defaults/blob/master/editorconfig-defaults.json 5 | # 6 | # 1. What happens when I press the Tab key in my text editor? 7 | # 2. What happens when I request my editor to indent one or more lines? 8 | # 3. What happens when I view a file containing U+0009 HORIZONTAL TAB characters? 9 | # 10 | # Answers: 11 | # 12 | # 1. Pressing the Tab key should indent the current line (or selected lines) one additional level. 13 | # 2. As a secondary alternative, I can also tolerate an editor that, 14 | # like Emacs, uses this key for a context-sensitive fix-my-indentation command. 15 | # 3. Indenting one or more lines should follow the reigning convention, if consensus is sufficiently strong; otherwise, 16 | # I greatly prefer 2-space indentation at each level. U+0009 characters should shift subsequent characters to the next tab stop. 17 | # 18 | # Note: VIM users should use alternate marks [[[ and ]]] as the original ones can confuse nested substitutions, e.g.: ${${${VAR}}} 19 | # 20 | # -*- mode: zsh; sh-indentation: 2; indent-tabs-mode: nil; sh-basic-offset: 2; -*- 21 | # vim: ft=zsh sw=2 ts=2 et 22 | 23 | root = true 24 | 25 | [*] 26 | charset = utf-8 27 | indent_style = space 28 | indent_size = 2 29 | insert_final_newline = true 30 | trim_trailing_whitespace = true 31 | 32 | [*.sln] 33 | indent_style = tab 34 | 35 | [*.{md,mdx,rst}] 36 | trim_trailing_whitespace = false 37 | 38 | [*.{cmd,bat}] 39 | end_of_line = crlf 40 | 41 | [*za-*] 42 | end_of_line = lf 43 | 44 | [*.{sh,bash,zsh,fish}] 45 | end_of_line = lf 46 | 47 | [Makefile] 48 | indent_style = tab 49 | indent_size = 4 50 | 51 | [*.{py,rb}] 52 | indent_size = 4 53 | 54 | [*.{go,java,scala,groovy,kotlin}] 55 | indent_style = tab 56 | indent_size = 4 57 | 58 | [*.{cs,csx,cake,vb,vbx}] 59 | # Default Severity for all .NET Code Style rules below 60 | dotnet_analyzer_diagnostic.severity = warning 61 | 62 | # https://docs.microsoft.com/dotnet/fundamentals/code-analysis/style-rules/language-rules#net-style-rules 63 | [*.{cs,csx,cake,vb,vbx}] 64 | # "this." and "Me." qualifiers 65 | dotnet_style_qualification_for_field = true:warning 66 | dotnet_style_qualification_for_property = true:warning 67 | dotnet_style_qualification_for_method = true:warning 68 | dotnet_style_qualification_for_event = true:warning 69 | # Language keywords instead of framework type names for type references 70 | dotnet_style_predefined_type_for_locals_parameters_members = true:warning 71 | dotnet_style_predefined_type_for_member_access = true:warning 72 | # Modifier preferences 73 | dotnet_style_require_accessibility_modifiers = always:warning 74 | csharp_preferred_modifier_order = public,private,protected,internal,static,extern,new,virtual,abstract,sealed,override,readonly,unsafe,volatile,async:warning 75 | visual_basic_preferred_modifier_order = Partial,Default,Private,Protected,Public,Friend,NotOverridable,Overridable,MustOverride,Overloads,Overrides,MustInherit,NotInheritable,Static,Shared,Shadows,ReadOnly,WriteOnly,Dim,Const,WithEvents,Widening,Narrowing,Custom,Async:warning 76 | dotnet_style_readonly_field = true:warning 77 | # Parentheses preferences 78 | dotnet_style_parentheses_in_arithmetic_binary_operators = always_for_clarity:warning 79 | dotnet_style_parentheses_in_relational_binary_operators = always_for_clarity:warning 80 | dotnet_style_parentheses_in_other_binary_operators = always_for_clarity:warning 81 | dotnet_style_parentheses_in_other_operators = never_if_unnecessary:warning 82 | # Expression-level preferences 83 | dotnet_style_object_initializer = true:warning 84 | dotnet_style_collection_initializer = true:warning 85 | dotnet_style_explicit_tuple_names = true:warning 86 | dotnet_style_prefer_inferred_tuple_names = true:warning 87 | dotnet_style_prefer_inferred_anonymous_type_member_names = true:warning 88 | dotnet_style_prefer_auto_properties = true:warning 89 | dotnet_style_prefer_conditional_expression_over_assignment = false:suggestion 90 | dotnet_diagnostic.IDE0045.severity = suggestion 91 | dotnet_style_prefer_conditional_expression_over_return = false:suggestion 92 | dotnet_diagnostic.IDE0046.severity = suggestion 93 | dotnet_style_prefer_compound_assignment = true:warning 94 | dotnet_style_prefer_simplified_interpolation = true:warning 95 | dotnet_style_prefer_simplified_boolean_expressions = true:warning 96 | # Null-checking preferences 97 | dotnet_style_coalesce_expression = true:warning 98 | dotnet_style_null_propagation = true:warning 99 | dotnet_style_prefer_is_null_check_over_reference_equality_method = true:warning 100 | # File header preferences 101 | # file_header_template = \n© PROJECT-AUTHOR\n 102 | # If you use StyleCop, you'll need to disable SA1636: File header copyright text should match. 103 | # dotnet_diagnostic.SA1636.severity = none 104 | # Undocumented 105 | dotnet_style_operator_placement_when_wrapping = end_of_line:warning 106 | csharp_style_prefer_null_check_over_type_check = true:warning 107 | 108 | # C# Style Rules 109 | # https://docs.microsoft.com/dotnet/fundamentals/code-analysis/style-rules/language-rules#c-style-rules 110 | [*.{cs,csx,cake}] 111 | # 'var' preferences 112 | csharp_style_var_for_built_in_types = true:warning 113 | csharp_style_var_when_type_is_apparent = true:warning 114 | csharp_style_var_elsewhere = true:warning 115 | # Expression-bodied members 116 | csharp_style_expression_bodied_methods = true:warning 117 | csharp_style_expression_bodied_constructors = true:warning 118 | csharp_style_expression_bodied_operators = true:warning 119 | csharp_style_expression_bodied_properties = true:warning 120 | csharp_style_expression_bodied_indexers = true:warning 121 | csharp_style_expression_bodied_accessors = true:warning 122 | csharp_style_expression_bodied_lambdas = true:warning 123 | csharp_style_expression_bodied_local_functions = true:warning 124 | # Pattern matching preferences 125 | csharp_style_pattern_matching_over_is_with_cast_check = true:warning 126 | csharp_style_pattern_matching_over_as_with_null_check = true:warning 127 | csharp_style_prefer_switch_expression = true:warning 128 | csharp_style_prefer_pattern_matching = true:warning 129 | csharp_style_prefer_not_pattern = true:warning 130 | # Expression-level preferences 131 | csharp_style_inlined_variable_declaration = true:warning 132 | csharp_prefer_simple_default_expression = true:warning 133 | csharp_style_pattern_local_over_anonymous_function = true:warning 134 | csharp_style_deconstructed_variable_declaration = true:warning 135 | csharp_style_prefer_index_operator = true:warning 136 | csharp_style_prefer_range_operator = true:warning 137 | csharp_style_implicit_object_creation_when_type_is_apparent = true:warning 138 | # "Null" checking preferences 139 | csharp_style_throw_expression = true:warning 140 | csharp_style_conditional_delegate_call = true:warning 141 | # Code block preferences 142 | csharp_prefer_braces = true:warning 143 | csharp_prefer_simple_using_statement = true:suggestion 144 | dotnet_diagnostic.IDE0063.severity = suggestion 145 | # 'using' directive preferences 146 | csharp_using_directive_placement = inside_namespace:warning 147 | # Modifier preferences 148 | csharp_prefer_static_local_function = true:warning 149 | 150 | # .NET Unnecessary code rules 151 | [*.{cs,csx,cake,vb,vbx}] 152 | dotnet_code_quality_unused_parameters = all:warning 153 | dotnet_remove_unnecessary_suppression_exclusions = none:warning 154 | 155 | # C# Unnecessary code rules 156 | [*.{cs,csx,cake}] 157 | csharp_style_unused_value_expression_statement_preference = discard_variable:suggestion 158 | dotnet_diagnostic.IDE0058.severity = suggestion 159 | csharp_style_unused_value_assignment_preference = discard_variable:suggestion 160 | dotnet_diagnostic.IDE0059.severity = suggestion 161 | 162 | # .NET formatting rules 163 | # https://docs.microsoft.com/dotnet/fundamentals/code-analysis/style-rules/formatting-rules#net-formatting-rules 164 | [*.{cs,csx,cake,vb,vbx}] 165 | # Organize using directives 166 | dotnet_sort_system_directives_first = true 167 | dotnet_separate_import_directive_groups = false 168 | # Dotnet namespace options 169 | dotnet_style_namespace_match_folder = true:suggestion 170 | dotnet_diagnostic.IDE0130.severity = suggestion 171 | 172 | # C# formatting rules 173 | # https://docs.microsoft.com/dotnet/fundamentals/code-analysis/style-rules/formatting-rules#c-formatting-rules 174 | [*.{cs,csx,cake}] 175 | # Newline options 176 | # https://docs.microsoft.com/dotnet/fundamentals/code-analysis/style-rules/formatting-rules#new-line-options 177 | csharp_new_line_before_open_brace = all 178 | csharp_new_line_before_else = true 179 | csharp_new_line_before_catch = true 180 | csharp_new_line_before_finally = true 181 | csharp_new_line_before_members_in_object_initializers = true 182 | csharp_new_line_before_members_in_anonymous_types = true 183 | csharp_new_line_between_query_expression_clauses = true 184 | # Indentation options 185 | # https://docs.microsoft.com/dotnet/fundamentals/code-analysis/style-rules/formatting-rules#indentation-options 186 | csharp_indent_case_contents = true 187 | csharp_indent_switch_labels = true 188 | csharp_indent_labels = no_change 189 | csharp_indent_block_contents = true 190 | csharp_indent_braces = false 191 | csharp_indent_case_contents_when_block = false 192 | # Spacing options 193 | # https://docs.microsoft.com/dotnet/fundamentals/code-analysis/style-rules/formatting-rules#spacing-options 194 | csharp_space_after_cast = false 195 | csharp_space_after_keywords_in_control_flow_statements = true 196 | csharp_space_between_parentheses = false 197 | csharp_space_before_colon_in_inheritance_clause = true 198 | csharp_space_after_colon_in_inheritance_clause = true 199 | csharp_space_around_binary_operators = before_and_after 200 | csharp_space_between_method_declaration_parameter_list_parentheses = false 201 | csharp_space_between_method_declaration_empty_parameter_list_parentheses = false 202 | csharp_space_between_method_declaration_name_and_open_parenthesis = false 203 | csharp_space_between_method_call_parameter_list_parentheses = false 204 | csharp_space_between_method_call_empty_parameter_list_parentheses = false 205 | csharp_space_between_method_call_name_and_opening_parenthesis = false 206 | csharp_space_after_comma = true 207 | csharp_space_before_comma = false 208 | csharp_space_after_dot = false 209 | csharp_space_before_dot = false 210 | csharp_space_after_semicolon_in_for_statement = true 211 | csharp_space_before_semicolon_in_for_statement = false 212 | csharp_space_around_declaration_statements = false 213 | csharp_space_before_open_square_brackets = false 214 | csharp_space_between_empty_square_brackets = false 215 | csharp_space_between_square_brackets = false 216 | # Wrap options 217 | # https://docs.microsoft.com/dotnet/fundamentals/code-analysis/style-rules/formatting-rules#wrap-options 218 | csharp_preserve_single_line_statements = false 219 | csharp_preserve_single_line_blocks = true 220 | # Namespace options 221 | # https://docs.microsoft.com/dotnet/fundamentals/code-analysis/style-rules/formatting-rules#namespace-options 222 | csharp_style_namespace_declarations = file_scoped:warning 223 | 224 | [*.{cs,csx,cake,vb,vbx}] 225 | 226 | # camel_case_style - Define the camelCase style 227 | dotnet_naming_style.camel_case_style.capitalization = camel_case 228 | # pascal_case_style - Define the PascalCase style 229 | dotnet_naming_style.pascal_case_style.capitalization = pascal_case 230 | # first_upper_style - The first character must start with an upper-case character 231 | dotnet_naming_style.first_upper_style.capitalization = first_word_upper 232 | # prefix_interface_with_i_style - Interfaces must be PascalCase and the first character of an interface must be an 'I' 233 | dotnet_naming_style.prefix_interface_with_i_style.capitalization = pascal_case 234 | dotnet_naming_style.prefix_interface_with_i_style.required_prefix = I 235 | # prefix_type_parameters_with_t_style - Generic Type Parameters must be PascalCase and the first character must be a 'T' 236 | dotnet_naming_style.prefix_type_parameters_with_t_style.capitalization = pascal_case 237 | dotnet_naming_style.prefix_type_parameters_with_t_style.required_prefix = T 238 | # disallowed_style - Anything that has this style applied is marked as disallowed 239 | dotnet_naming_style.disallowed_style.capitalization = pascal_case 240 | dotnet_naming_style.disallowed_style.required_prefix = ____RULE_VIOLATION____ 241 | dotnet_naming_style.disallowed_style.required_suffix = ____RULE_VIOLATION____ 242 | # internal_error_style - This style should never occur... if it does, it indicates a bug in file or in the parser using the file 243 | dotnet_naming_style.internal_error_style.capitalization = pascal_case 244 | dotnet_naming_style.internal_error_style.required_prefix = ____INTERNAL_ERROR____ 245 | dotnet_naming_style.internal_error_style.required_suffix = ____INTERNAL_ERROR____ 246 | 247 | # All public/protected/protected_internal constant fields must be PascalCase 248 | # https://docs.microsoft.com/dotnet/standard/design-guidelines/field 249 | dotnet_naming_symbols.public_protected_constant_fields_group.applicable_accessibilities = public, protected, protected_internal 250 | dotnet_naming_symbols.public_protected_constant_fields_group.required_modifiers = const 251 | dotnet_naming_symbols.public_protected_constant_fields_group.applicable_kinds = field 252 | dotnet_naming_rule.public_protected_constant_fields_must_be_pascal_case_rule.symbols = public_protected_constant_fields_group 253 | dotnet_naming_rule.public_protected_constant_fields_must_be_pascal_case_rule.style = pascal_case_style 254 | dotnet_naming_rule.public_protected_constant_fields_must_be_pascal_case_rule.severity = warning 255 | 256 | # All public/protected/protected_internal static readonly fields must be PascalCase 257 | # https://docs.microsoft.com/dotnet/standard/design-guidelines/field 258 | dotnet_naming_symbols.public_protected_static_readonly_fields_group.applicable_accessibilities = public, protected, protected_internal 259 | dotnet_naming_symbols.public_protected_static_readonly_fields_group.required_modifiers = static, readonly 260 | dotnet_naming_symbols.public_protected_static_readonly_fields_group.applicable_kinds = field 261 | dotnet_naming_rule.public_protected_static_readonly_fields_must_be_pascal_case_rule.symbols = public_protected_static_readonly_fields_group 262 | dotnet_naming_rule.public_protected_static_readonly_fields_must_be_pascal_case_rule.style = pascal_case_style 263 | dotnet_naming_rule.public_protected_static_readonly_fields_must_be_pascal_case_rule.severity = warning 264 | 265 | # No other public/protected/protected_internal fields are allowed 266 | # https://docs.microsoft.com/dotnet/standard/design-guidelines/field 267 | dotnet_naming_symbols.other_public_protected_fields_group.applicable_accessibilities = public, protected, protected_internal 268 | dotnet_naming_symbols.other_public_protected_fields_group.applicable_kinds = field 269 | dotnet_naming_rule.other_public_protected_fields_disallowed_rule.symbols = other_public_protected_fields_group 270 | dotnet_naming_rule.other_public_protected_fields_disallowed_rule.style = disallowed_style 271 | dotnet_naming_rule.other_public_protected_fields_disallowed_rule.severity = error 272 | 273 | # All constant fields must be PascalCase 274 | # https://github.com/DotNetAnalyzers/StyleCopAnalyzers/blob/master/documentation/SA1303.md 275 | dotnet_naming_symbols.stylecop_constant_fields_group.applicable_accessibilities = public, internal, protected_internal, protected, private_protected, private 276 | dotnet_naming_symbols.stylecop_constant_fields_group.required_modifiers = const 277 | dotnet_naming_symbols.stylecop_constant_fields_group.applicable_kinds = field 278 | dotnet_naming_rule.stylecop_constant_fields_must_be_pascal_case_rule.symbols = stylecop_constant_fields_group 279 | dotnet_naming_rule.stylecop_constant_fields_must_be_pascal_case_rule.style = pascal_case_style 280 | dotnet_naming_rule.stylecop_constant_fields_must_be_pascal_case_rule.severity = warning 281 | 282 | # All static readonly fields must be PascalCase 283 | # https://github.com/DotNetAnalyzers/StyleCopAnalyzers/blob/master/documentation/SA1311.md 284 | dotnet_naming_symbols.stylecop_static_readonly_fields_group.applicable_accessibilities = public, internal, protected_internal, protected, private_protected, private 285 | dotnet_naming_symbols.stylecop_static_readonly_fields_group.required_modifiers = static, readonly 286 | dotnet_naming_symbols.stylecop_static_readonly_fields_group.applicable_kinds = field 287 | dotnet_naming_rule.stylecop_static_readonly_fields_must_be_pascal_case_rule.symbols = stylecop_static_readonly_fields_group 288 | dotnet_naming_rule.stylecop_static_readonly_fields_must_be_pascal_case_rule.style = pascal_case_style 289 | dotnet_naming_rule.stylecop_static_readonly_fields_must_be_pascal_case_rule.severity = warning 290 | 291 | # No non-private instance fields are allowed 292 | # https://github.com/DotNetAnalyzers/StyleCopAnalyzers/blob/master/documentation/SA1401.md 293 | dotnet_naming_symbols.stylecop_fields_must_be_private_group.applicable_accessibilities = public, internal, protected_internal, protected, private_protected 294 | dotnet_naming_symbols.stylecop_fields_must_be_private_group.applicable_kinds = field 295 | dotnet_naming_rule.stylecop_instance_fields_must_be_private_rule.symbols = stylecop_fields_must_be_private_group 296 | dotnet_naming_rule.stylecop_instance_fields_must_be_private_rule.style = disallowed_style 297 | dotnet_naming_rule.stylecop_instance_fields_must_be_private_rule.severity = error 298 | 299 | # Private fields must be camelCase 300 | # https://github.com/DotNetAnalyzers/StyleCopAnalyzers/blob/master/documentation/SA1306.md 301 | dotnet_naming_symbols.stylecop_private_fields_group.applicable_accessibilities = private 302 | dotnet_naming_symbols.stylecop_private_fields_group.applicable_kinds = field 303 | dotnet_naming_rule.stylecop_private_fields_must_be_camel_case_rule.symbols = stylecop_private_fields_group 304 | dotnet_naming_rule.stylecop_private_fields_must_be_camel_case_rule.style = camel_case_style 305 | dotnet_naming_rule.stylecop_private_fields_must_be_camel_case_rule.severity = warning 306 | 307 | # Local variables must be camelCase 308 | # https://github.com/DotNetAnalyzers/StyleCopAnalyzers/blob/master/documentation/SA1312.md 309 | dotnet_naming_symbols.stylecop_local_fields_group.applicable_accessibilities = local 310 | dotnet_naming_symbols.stylecop_local_fields_group.applicable_kinds = local 311 | dotnet_naming_rule.stylecop_local_fields_must_be_camel_case_rule.symbols = stylecop_local_fields_group 312 | dotnet_naming_rule.stylecop_local_fields_must_be_camel_case_rule.style = camel_case_style 313 | dotnet_naming_rule.stylecop_local_fields_must_be_camel_case_rule.severity = silent 314 | 315 | # This rule should never fire. However, it's included for at least two purposes: 316 | # First, it helps to understand, reason about, and root-case certain types of issues, such as bugs in .editorconfig parsers. 317 | # Second, it helps to raise immediate awareness if a new field type is added (as occurred recently in C#). 318 | dotnet_naming_symbols.sanity_check_uncovered_field_case_group.applicable_accessibilities = * 319 | dotnet_naming_symbols.sanity_check_uncovered_field_case_group.applicable_kinds = field 320 | dotnet_naming_rule.sanity_check_uncovered_field_case_rule.symbols = sanity_check_uncovered_field_case_group 321 | dotnet_naming_rule.sanity_check_uncovered_field_case_rule.style = internal_error_style 322 | dotnet_naming_rule.sanity_check_uncovered_field_case_rule.severity = error 323 | 324 | # All of the following must be PascalCase: 325 | # - Namespaces 326 | # https://docs.microsoft.com/dotnet/standard/design-guidelines/names-of-namespaces 327 | # https://github.com/DotNetAnalyzers/StyleCopAnalyzers/blob/master/documentation/SA1300.md 328 | # - Classes and Enumerations 329 | # https://docs.microsoft.com/dotnet/standard/design-guidelines/names-of-classes-structs-and-interfaces 330 | # https://github.com/DotNetAnalyzers/StyleCopAnalyzers/blob/master/documentation/SA1300.md 331 | # - Delegates 332 | # https://docs.microsoft.com/dotnet/standard/design-guidelines/names-of-classes-structs-and-interfaces#names-of-common-types 333 | # - Constructors, Properties, Events, Methods 334 | # https://docs.microsoft.com/dotnet/standard/design-guidelines/names-of-type-members 335 | dotnet_naming_symbols.element_group.applicable_kinds = namespace, class, enum, struct, delegate, event, method, property 336 | dotnet_naming_rule.element_rule.symbols = element_group 337 | dotnet_naming_rule.element_rule.style = pascal_case_style 338 | dotnet_naming_rule.element_rule.severity = warning 339 | 340 | # Interfaces use PascalCase and are prefixed with uppercase 'I' 341 | # https://docs.microsoft.com/dotnet/standard/design-guidelines/names-of-classes-structs-and-interfaces 342 | dotnet_naming_symbols.interface_group.applicable_kinds = interface 343 | dotnet_naming_rule.interface_rule.symbols = interface_group 344 | dotnet_naming_rule.interface_rule.style = prefix_interface_with_i_style 345 | dotnet_naming_rule.interface_rule.severity = warning 346 | 347 | # Generics Type Parameters use PascalCase and are prefixed with uppercase 'T' 348 | # https://docs.microsoft.com/dotnet/standard/design-guidelines/names-of-classes-structs-and-interfaces 349 | dotnet_naming_symbols.type_parameter_group.applicable_kinds = type_parameter 350 | dotnet_naming_rule.type_parameter_rule.symbols = type_parameter_group 351 | dotnet_naming_rule.type_parameter_rule.style = prefix_type_parameters_with_t_style 352 | dotnet_naming_rule.type_parameter_rule.severity = warning 353 | 354 | # Function parameters use camelCase 355 | # https://docs.microsoft.com/dotnet/standard/design-guidelines/naming-parameters 356 | dotnet_naming_symbols.parameters_group.applicable_kinds = parameter 357 | dotnet_naming_rule.parameters_rule.symbols = parameters_group 358 | dotnet_naming_rule.parameters_rule.style = camel_case_style 359 | dotnet_naming_rule.parameters_rule.severity = warning 360 | -------------------------------------------------------------------------------- /.github/CODEOWNERS: -------------------------------------------------------------------------------- 1 | * @z-shell/tsc 2 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/01_bug_report.yml: -------------------------------------------------------------------------------- 1 | name: "🐞 Bug report" 2 | description: File a bug report 3 | title: "[bug]: " 4 | labels: ["bug 🐞", "triage 📑"] 5 | assignees: ["ss-o"] 6 | body: 7 | - type: markdown 8 | attributes: 9 | value: | 10 | First off, thanks for taking the time to contribute! Contributions are what make the open-source community such an amazing place to learn, inspire, and create. Any contributions you make will benefit everybody else and are greatly appreciated. 11 | - type: input 12 | id: environment 13 | attributes: 14 | label: Environment 15 | description: > 16 | Please describe your environment in as much detail as possible. Otherwise, we may not be able to reproduce the issue. 17 | placeholder: > 18 | Example: 19 | print "Device: $VENDOR | $OSTYPE | $CPUTYPE" 20 | print "Shell: $SHELL | $ZSH_ARGZERO | $ZSH_PATCHLEVEL" 21 | print "Zi: $(git -C $ZI[BIN_DIR] rev-parse HEAD)" 22 | validations: 23 | required: true 24 | - type: textarea 25 | id: repro 26 | attributes: 27 | label: Reproduction steps 28 | description: "How do you trigger this bug? Please walk us through it step by step." 29 | value: | 30 | 1. 31 | 2. 32 | 3. 33 | 4. 34 | 5. 35 | ... 36 | render: bash 37 | validations: 38 | required: true 39 | - type: textarea 40 | id: expected 41 | attributes: 42 | label: Expected behavior 43 | description: "Please describe the expected behavior" 44 | value: | 45 | 1. 46 | 2. 47 | 3. 48 | 4. 49 | 5. 50 | ... 51 | render: bash 52 | validations: 53 | required: true 54 | - type: textarea 55 | id: current 56 | attributes: 57 | label: Current behavior 58 | description: "Please describe how the bug manifests" 59 | value: | 60 | 1. 61 | 2. 62 | 3. 63 | 4. 64 | 5. 65 | ... 66 | render: bash 67 | validations: 68 | required: true 69 | - type: textarea 70 | id: code-snippet 71 | attributes: 72 | label: Code snippet 73 | description: "Please insert your zshrc or just a short code snippet in concern." 74 | validations: 75 | required: true 76 | - type: textarea 77 | id: additional 78 | attributes: 79 | label: Additional information 80 | description: "List any other information that is relevant to your issue. For reports and stats run `zi analytics`" 81 | validations: 82 | required: true 83 | - type: checkboxes 84 | attributes: 85 | label: Self-service 86 | description: | 87 | If you feel like you could contribute to this issue, please check the box below. This would tell us and other people looking for contributions that someone's working on it. 88 | If you do check this box, please send a pull request within 7 days so we can still delegate this to someone else. 89 | options: 90 | - label: I'd be willing to address this documentation request myself. 91 | - type: checkboxes 92 | attributes: 93 | label: Have you read the Contributing Guidelines? 94 | options: 95 | - label: I have read the [Contributing Guidelines](https://github.com/z-shell/community/blob/main/docs/CONTRIBUTING_GUIDELINES.md). 96 | required: true 97 | - type: checkboxes 98 | attributes: 99 | label: Are you familiar with the Contributor Covenant Code of Conduct? 100 | options: 101 | - label: I have read the [Contributor Covenant Code of Conduct](https://github.com/z-shell/zi/blob/main/docs/CODE_OF_CONDUCT.md). 102 | required: true 103 | - type: input 104 | id: contact 105 | attributes: 106 | label: Contact Details 107 | description: How can we get in touch with you if we need more info? 108 | placeholder: ex. email@example.com 109 | validations: 110 | required: false 111 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/02_feature_request.yml: -------------------------------------------------------------------------------- 1 | name: "💡 Feature request" 2 | description: Suggest an idea for this project 3 | title: "[feat]: " 4 | labels: ["feature-request 💡"] 5 | assignees: ["ss-o"] 6 | body: 7 | - type: markdown 8 | attributes: 9 | value: | 10 | First off, thanks for taking the time to contribute! Contributions are what make the open-source community such an amazing place to learn, inspire, and create. Any contributions you make will benefit everybody else and are greatly appreciated. 11 | - type: input 12 | id: description 13 | attributes: 14 | label: Feature description 15 | description: A clear and concise description of what the feature request is. Please include if your feature request is related to a problem 16 | validations: 17 | required: true 18 | - type: textarea 19 | id: code-snippet 20 | attributes: 21 | label: Related Code 22 | description: "If you can illustrate the bug or feature request with an example, please provide it here" 23 | validations: 24 | required: false 25 | - type: textarea 26 | id: additional 27 | attributes: 28 | label: Additional Context 29 | description: 30 | "List any other information that is relevant to your issue. Stack traces, related issues, suggestions on how to add, use case, Stack Overflow links, forum links, screenshots, OS if applicable, 31 | etc." 32 | validations: 33 | required: false 34 | - type: checkboxes 35 | attributes: 36 | label: Self-service 37 | description: | 38 | If you feel like you could contribute to this issue, please check the box below. This would tell us and other people looking for contributions that someone's working on it. 39 | If you do check this box, please send a pull request within 7 days so we can still delegate this to someone else. 40 | options: 41 | - label: I'd be willing to address this documentation request myself. 42 | - type: checkboxes 43 | attributes: 44 | label: Have you read the Contributing Guidelines? 45 | options: 46 | - label: I have read the [Contributing Guidelines](https://github.com/z-shell/community/blob/main/docs/CONTRIBUTING_GUIDELINES.md). 47 | required: true 48 | - type: checkboxes 49 | attributes: 50 | label: Are you familiar with the Contributor Covenant Code of Conduct? 51 | options: 52 | - label: I have read the [Contributor Covenant Code of Conduct](https://github.com/z-shell/zi/blob/main/docs/CODE_OF_CONDUCT.md). 53 | required: true 54 | - type: input 55 | id: contact 56 | attributes: 57 | label: Contact Details 58 | description: How can we get in touch with you if we need more info? 59 | placeholder: ex. email@example.com 60 | validations: 61 | required: false 62 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/03_codebase_improvement.yml: -------------------------------------------------------------------------------- 1 | name: "✨ Codebase improvement" 2 | description: Suggest a better solution for algorithms, annexes, packages, development tools, etc. 3 | title: "[dev]: " 4 | labels: ["enhancement ✨"] 5 | assignees: ["ss-o"] 6 | body: 7 | - type: textarea 8 | id: enhancement 9 | attributes: 10 | label: "Your feedback for the existing codebase" 11 | validations: 12 | required: false 13 | - type: markdown 14 | attributes: 15 | value: | 16 | First off, thanks for taking the time to contribute! 17 | Contributions are what make the open-source community such an amazing place to learn, inspire, and create. 18 | Any contributions you make will benefit everybody else and are greatly appreciated. 19 | - type: checkboxes 20 | attributes: 21 | label: Self-service 22 | description: | 23 | If you feel like you could contribute to this issue, please check the box below. This would tell us and other people looking for contributions that someone's working on it. 24 | If you do check this box, please send a pull request within 7 days so we can still delegate this to someone else. 25 | options: 26 | - label: I'd be willing to address this documentation request myself. 27 | - type: checkboxes 28 | attributes: 29 | label: Have you read the Contributing Guidelines? 30 | options: 31 | - label: I have read the [Contributing Guidelines](https://github.com/z-shell/community/blob/main/docs/CONTRIBUTING_GUIDELINES.md). 32 | required: true 33 | - type: checkboxes 34 | attributes: 35 | label: Are you familiar with the Contributor Covenant Code of Conduct? 36 | options: 37 | - label: I have read the [Contributor Covenant Code of Conduct](https://github.com/z-shell/zi/blob/main/docs/CODE_OF_CONDUCT.md). 38 | required: true 39 | - type: input 40 | id: contact 41 | attributes: 42 | label: Contact Details 43 | description: How can we get in touch with you if we need more info? 44 | placeholder: ex. email@example.com 45 | validations: 46 | required: false 47 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/04_documentation.yml: -------------------------------------------------------------------------------- 1 | name: "📚 Documentation" 2 | description: The issue request for changes in documentation 3 | title: "[docs]: " 4 | labels: ["documentation 📝"] 5 | assignees: ["ss-o"] 6 | body: 7 | - type: markdown 8 | attributes: 9 | value: | 10 | This template is strictly used for documentation requests, including: 11 | 12 | - Elaborating on a particular topic; 13 | - Updating external links; 14 | - Anything else that doesn't require touching the codebase itself. 15 | 16 | If you followed the documentation but things don't work, take some time to consider if it's the documentation or the code that's wrong. In the latter, prefer using the "bug" template. 17 | 18 | You may proceed directly to sending a pull request without filing this issue, and we can improve your work. 19 | If you think some of the requirements above are not met, or if you are not able to contribute yourself, the issue is still welcomed. 20 | 21 | - type: textarea 22 | id: request-info 23 | attributes: 24 | label: Description 25 | description: Tell us, what can be done better or a clear and concise description of what the issue is. 26 | validations: 27 | required: true 28 | - type: dropdown 29 | id: ecosystem 30 | attributes: 31 | label: Select the area that is associated with this issue. 32 | multiple: true 33 | options: 34 | - ZI (this repository) 35 | - Annexes 36 | - Plugins 37 | - Packages 38 | - Other 39 | - type: checkboxes 40 | attributes: 41 | label: Self-service 42 | description: | 43 | If you feel like you could contribute to this issue, please check the box below. This would tell us and other people looking for contributions that someone's working on it. 44 | If you do check this box, please send a pull request within 7 days so we can still delegate this to someone else. 45 | options: 46 | - label: I'd be willing to address this documentation request myself. 47 | - type: checkboxes 48 | attributes: 49 | label: Have you read the Contributing Guidelines? 50 | options: 51 | - label: I have read the [Contributing Guidelines](https://github.com/z-shell/community/blob/main/docs/CONTRIBUTING_GUIDELINES.md). 52 | required: true 53 | - type: checkboxes 54 | attributes: 55 | label: Are you familiar with the Contributor Covenant Code of Conduct? 56 | options: 57 | - label: I have read the [Contributor Covenant Code of Conduct](https://github.com/z-shell/zi/blob/main/docs/CODE_OF_CONDUCT.md). 58 | required: true 59 | - type: input 60 | id: contact 61 | attributes: 62 | label: Contact Details 63 | description: How can we get in touch with you if we need more info? 64 | placeholder: ex. email@example.com 65 | validations: 66 | required: false 67 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/config.yml: -------------------------------------------------------------------------------- 1 | --- 2 | blank_issues_enabled: false 3 | contact_links: 4 | - name: Wiki 5 | url: https://wiki.zshell.dev 6 | about: Knowledge base 7 | - name: Discussions 8 | url: https://discussions.zshell.dev 9 | about: Please ask and answer questions here 10 | - name: Matrix 11 | url: https://matrix.zshell.dev 12 | about: An open network for secure, decentralized communication 13 | - name: Slack 14 | url: https://join.slack.com/t/z-shell/shared_invite/zt-16twpopd2-p08ROUeT2aGZ5njJwysawA 15 | about: Workspace to collaborate, ask and answer questions 16 | - name: Crowdin 17 | url: https://translate.zshell.dev 18 | about: Translation and localization management 19 | -------------------------------------------------------------------------------- /.github/PULL_REQUEST_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | # Pull request template 2 | 3 | 4 | 5 | ## Type of changes 6 | 7 | 8 | 9 | - [ ] CI 10 | - [ ] Bugfix 11 | - [ ] Feature 12 | - [ ] Generic maintenance tasks 13 | - [ ] Documentation content changes 14 | - [ ] Code style update (formatting, renaming) 15 | - [ ] Refactoring (no functional changes, no URL changes) 16 | - [ ] Improving the performance of the project (not introducing new features) 17 | - [ ] Other (please describe): 18 | 19 | Issue Number: N/A 20 | 21 | ## What is the current behavior? 22 | 23 | 24 | 25 | ## What is the new behavior? 26 | 27 | 28 | 29 | ### Does this introduce a breaking change? 30 | 31 | - [ ] Yes 32 | - [ ] No 33 | 34 | 35 | 36 | ## Other information 37 | 38 | 39 | 40 | N/A 41 | -------------------------------------------------------------------------------- /.github/dependabot.yml: -------------------------------------------------------------------------------- 1 | # https://help.github.com/github/administering-a-repository/configuration-options-for-dependency-updates 2 | 3 | version: 2 4 | updates: 5 | - package-ecosystem: "github-actions" 6 | directory: "/" 7 | schedule: 8 | interval: "daily" 9 | -------------------------------------------------------------------------------- /.github/labeler.yml: -------------------------------------------------------------------------------- 1 | documentation 📝: 2 | - "docs/*.md" 3 | - "docs/man/*" 4 | enhancement ✨: 5 | - "*.zsh" 6 | - "lib/**" 7 | maintenance 📈: 8 | - ".github/CODEOWNERS" 9 | - ".github/*.yml" 10 | - ".github/*.json" 11 | - ".vscode/*" 12 | - ".trunk/**" 13 | ci 🤖: 14 | - ".github/workflows/*.yml" 15 | -------------------------------------------------------------------------------- /.github/workflows/assign.yml: -------------------------------------------------------------------------------- 1 | --- 2 | name: "❇️ Assign" 3 | 4 | on: 5 | issues: 6 | types: 7 | - opened 8 | pull_request: 9 | types: 10 | - labeled 11 | 12 | jobs: 13 | assign: 14 | runs-on: ubuntu-latest 15 | steps: 16 | - uses: actions/add-to-project@main 17 | with: 18 | project-url: https://github.com/orgs/z-shell/projects/4 19 | github-token: ${{ secrets.GITHUB_TOKEN }} 20 | labeled: bug 🐞, triage 📑, annex 🌀, plugin ⚙️, package 📦, feature-request 💡 21 | label-operator: OR 22 | -------------------------------------------------------------------------------- /.github/workflows/labeler.yml: -------------------------------------------------------------------------------- 1 | --- 2 | name: 🔖 Pull Request Labeler 3 | on: 4 | pull_request_target: 5 | 6 | permissions: 7 | contents: read 8 | pull-requests: write 9 | 10 | jobs: 11 | triage: 12 | runs-on: ubuntu-latest 13 | steps: 14 | - uses: actions/labeler@v4 15 | with: 16 | repo-token: "${{ secrets.GITHUB_TOKEN }}" 17 | sync-labels: false 18 | -------------------------------------------------------------------------------- /.github/workflows/lock.yml: -------------------------------------------------------------------------------- 1 | --- 2 | name: 🔒 Lock closed issues and PRs 3 | 4 | on: 5 | schedule: 6 | - cron: "30 2 * * *" 7 | 8 | permissions: 9 | issues: write 10 | pull-requests: write 11 | 12 | concurrency: 13 | group: lock 14 | 15 | jobs: 16 | lock: 17 | name: 🔐 Lock closed issues and PRs 18 | runs-on: ubuntu-latest 19 | steps: 20 | - uses: dessant/lock-threads@v4 21 | with: 22 | github-token: ${{ github.token }} 23 | issue-inactive-days: "30" 24 | issue-lock-reason: "" 25 | issue-comment: > 26 | Issue closed and locked due to lack of activity. 27 | 28 | If you encounter this same issue, please open a new issue and refer to this closed one. 29 | 30 | pr-inactive-days: "7" 31 | pr-lock-reason: "" 32 | pr-comment: > 33 | Pull Request closed and locked due to lack of activity. 34 | 35 | If you'd like to build on this closed PR, you can clone it using this method: https://stackoverflow.com/a/14969986 36 | 37 | Then open a new PR, referencing this closed PR in your message. 38 | -------------------------------------------------------------------------------- /.github/workflows/pr-labels.yml: -------------------------------------------------------------------------------- 1 | --- 2 | name: 🏷️ Verify PR Labels 3 | 4 | on: 5 | workflow_dispatch: 6 | pull_request_target: 7 | types: ["opened", "labeled", "unlabeled", "synchronize"] 8 | 9 | jobs: 10 | pr_labels: 11 | name: 🏭 Verify PR Labels 12 | runs-on: ubuntu-latest 13 | steps: 14 | - name: 🏷 Verify PR has a valid label 15 | uses: jesusvasquez333/verify-pr-label-action@v1.4.0 16 | with: 17 | github-token: "${{ secrets.GITHUB_TOKEN }}" 18 | pull-request-number: "${{ github.event.pull_request.number }}" 19 | valid-labels: > 20 | "breaking-change 💥, bug 🐞, i18n 🌐, l10n 🗣, documentation 📝, enhancement ✨, security 🛡️, refactor ♻️, performance 🚀, new-feature 🎉, triage 📑, maintenance 📈, ci 🤖, fix ⚡, 21 | dependencies 📦, submodules ⚙️, annex 🌀, plugin ⚙️, package 📦" 22 | invalid-labels: > 23 | "Q&A ✍️, stale 👻, no-stale 🔒, locked ‼️, resolved ☑️, feature-request 💡, help-wanted, beginner-friendly 💕, priority-low 🔖, invalid ⚠️" 24 | disable-reviews: true 25 | -------------------------------------------------------------------------------- /.github/workflows/rebase.yml: -------------------------------------------------------------------------------- 1 | --- 2 | name: "🔁 Rebase" 3 | on: 4 | issue_comment: 5 | types: [created] 6 | jobs: 7 | rebase: 8 | runs-on: ubuntu-latest 9 | name: 🔁 Rebase 10 | # Automate with comments: /autosquash, /rebase 11 | if: >- 12 | github.event.issue.pull_request != '' && ( 13 | contains(github.event.comment.body, '/rebase') || 14 | contains(github.event.comment.body, '/autosquash') 15 | ) 16 | steps: 17 | - name: ⤵️ Check out code from GitHub 18 | uses: actions/checkout@v3 19 | with: 20 | token: ${{ secrets.GITHUB_TOKEN }} 21 | fetch-depth: 0 # otherwise, you will fail to push refs to dest repo 22 | - name: 🔁 Rebase 23 | uses: z-shell/.github/actions/rebase@main 24 | with: 25 | autosquash: ${{ contains(github.event.comment.body, '/autosquash') || contains(github.event.comment.body, '/rebase-autosquash') }} 26 | env: 27 | GITHUB_TOKEN: ${{ secrets.GH_PAT }} 28 | -------------------------------------------------------------------------------- /.github/workflows/stale.yml: -------------------------------------------------------------------------------- 1 | --- 2 | name: 🧹 Clean up stale issues and PRs 3 | 4 | on: 5 | schedule: 6 | - cron: "0 8 * * *" 7 | workflow_dispatch: 8 | 9 | jobs: 10 | stale: 11 | name: 🧹 Clean up stale issues and PRs 12 | runs-on: ubuntu-latest 13 | steps: 14 | - name: 🚀 Run stale 15 | uses: actions/stale@v7 16 | with: 17 | repo-token: ${{ secrets.GITHUB_TOKEN }} 18 | days-before-stale: 30 19 | days-before-close: 7 20 | remove-stale-when-updated: true 21 | stale-issue-label: "stale 👻" 22 | exempt-issue-labels: "no-stale 🔒,help-wanted 👥" 23 | stale-issue-message: > 24 | There hasn't been any activity on this issue recently, and in order to prioritize active issues, it will be marked as stale. 25 | 26 | Please make sure to update to the latest version and check if that solves the issue. Let us know if that works for you by leaving a 👍 27 | 28 | Because this issue is marked as stale, it will be closed and locked in 7 days if no further activity occurs. 29 | 30 | Thank you for your contributions! 31 | stale-pr-label: "stale 👻" 32 | exempt-pr-labels: "no-stale 🔒" 33 | stale-pr-message: > 34 | There hasn't been any activity on this pull request recently, and in order to prioritize active work, it has been marked as stale. 35 | 36 | This PR will be closed and locked in 7 days if no further activity occurs. 37 | 38 | Thank you for your contributions! 39 | -------------------------------------------------------------------------------- /.github/workflows/sync-labels.yml: -------------------------------------------------------------------------------- 1 | --- 2 | name: "♻️ Sync Labels" 3 | on: 4 | schedule: 5 | - cron: "22 2 * * 2" 6 | workflow_dispatch: 7 | jobs: 8 | labels: 9 | name: "♻️ Sync labels" 10 | uses: z-shell/.github/.github/workflows/sync-labels.yml@main 11 | -------------------------------------------------------------------------------- /.github/workflows/trunk-check.yml: -------------------------------------------------------------------------------- 1 | --- 2 | name: "⭕ Trunk" 3 | on: 4 | push: 5 | branches: [main] 6 | tags: ["v*.*.*"] 7 | pull_request: 8 | types: [opened, synchronize] 9 | schedule: 10 | - cron: "0 05 * * 5" 11 | workflow_dispatch: {} 12 | 13 | jobs: 14 | check: 15 | if: github.event.schedule != '0 05 * * 5' 16 | name: "⚡" 17 | uses: z-shell/.github/.github/workflows/trunk.yml@main 18 | upload: 19 | if: github.event.schedule == '0 05 * * 5' 20 | name: "🆙" 21 | uses: z-shell/.github/.github/workflows/trunk.yml@main 22 | secrets: 23 | trunk-token: ${{ secrets.TRUNK_TOKEN }} 24 | -------------------------------------------------------------------------------- /.github/workflows/zsh-n.yml: -------------------------------------------------------------------------------- 1 | --- 2 | name: "✅ Zsh" 3 | on: 4 | push: 5 | tags: ["v*.*.*"] 6 | branches: 7 | - main 8 | - next 9 | paths: 10 | - "zi.zsh" 11 | - "lib/**" 12 | pull_request: 13 | paths: 14 | - "zi.zsh" 15 | - "lib/**" 16 | workflow_run: 17 | workflows: 18 | - "⭕ Trunk" 19 | types: 20 | - completed 21 | branches: [main] 22 | workflow_dispatch: {} 23 | 24 | jobs: 25 | zsh-matrix: 26 | runs-on: ubuntu-latest 27 | outputs: 28 | matrix: ${{ steps.set-matrix.outputs.matrix }} 29 | steps: 30 | - name: ⤵️ Check out code from GitHub 31 | uses: actions/checkout@v3 32 | - name: "Set matrix output" 33 | id: set-matrix 34 | run: | 35 | MATRIX="$(find . -type d -name 'doc' -prune -o -type f \( -iname '*.zsh' -o -iname '_zi' \) -print | jq -ncR '{"include": [{"file": inputs}]}')" 36 | echo "MATRIX=${MATRIX}" >&2 37 | echo "matrix=${MATRIX}" >> $GITHUB_OUTPUT 38 | 39 | zsh-n: 40 | runs-on: ubuntu-latest 41 | needs: zsh-matrix 42 | strategy: 43 | fail-fast: false 44 | matrix: ${{ fromJSON(needs.zsh-matrix.outputs.matrix) }} 45 | steps: 46 | - name: ⤵️ Check out code from GitHub 47 | uses: actions/checkout@v3 48 | - name: "⚡ Install dependencies" 49 | run: sudo apt update && sudo apt-get install -yq zsh 50 | - name: "⚡ zsh -n: ${{ matrix.file }}" 51 | env: 52 | ZSH_FILE: ${{ matrix.file }} 53 | run: | 54 | zsh -n "${ZSH_FILE}" 55 | - name: "⚡ zcompile ${{ matrix.file }}" 56 | env: 57 | ZSH_FILE: ${{ matrix.file }} 58 | run: | 59 | zsh -fc "zcompile ${ZSH_FILE}"; rc=$? 60 | ls -al "${ZSH_FILE}.zwc"; exit "$rc" 61 | -------------------------------------------------------------------------------- /.github/workflows/zunit.yml: -------------------------------------------------------------------------------- 1 | --- 2 | name: "♾️ ZUnit" 3 | 4 | on: 5 | push: 6 | branches: [main] 7 | tags: ["v*.*.*"] 8 | paths: 9 | - "lib/zsh/install.zsh" 10 | - "lib/zsh/autoload.zsh" 11 | pull_request: 12 | branches: [main] 13 | paths: 14 | - "lib/zsh/install.zsh" 15 | - "lib/zsh/autoload.zsh" 16 | workflow_dispatch: {} 17 | 18 | jobs: 19 | zunit-matrix: 20 | runs-on: ubuntu-latest 21 | outputs: 22 | matrix: ${{ steps.set-matrix.outputs.matrix }} 23 | steps: 24 | - uses: actions/checkout@v3 25 | with: 26 | token: ${{ secrets.GITHUB_TOKEN }} 27 | repository: "z-shell/zd" 28 | - name: "Set matrix output" 29 | id: set-matrix 30 | run: | 31 | builtin cd docker/tests 32 | MATRIX="$(ls -1 *.zunit | sed 's/.zunit$//' | jq -ncR '{"include": [{"file": inputs}]}')" 33 | echo "MATRIX=${MATRIX}" >&2 34 | echo "matrix=${MATRIX}" >> $GITHUB_OUTPUT 35 | 36 | zunit: 37 | runs-on: ubuntu-latest 38 | needs: zunit-matrix 39 | strategy: 40 | fail-fast: false 41 | matrix: ${{ fromJSON(needs.zunit-matrix.outputs.matrix) }} 42 | steps: 43 | - name: Login to GitHub Container Registry 44 | uses: docker/login-action@v3 45 | with: 46 | registry: ghcr.io 47 | username: ${{ github.repository_owner }} 48 | password: ${{ secrets.GITHUB_TOKEN }} 49 | - uses: actions/checkout@v3 50 | with: 51 | repository: "z-shell/zd" 52 | token: ${{ secrets.GITHUB_TOKEN }} 53 | - run: command git clone --branch main --depth 1 -- https://github.com/z-shell/zi.git zi 54 | - name: "⚡ Install dependencies" 55 | run: | 56 | sudo apt-get update && sudo apt-get install -yq zsh 57 | mkdir bin 58 | curl -fsSL https://raw.githubusercontent.com/zdharma/revolver/v0.2.4/revolver > bin/revolver 59 | curl -fsSL https://raw.githubusercontent.com/zdharma/color/d8f91ab5fcfceb623ae45d3333ad0e543775549c/color.zsh > bin/color 60 | git clone https://github.com/zdharma/zunit.git zunit.git 61 | cd zunit.git 62 | ./build.zsh 63 | cd .. 64 | mv ./zunit.git/zunit bin 65 | chmod u+x bin/{color,revolver,zunit} 66 | - name: "⚡ ZUnit: ${{ matrix.file }}" 67 | env: 68 | ZUNIT_TEST: ${{ matrix.file }} 69 | run: | 70 | echo "⚡ $ZUNIT_TEST" >&2 71 | export PATH="$PWD/bin:$PATH" 72 | export TERM=xterm-256color 73 | zunit --tap --verbose "docker/tests/${ZUNIT_TEST}.zunit" 74 | -------------------------------------------------------------------------------- /.trunk/config/.markdownlint.yaml: -------------------------------------------------------------------------------- 1 | # Autoformatter friendly markdownlint config (all formatting rules disabled) 2 | default: true 3 | blank_lines: false 4 | bullet: false 5 | html: false 6 | indentation: false 7 | line_length: false 8 | spaces: false 9 | url: false 10 | whitespace: false 11 | MD041: false 12 | -------------------------------------------------------------------------------- /.trunk/config/svgo.config.js: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | plugins: [ 3 | { 4 | name: "preset-default", 5 | params: { 6 | overrides: { 7 | removeViewBox: false, // https://github.com/svg/svgo/issues/1128 8 | sortAttrs: true, 9 | removeOffCanvasPaths: true, 10 | }, 11 | }, 12 | }, 13 | ], 14 | }; 15 | -------------------------------------------------------------------------------- /.trunk/trunk.yaml: -------------------------------------------------------------------------------- 1 | version: 0.1 2 | cli: 3 | version: 1.1.0 4 | plugins: 5 | sources: 6 | - id: trunk 7 | ref: v0.0.6 8 | uri: https://github.com/trunk-io/plugins 9 | lint: 10 | enabled: 11 | - actionlint@1.6.22 12 | - svgo@3.0.2 13 | - gitleaks@8.15.1 14 | - markdownlint@0.32.2 15 | - git-diff-check 16 | - prettier@2.7.1 17 | runtimes: 18 | enabled: 19 | - go@1.18.3 20 | - node@16.14.2 21 | actions: 22 | enabled: 23 | - trunk-announce 24 | - trunk-check-pre-push 25 | - trunk-fmt-pre-commit 26 | - trunk-upgrade-available 27 | -------------------------------------------------------------------------------- /.vscode/settings.json: -------------------------------------------------------------------------------- 1 | { 2 | "conventionalCommits.scopes": [ 3 | "maintenance", 4 | "library", 5 | "feature", 6 | "refactor", 7 | "style", 8 | "chore", 9 | "revert", 10 | "docs", 11 | "deps", 12 | "misc", 13 | "build", 14 | "perf", 15 | "test", 16 | "fix", 17 | "ci" 18 | ], 19 | "shellformat.useEditorConfig": true, 20 | "todo-tree.general.tags": [ 21 | "BUG", 22 | "HACK", 23 | "FIXME", 24 | "TODO", 25 | "NOTE", 26 | "[ ]", 27 | "[x]" 28 | ], 29 | "todo-tree.highlights.customHighlight": { 30 | "TODO": { 31 | "icon": "tools", 32 | "type": "line", 33 | "fontWeight": "bold", 34 | "iconColour": "#2fca2f", 35 | "background": "#00ff00", 36 | "opacity": 0.1 37 | }, 38 | "BUG": { 39 | "icon": "bug", 40 | "type": "line", 41 | "fontWeight": "bold", 42 | "iconColour": "#ff0000", 43 | "background": "#ff0000", 44 | "opacity": 0.2 45 | }, 46 | "HACK": { 47 | "icon": "tools" 48 | }, 49 | "FIXME": { 50 | "icon": "flame", 51 | "type": "line", 52 | "fontWeight": "bold", 53 | "iconColour": "#ffff00", 54 | "background": "#ffff00", 55 | "opacity": 0.1 56 | }, 57 | "NOTE": { 58 | "icon": "info", 59 | "type": "line", 60 | "fontWeight": "bold", 61 | "iconColour": "#0077ff", 62 | "background": "#0077ff", 63 | "opacity": 0.1 64 | } 65 | }, 66 | "files.associations": { 67 | "*za-*": "shellscript" 68 | }, 69 | "shellcheck.ignorePatterns": { 70 | "**/*.xonshrc": true, 71 | "**/*.xsh": true, 72 | "**/*.zsh": true, 73 | "**/*.zshrc": true, 74 | "**/zshrc": true, 75 | "**/*.zprofile": true, 76 | "**/zprofile": true, 77 | "**/*.zlogin": true, 78 | "**/zlogin": true, 79 | "**/*.zlogout": true, 80 | "**/zlogout": true, 81 | "**/*.zshenv": true, 82 | "**/zshenv": true, 83 | "**/*.zsh-theme": true, 84 | "**/*za-*": true 85 | } 86 | } 87 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2021, Salvydas Lukosius & Z-Shell ZI Community 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /docs/CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contributing Guidelines 2 | 3 | When contributing, please first [discuss](https://github.com/z-shell/zi/issues/new/choose) the change you wish. The 4 | [contributing guidelines](https://github.com/z-shell/community/blob/main/docs/CONTRIBUTING_GUIDELINES.md) and other relevant documents can be found in the 5 | [community](https://github.com/z-shell/community) repository. 6 | 7 | Please note we have a [code of conduct](CODE_OF_CONDUCT.md), please follow it in all your interactions with the project. 8 | -------------------------------------------------------------------------------- /docs/README.md: -------------------------------------------------------------------------------- 1 | 2 | 3 | 26 | 27 | 28 | 38 | 39 | 40 | 66 | 67 | 68 | 73 | 74 | 75 | 83 | 84 |
4 |

5 | 6 | ❮ Zi ❯ Logo 8 | Zi ❯ 9 |

10 |

11 | 🧙‍♂️ 🪄 A Swiss Army Knife for Zsh - 12 | Unix Shell ✨ 13 |

14 |
15 | 《 17 | Report an issue 18 | · 19 | 《 21 | Request a Feature 》 22 | · 23 | 《 Ask a Question 》 24 |
25 |
29 |
30 | 《💡》Search Wiki 31 | 《⚡️》 Install 32 | 《💜》Join 34 | 35 | 《🌐》Localize 36 |
37 |
41 |
42 | 43 | Zi Matrix 44 | 45 | 46 | Zi Gitter Matrix 47 | 48 | 49 | 50 | 51 | 52 | Version 53 | 54 | 55 | Project License 56 | 57 | 58 | VIM 59 | 60 | 61 | Visual Studio Code 63 | 64 |
65 |
69 |
70 | 71 |
72 |
76 |
77 | 79 | 81 |
82 |
85 |
86 |

🎯 Roadmap

87 |
88 | Generally, new features will be introduced as a component to improve performance and compatibility and not to 89 | force, but to allow the user decide and 90 | choose the features. Let us know what should be improved and 91 | maintained with a ⭐ on features you like and use:

92 |
93 | 107 | 130 |
131 |

💞 Contributing

132 |
133 | Contributions are what make the open-source community such an amazing place to learn, inspire, and create. 134 | Any contributions you make will benefit everybody else and greatly appreciated and our 135 | target support each other. 136 |
137 |
138 | Please read our contribution 139 | guidelines 140 | before you start. Thank you for being involved! 141 |
142 |
143 |

🆙 Project assistance

144 |
If you want to say thank you or/and support the active development, add a GitHub Star to the project, and follow the 146 | Z-Shell organization. 147 |

148 |
Write interesting articles about the project on: 149 | Dev.to, Medium.com, 150 | Hacker News, 151 | Reddit, Twitter, or your blog. 152 | Participate in the community by showing interest 154 | in the project, as it may bring us together, then great things may happen. If you want but are not confident 155 | about participating - do not hesitate to contact us so we can discuss the situation 👍. 156 |
157 |
158 |

🛡️ Security

159 |
160 | - Z-Shell Zi follows good practices of security, but 100% security cannot be assured.
161 |
162 | - Z-Shell Zi is provided "as is" without any warranty. Use at your 163 | own risk. 164 |
165 |
166 | - For more information and to report security issues, please refer to our 167 | security 168 | documentation. 169 |
170 |
171 |

ℹ️ Acknowledgements

172 |
173 | The Z-Shell organization was created to recover the 174 | Zdharma organization which was deleted by the owner for an unknown 175 | reason. It took a lot of time and effort for all those who liked the project and were depending on it don't 176 | want to depend on an unreliable source. 177 |
178 |
179 | 180 | Zi 181 | , formerly known as zplugin, zinit, is an open-source 182 | community project released under the 183 | MIT License. 184 |
185 |
186 |

🥇 Authors & contributors

187 |
188 | Check the list of authors and contributors in this 189 | repository and all other repositories under the 190 | Z-Shell organization. We will include 191 | all showing interest or dedicating their time to taking part. 192 |
193 |
194 |

⭐ Credits

195 |
196 | 197 | Trunk 199 | 200 | 201 | Crowdin | Agile localization for tech companies 204 | 205 | 207 | DigitalOcean Referral Badge 209 | 210 | 211 | Cloudflare 213 | 214 |
215 | -------------------------------------------------------------------------------- /docs/images/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/z-shell/zi/07203d4a810f81e1457714f261e3397494dd3cba/docs/images/logo.png -------------------------------------------------------------------------------- /docs/images/logo.svg: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /docs/images/logo_source.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/z-shell/zi/07203d4a810f81e1457714f261e3397494dd3cba/docs/images/logo_source.tar.gz -------------------------------------------------------------------------------- /docs/man/zi.1: -------------------------------------------------------------------------------- 1 | .TH "" "" "November 2021" "" "" 2 | News 3 | .P 4 | \fBTable of Contents\fR \fIgenerated with \fBDocToc\fI \fI\(lahttps://github.com/thlorenz/doctoc\(ra\fI\fR 5 | .RS 0 6 | .IP \(bu 4 7 | \fBNews\fR \fI(News)\fR 8 | .IP \(bu 4 9 | \fBZI\fR \fI(ZI)\fR 10 | .IP \(bu 4 11 | \fBZI Wiki\fR \fI(ZI Wiki)\fR 12 | .IP \(bu 4 13 | \fBInstallation\fR \fI(Installation)\fR 14 | .RS 4 15 | .IP \(bu 4 16 | \fBOption 1 - Automatic Installation (Recommended)\fR \fI(Option 1 - Automatic Installation (Recommended))\fR 17 | .IP \(bu 4 18 | \fBOption 2 - Manual Installation\fR \fI(Option 2 - Manual Installation)\fR 19 | .RE 0 20 | 21 | .IP \(bu 4 22 | \fBUsage\fR \fI(Usage)\fR 23 | .RS 4 24 | .IP \(bu 4 25 | \fBIntroduction\fR \fI(Introduction)\fR 26 | .IP \(bu 4 27 | \fBExample Usage\fR \fI(Example Usage)\fR 28 | .IP \(bu 4 29 | \fBIce Modifiers\fR \fI(Ice Modifiers)\fR 30 | .IP \(bu 4 31 | \fBZI Commands\fR \fI(ZI Commands)\fR 32 | .IP \(bu 4 33 | \fBUpdating ZI and Plugins\fR \fI(Updating ZI and Plugins)\fR 34 | .IP \(bu 4 35 | \fBUsing Oh My Zsh Themes\fR \fI(Using Oh My Zsh Themes)\fR 36 | .RE 0 37 | 38 | .IP \(bu 4 39 | \fBCompletions\fR \fI(Completions)\fR 40 | .RS 4 41 | .IP \(bu 4 42 | \fBCalling \fBcompinit\fR Without Turbo Mode\fR \fI(Calling compinit Without Turbo Mode)\fR 43 | .IP \(bu 4 44 | \fBCalling \fBcompinit\fR With Turbo Mode\fR \fI(Calling compinit With Turbo Mode)\fR 45 | .IP \(bu 4 46 | \fBIgnoring Compdefs\fR \fI(Ignoring Compdefs)\fR 47 | .IP \(bu 4 48 | \fBDisabling System-Wide \fBcompinit\fR Call (Ubuntu)\fR \fI(Disabling System-Wide compinit Call (Ubuntu))\fR 49 | .RE 0 50 | 51 | .IP \(bu 4 52 | \fBZI Module\fR \fI(ZI Module)\fR 53 | .RS 4 54 | .IP \(bu 4 55 | \fBMotivation\fR \fI(Motivation)\fR 56 | .IP \(bu 4 57 | \fBInstallation\fR \fI(Installation)\fR 58 | .IP \(bu 4 59 | \fBMeasuring Time of \fBsource\fRs\fR \fI(Measuring Time of sources)\fR 60 | .IP \(bu 4 61 | \fBDebugging\fR \fI(Debugging)\fR 62 | .RE 0 63 | 64 | .IP \(bu 4 65 | \fBHints and Tips\fR \fI(Hints and Tips)\fR 66 | .RS 4 67 | .IP \(bu 4 68 | \fBCustomizing Paths\fR \fI(Customizing Paths)\fR 69 | .IP \(bu 4 70 | \fBNon-GitHub (Local) Plugins\fR \fI(Non-GitHub (Local) Plugins)\fR 71 | .IP \(bu 4 72 | \fBExtending Git\fR \fI(Extending Git)\fR 73 | .IP \(bu 4 74 | \fBPreinstalling Plugins\fR \fI(Preinstalling Plugins)\fR 75 | .RE 0 76 | 77 | .IP \(bu 4 78 | \fBGetting Help and Community\fR \fI(Getting Help and Community)\fR 79 | .RE 0 80 | 81 | .RS 0 82 | .IP \(bu 4 83 | 12-10-2019 84 | .RS 4 85 | .IP \(bu 4 86 | Special value for the \fBid-as''\fR ice \[en] \fBauto\fR. It sets the plugin/snippet ID automatically to the last component of its spec, e.g.: 87 | .P 88 | .RS 2 89 | .nf 90 | zi ice id-as"auto" 91 | zi load robobenklein/zinc 92 | .fi 93 | .RE 94 | .P 95 | will load the plugin as \fBid-as'zinc'\fR. 96 | .RE 0 97 | 98 | .IP \(bu 4 99 | 14-09-2019 100 | .RS 4 101 | .IP \(bu 4 102 | There's a Vim plugin which extends syntax highlighting of zsh scripts with coloring of the ZI commands. \fBProject homepage\fR \fI\(lahttps://github.com/zi/zi-vim-syntax\(ra\fR. 103 | .RE 0 104 | 105 | .IP \(bu 4 106 | 13-09-2019 107 | .RS 4 108 | .IP \(bu 4 109 | New ice \fBaliases\fR which loads plugin with the aliases mechanism enabled. Use for plugins that define \fBand use\fR aliases in their scripts. 110 | .RE 0 111 | 112 | .IP \(bu 4 113 | 11-09-2019 114 | .RS 4 115 | .IP \(bu 4 116 | New ice-mods \fBsh\fR,\fBbash\fR,\fBksh\fR,\fBcsh\fR that load plugins (and snippets) with the \fBsticky emulation\fR feature of Zsh \[en] all functions defined within the plugin will automatically switch to the desired emulation mode before executing and switch back thereafter. In other words it is now possible to load e.g. bash plugins with ZI, provided that the emulation level done by Zsh is sufficient, e.g.: 117 | .P 118 | .RS 2 119 | .nf 120 | zi ice bash pick"bash_it.sh" \[rs] 121 | atinit"BASH_IT=${ZPLGM\[lB]PLUGINS_DIR\[rB]}/Bash-it---bash-it" \[rs] 122 | atclone"yes n | ./install.sh" 123 | zi load Bash-it/bash-it 124 | .fi 125 | .RE 126 | .P 127 | This script loads correctly thanks to the emulation, however it isn't functional because it uses \fBtype -t …\fR to check if a function exists. 128 | .RE 0 129 | 130 | .IP \(bu 4 131 | 10-09-2019 132 | .RS 4 133 | .IP \(bu 4 134 | A new ice-mod \fBreset''\fR that ivokes \fBgit reset --hard\fR (or the provided command) before \fBgit pull\fR and \fBatpull''\fR ice. It can be used it to implement altering (i.e. patching) of the plugin's files inside the \fBatpull''\fR ice \[en] \fBgit\fR will report no conflicts when doing \fBpull\fR, and the changes can be then again introduced by the \fBatpull''\fR ice. 135 | .IP \(bu 4 136 | Three new ZI annexes (i.e. \fBextensions\fR \fI\(lahttp://z-shell.github.io/zi/wiki/Annexes/\(ra\fR): 137 | .RS 4 138 | .IP \(bu 4 139 | \fBz-a-man\fR \fI\(lahttps://github.com/z-shell/z-a-man\(ra\fR 140 | .P 141 | Generates man pages and code-documentation man pages from plugin's README.md and source files (the code documentation is obtained from \fBZshelldoc\fR \fI\(lahttps://github.com/z-shell/zshelldoc\(ra\fR). 142 | .IP \(bu 4 143 | \fBz-a-test\fR \fI\(lahttps://github.com/z-shell/z-a-test\(ra\fR 144 | .P 145 | Runs tests (if detected \fBtest\fR target in a \fBMakefile\fR or any \fB*.zunit\fR files) on plugin installation and non-empty update. 146 | .IP \(bu 4 147 | \fBz-a-patch-dl\fR \fI\(lahttps://github.com/z-shell/z-a-patch-dl\(ra\fR 148 | .P 149 | Allows easy download and applying of patches, to e.g. aid building a binary program equipped in the plugin. 150 | .RE 0 151 | 152 | .IP \(bu 4 153 | A new variable is being recognized by the installation script: \fB$ZPLG_BIN_DIR_NAME\fR. It configures the directory within \fB$ZPLG_HOME\fR to which ZI should be cloned. 154 | .RE 0 155 | 156 | .IP \(bu 4 157 | 09-08-2019 158 | .RS 4 159 | .IP \(bu 4 160 | A new ice-mod \fBwrap-track''\fR which gets \fB;\fR-separated list of functions that are to be tracked \fBonce\fR when executing. In other words you can extend the tracking beyond the moment of loading of a plugin. 161 | .IP \(bu 4 162 | The unloading of Zle widgets is now more smart \[en] it takes into account the chains of plugins that can overload the Zle widgets, and solves the interactions that result out of it. 163 | .RE 0 164 | 165 | .IP \(bu 4 166 | 29-07-2019 167 | .RS 4 168 | .IP \(bu 4 169 | \fBdelete\fR now supports following options: 170 | .RS 4 171 | .IP \(bu 4 172 | \fB--all\fR \[en] deletes all plugins and snippets (a purge, similar to \fBrm -rf 173 | ${ZPLGM\[lB]PLUGINS_DIR\[rB]} ${ZPLGM\[lB]SNIPPETS_DIR\[rB]}\fR) 174 | .IP \(bu 4 175 | \fB--clean\fR \[en] deletes only plugins and snippets that are \fBcurrently not loaded\fR in the current session. 176 | .RE 0 177 | 178 | .RE 0 179 | 180 | .IP \(bu 4 181 | 09-07-2019 182 | .RS 4 183 | .IP \(bu 4 184 | ZI can now have \fBits own plugins\fR, called \fBz-plugins\fR! Check out an example but fully functional z-plugin \fBz-shell/z-a-submods\fR \fI\(lahttps://github.com/z-shell/z-a-submods\(ra\fR and a document that explains on how to implement your own z-plugin (\fBhere\fR \fI\(la../../wiki/Z-PLUGINS\(ra\fR). 185 | .RE 0 186 | 187 | .IP \(bu 4 188 | 08-07-2019 189 | .RS 4 190 | .IP \(bu 4 191 | You can now do \fBzi ice wait ...\fR and it will work as \fBzi ice wait'0' ...\fR :) I.e. when there's no value to the \fBwait''\fR ice then a value of \fB0\fR is being substituted. 192 | .RE 0 193 | 194 | .IP \(bu 4 195 | 02-07-2019 196 | .RS 4 197 | .IP \(bu 4 198 | \fBCooperation of Fast-Syntax-Highlighting and ZI\fR \fI\(lahttps://asciinema.org/a/254630\(ra\fR \[en] a new precise highlighting for ZI in F-Sy-H. 199 | .RE 0 200 | 201 | .IP \(bu 4 202 | 01-07-2019 203 | .RS 4 204 | .IP \(bu 4 205 | \fBatclone''\fR, \fBatpull''\fR & \fBmake''\fR get run in the same subshell, thus an e.g. export done in \fBatclone''\fR will be visible during the \fBmake\fR. 206 | .RE 0 207 | 208 | .IP \(bu 4 209 | 26-06-2019 210 | .RS 4 211 | .IP \(bu 4 212 | \fBnotify''\fR contents gets evaluated, i.e. can contain active code like \fB$(tail -1 213 | /var/log/messages)\fR, etc. 214 | .RE 0 215 | 216 | .IP \(bu 4 217 | 23-06-2019 218 | .RS 4 219 | .IP \(bu 4 220 | New ice mod \fBsubscribe''\fR/\fBon-update-of''\fR which works like the \fBwait''\fR ice-mod, i.e. defers loading of a plugin, but it \fBlooks at modification time of the given file(s)\fR, and when it changes, it then triggers loading of the plugin/snippet: 221 | .P 222 | .RS 2 223 | .nf 224 | % zi ice on-update-of'{~/files-*,/tmp/files-*}' lucid \[rs] 225 | atload"echo I have been loaded" \[rs] 226 | notify"Yes that's true :)" 227 | % zi load z-shell/null 228 | % touch ~/files-1 229 | The plugin has been loaded 230 | % 231 | Yes that's true :) 232 | .fi 233 | .RE 234 | .P 235 | The plugin/snippet will be sourced as many times as the file gets updated. 236 | .RE 0 237 | 238 | .IP \(bu 4 239 | 22-06-2019 240 | .RS 4 241 | .IP \(bu 4 242 | New ice mod \fBreset-prompt\fR that will issue \fBzle .reset-prompt\fR after loading the plugin or snippet, causing the prompt to be recomputed. Useful with themes & Turbo mode. 243 | .IP \(bu 4 244 | New ice-mod \fBnotify''\fR which will cause to display an under-prompt notification when the plugin or snippet gets loaded. E.g.: 245 | .P 246 | .RS 2 247 | .nf 248 | % zi ice wait"0" lucid notify"z-shell/null has been loaded" 249 | % zi light z-shell/null 250 | % 251 | z-shell/null has been loaded 252 | .fi 253 | .RE 254 | .P 255 | In case of problems with the loading a warning message will be output: 256 | .P 257 | .RS 2 258 | .nf 259 | % zi ice notify atload'return 7' 260 | % zi light z-shell/null 261 | % 262 | notify: Plugin not loaded / loaded with problem, the return code: 7 263 | .fi 264 | .RE 265 | .P 266 | Refer to \fBIce Modifiers\fR \fI(Ice Modifiers)\fR section for a complete description. 267 | .RE 0 268 | 269 | .IP \(bu 4 270 | 29-05-2019 271 | .RS 4 272 | .IP \(bu 4 273 | Turbo mode, i.e. the \fBwait''\fR ice-mode now supports a suffix \[en] the letter \fBa\fR, \fBb\fR or \fBc\fR. The meaning is illustrated by the following example: 274 | .P 275 | .RS 2 276 | .nf 277 | zi ice wait"0b" as"command" pick"wd.sh" atinit"echo Firing 1" lucid 278 | zi light mfaerevaag/wd 279 | zi ice wait"0a" as"command" pick"wd.sh" atinit"echo Firing 2" lucid 280 | zi light mfaerevaag/wd 281 | 282 | # The output 283 | Firing 2 284 | Firing 1 285 | .fi 286 | .RE 287 | .P 288 | As it can be seen, the second plugin has been loaded first. That's because there are now three sub-slots (the \fBa\fR, \fBb\fR and \fBc\fR) in which the plugin/snippet loadings can be put into. Plugins from the same time-slot with suffix \fBa\fR will be loaded before plugins with suffix \fBb\fR, etc. 289 | .P 290 | In other words, instead of \fBwait'1'\fR you can enter \fBwait'1a'\fR, \fBwait'1b'\fR and \fBwait'1c'\fR \[en] to this way \fBimpose order\fR on the loadings \fBregardless of the order of \fBzi\fB commands\fR. 291 | .RE 0 292 | 293 | .RE 0 294 | 295 | .P 296 | To see the full history check \fBthe changelog\fR \fI\(laCHANGELOG.md\(ra\fR. 297 | .SH "ZI" 298 | .P 299 | ZI is an elastic and fast Zshell plugin manager that will allow you to install everything from GitHub and other sites. 300 | .P 301 | ZI is currently the only plugin manager out there that has Turbo mode which yields \fB50-73% faster Zsh startup!\fR 302 | .P 303 | ZI gives \fBreports\fR from plugin load describing what aliases, functions, bindkeys, Zle widgets, zstyles, completions, variables, \fBPATH\fR and \fBFPATH\fR elements a plugin has set up. 304 | .P 305 | Supported is \fBunloading\fR of plugin and ability to list, (un)install and selectively disable, enable plugin's completions. 306 | .P 307 | The system does not use \fB$FPATH\fR, loading multiple plugins doesn't clutter \fB$FPATH\fR with the same number of entries (e.g. \fB10\fR). Code is immune to \fBKSH_ARRAYS\fR. Completion management functionality is provided to allow user to call \fBcompinit\fR only once in \fB.zshrc\fR. 308 | .SH "ZI WIKI" 309 | .P 310 | The information in this README is complemented by the \fBZI wiki\fR \fI\(lahttp://z-shell.github.io/zi/wiki/\(ra\fR. The README is an introductory overview of ZI while the wiki gives a complete and in-depth information with examples. Make sure to read it to get the most out of ZI. 311 | .SH "INSTALLATION" 312 | .SS "Option 1 - Automatic Installation (Recommended)" 313 | .P 314 | The easiest way to install ZI is to execute: 315 | .P 316 | .RS 2 317 | .nf 318 | sh -c "$(curl -fsSL https://raw.githubusercontent.com/z-shell/zi/main/lib/install.sh)" 319 | .fi 320 | .RE 321 | .P 322 | This will install ZI in \fB~/.zi/bin\fR. \fB.zshrc\fR will be updated with three lines of code that will be added to the bottom. The lines will be sourcing \fBzi.zsh\fR and setting up completion for command \fBzi\fR. After installing and reloading the shell compile ZI with \fBzi self-update\fR. 323 | .SS "Option 2 - Manual Installation" 324 | .P 325 | To manually install ZI clone the repo to e.g. \fB~/.zi/bin\fR: 326 | .P 327 | .RS 2 328 | .nf 329 | mkdir ~/.zi 330 | git clone https://github.com/z-shell/zi.git ~/.zi/bin 331 | .fi 332 | .RE 333 | .P 334 | and source it from \fB.zshrc\fR (above compinit): 335 | .P 336 | .RS 2 337 | .nf 338 | source ~/.zi/bin/zi.zsh 339 | .fi 340 | .RE 341 | .P 342 | If you place the \fBsource\fR below \fBcompinit\fR, then add those two lines after the \fBsource\fR: 343 | .P 344 | .RS 2 345 | .nf 346 | autoload -Uz _zi 347 | (( ${+_comps} )) && _comps\[lB]zi\[rB]=_zi 348 | .fi 349 | .RE 350 | .P 351 | Various paths can be customized, see section \fBCustomizing Paths\fR \fI(Customizing Paths)\fR. 352 | .P 353 | After installing and reloading the shell compile ZI with \fBzi self-update\fR. 354 | .SH "USAGE" 355 | .SS "Introduction" 356 | .P 357 | \fBClick here to read the introduction to ZI\fR \fI\(lahttp://z-shell.github.io/zi/wiki/INTRODUCTION/\(ra\fR. It explains basic usage and some of the more unique features of ZI such as the Turbo mode. If you're new to ZI we highly recommend you read it at least once. 358 | .SS "Example Usage" 359 | .P 360 | After installing ZI you can start adding some actions (load some plugins) to \fB~/.zshrc\fR, at bottom. Some examples: 361 | .P 362 | .RS 2 363 | .nf 364 | # Two regular plugins loaded without tracking. 365 | zi light zsh-users/zsh-autosuggestions 366 | zi light z-shell/F-Sy-H 367 | 368 | # Plugin history-search-multi-word loaded with tracking. 369 | zi load z-shell/history-search-multi-word 370 | 371 | # Load the pure theme, with zsh-async library that's bundled with it. 372 | zi ice pick"async.zsh" src"pure.zsh" 373 | zi light sindresorhus/pure 374 | 375 | # Binary release in archive, from GitHub-releases page. 376 | # After automatic unpacking it provides program "fzf". 377 | zi ice from"gh-r" as"program" 378 | zi load junegunn/fzf-bin 379 | 380 | # One other binary release, it needs renaming from `docker-compose-Linux-x86_64`. 381 | # This is done by ice-mod `mv'{from} -> {to}'. There are multiple packages per 382 | # single version, for OS X, Linux and Windows \[en] so ice-mod `bpick' is used to 383 | # select Linux package \[en] in this case this is actually not needed, ZI will 384 | # grep operating system name and architecture automatically when there's no `bpick'. 385 | zi ice from"gh-r" as"program" mv"docker* -> docker-compose" bpick"*linux*" 386 | zi load docker/compose 387 | 388 | # Vim repository on GitHub \[en] a typical source code that needs compilation \[en] ZI 389 | # can manage it for you if you like, run `./configure` and other `make`, etc. stuff. 390 | # Ice-mod `pick` selects a binary program to add to $PATH. You could also install the 391 | # package under the path $ZPFX, see: http://z-shell.github.io/zi/wiki/Compiling-programs 392 | zi ice as"program" atclone"rm -f src/auto/config.cache; ./configure" \[rs] 393 | atpull"%atclone" make pick"src/vim" 394 | zi light vim/vim 395 | 396 | # Scripts that are built at install (there's single default make target, "install", 397 | # and it constructs scripts by `cat'ing a few files). The make'' ice could also be: 398 | # `make"install PREFIX=$ZPFX"`, if "install" wouldn't be the only, default target. 399 | zi ice as"program" pick"$ZPFX/bin/git-*" make"PREFIX=$ZPFX" 400 | zi light tj/git-extras 401 | 402 | # Handle completions without loading any plugin, see "clist" command. 403 | # This one is to be ran just once, in interactive session. 404 | zi creinstall %HOME/my_completions 405 | .fi 406 | .RE 407 | .P 408 | .RS 2 409 | .nf 410 | # For GNU ls (the binaries can be gls, gdircolors, e.g. on OS X when installing the 411 | # coreutils package from Homebrew; you can also use https://github.com/eza-community/eza) 412 | zi ice atclone"dircolors -b LS_COLORS > c.zsh" atpull'%atclone' pick"c.zsh" nocompile'!' 413 | zi light trapd00r/LS_COLORS 414 | .fi 415 | .RE 416 | .P 417 | \fBYou can see an extended explanation of LS_COLORS in the wiki.\fR \fI\(lahttp://z-shell.github.io/zi/wiki/LS_COLORS-explanation/\(ra\fR 418 | .P 419 | .RS 2 420 | .nf 421 | # make'!...' -> run make before atclone & atpull 422 | zi ice as"program" make'!' atclone'./direnv hook zsh > zhook.zsh' atpull'%atclone' src"zhook.zsh" 423 | zi light direnv/direnv 424 | .fi 425 | .RE 426 | .P 427 | \fBYou can see an extended explanation of direnv in the wiki.\fR \fI\(lahttp://z-shell.github.io/zi/wiki/Direnv-explanation/\(ra\fR 428 | .P 429 | If you're interested in more examples then check out the \fBzi-configs repository\fR \fI\(lahttps://github.com/z-shell/zi-configs\(ra\fR where users have uploaded their \fB~/.zshrc\fR and ZI configurations. Feel free to \fBsubmit\fR \fI\(lahttps://github.com/z-shell/zi-configs/issues/new?template=request-to-add-zshrc-to-the-zi-configs-repo.md\(ra\fR your \fB~/.zshrc\fR there if it contains ZI commands. 430 | .P 431 | You can also check out the \fBGallery of ZI Invocations\fR \fI\(lahttp://z-shell.github.io/zi/wiki/GALLERY/\(ra\fR for some additional examples. 432 | .SS "Ice Modifiers" 433 | .P 434 | Following \fBice\fR modifiers are to be passed to \fBzi ice ...\fR to obtain described effects. The word \fBice\fR means something that's added (like ice to a drink) \[en] and in ZI it means adding modifier to a next \fBzi\fR command, and also something that's temporary because it melts \[en] and this means that the modification will last only for a \fBsingle\fR next \fBzi\fR command. 435 | .P 436 | Some Ice-modifiers are highlighted and clicking on them will take you to the appropriate wiki page for an extended explanation. 437 | .P 438 | You may safely assume a given ice works with both plugins and snippets unless explicitly stated otherwise. 439 | .SS "Cloning Options" 440 | .TS 441 | tab(@); 442 | cb cb 443 | c l . 444 | Modifier@Description 445 | \fBproto\fR@ Change protocol to \fBgit\fR,\fBftp\fR,\fBftps\fR,\fBssh\fR, \fBrsync\fR, etc. Default is \fBhttps\fR. \fBDoes not work with snippets.\fR 446 | \fBfrom\fR@ Clone plugin from given site. Supported are \fBfrom"github"\fR (default), \fB..."github-rel"\fR, \fB..."gitlab"\fR, \fB..."bitbucket"\fR, \fB..."notabug"\fR (short names: \fBgh\fR, \fBgh-r\fR, \fBgl\fR, \fBbb\fR, \fBnb\fR). Can also be a full domain name (e.g. for GitHub enterprise). \fBDoes not work with snippets.\fR 447 | \fBver\fR@ Used with \fBfrom"gh-r"\fR (i.e. downloading a binary release, e.g. for use with \fBas"program"\fR) \[en] selects which version to download. Default is latest, can also be explicitly \fBver"latest"\fR. Works also with regular plugins, checkouts e.g. \fBver"abranch"\fR, i.e. a specific version. \fBDoes not work with snippets.\fR 448 | \fBbpick\fR@ Used to select which release from GitHub Releases to download, e.g. \fBzi ice from"gh-r" as"program" bpick"*Darwin*"; zi load docker/compose\fR. \fBDoes not work with snippets.\fR 449 | \fBdepth\fR@ Pass \fB--depth\fR to \fBgit\fR, i.e. limit how much of history to download. \fBDoes not work with snippets.\fR 450 | \fBcloneopts\fR@ Pass the contents of \fBcloneopts\fR to \fBgit clone\fR. Defaults to \fB--recursive\fR i.e. Change cloning options. \fBDoes not work with snippets.\fR 451 | \fBsvn\fR@ Use Subversion for downloading snippet. GitHub supports \fBSVN\fR protocol, this allows to clone subdirectories as snippets, e.g. \fBzi ice svn; zi snippet OMZ::plugins/git\fR. Other ice \fBpick\fR can be used to select file to source (default are: \fB*.plugin.zsh\fR, \fBinit.zsh\fR, \fB*.zsh-theme\fR). \fBDoes not work with plugins.\fR 452 | .TE 453 | .SS "Selection of Files (To Source, …)" 454 | .TS 455 | tab(@); 456 | cb cb 457 | c l . 458 | Modifier@Description 459 | \fB\fB\fBpick\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/Sourcing-multiple-files/\(ra\fR@ Select the file to source, or the file to set as command (when using \fBsnippet --command\fR or the ice \fBas"program"\fR); it is a pattern, alphabetically first matched file is being chosen; e.g. \fBzi ice pick"*.plugin.zsh"; zi load …\fR. 460 | \fB\fB\fBsrc\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/Sourcing-multiple-files\(ra\fR@ Specify additional file to source after sourcing main file or after setting up command (via \fBas"program"\fR). It is not a pattern but a plain file name. 461 | \fB\fB\fBmultisrc\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/Sourcing-multiple-files\(ra\fR@ Allows to specify multiple files for sourcing, enumerated with spaces as the separators (e.g. \fBmultisrc'misc.zsh grep.zsh'\fR) and also using brace-expansion syntax (e.g. \fBmultisrc'{misc,grep}.zsh'\fR). Supports patterns. 462 | .TE 463 | .SS "Conditional Loading" 464 | .TS 465 | tab(@); 466 | cb cb 467 | c l . 468 | Modifier@Description 469 | \fB\fB\fBwait\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/Example-wait-conditions\(ra\fR@ Postpone loading a plugin or snippet. For \fBwait'1'\fR, loading is done \fB1\fR second after prompt. For \fBwait'\[lB]\[lB] ... \[rB]\[rB]'\fR, \fBwait'(( ... ))'\fR, loading is done when given condition is meet. For \fBwait'!...'\fR, prompt is reset after load. Zsh can start 73% faster thanks to postponed loading. \fBFact:\fR when \fBwait\fR is used without value, it works as \fBwait'0'\fR. 470 | \fB\fB\fBload\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/Multiple-prompts\(ra\fR@ A condition to check which should cause plugin to load. It will load once, the condition can be still true, but will not trigger second load (unless plugin is unloaded earlier, see \fBunload\fR below). E.g.: \fBload'\[lB]\[lB] $PWD = */github* \[rB]\[rB]'\fR. 471 | \fB\fB\fBunload\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/Multiple-prompts\(ra\fR@ A condition to check causing plugin to unload. It will unload once, then only if loaded again. E.g.: \fBunload'\[lB]\[lB] $PWD != */github* \[rB]\[rB]'\fR. 472 | \fBcloneonly\fR@ Don't load the plugin / snippet, only download it 473 | \fBif\fR@ Load plugin or snippet only when given condition is fulfilled, for example: \fBzi ice if'\[lB]\[lB] -n "$commands\[lB]otool\[rB]" \[rB]\[rB]'; zi load ...\fR. 474 | \fBhas\fR@ Load plugin or snippet only when given command is available (in $PATH), e.g. \fBzi ice has'git' ...\fR 475 | \fBsubscribe\fR / \fBon-update-of\fR@ Postpone loading of a plugin or snippet until the given file(s) get updated, e.g. \fBsubscribe'{~/files-*,/tmp/files-*}'\fR 476 | .TE 477 | .SS "Plugin Output" 478 | .TS 479 | tab(@); 480 | cb cb 481 | c l . 482 | Modifier@Description 483 | \fBsilent\fR@ Mute plugin's or snippet's \fBstderr\fR & \fBstdout\fR. Also skip \fBLoaded ...\fR message under prompt for \fBwait\fR, etc. loaded plugins, and completion-installation messages. 484 | \fBlucid\fR@ Skip \fBLoaded ...\fR message under prompt for \fBwait\fR, etc. loaded plugins (a subset of \fBsilent\fR). 485 | \fBnotify\fR@ Output given message under-prompt after successfully loading a plugin/snippet. In case of problems with the loading, output a warning message and the return code. If starts with \fB!\fR it will then always output the given message. Hint: if the message is empty, then it will just notify about problems. 486 | .TE 487 | .SS "Completions" 488 | .TS 489 | tab(@); 490 | cb cb 491 | c l . 492 | Modifier@Description 493 | \fBblockf\fR@ Disallow plugin to modify \fBfpath\fR. Useful when a plugin wants to provide completions in traditional way. ZI can manage completions and plugin can be blocked from exposing them. 494 | \fBnocompletions\fR@ Don't detect, install and manage completions for this plugin. Completions can be installed later with \fBzi creinstall {plugin-spec}\fR. 495 | .TE 496 | .SS "Command Execution After Cloning, Updating or Loading" 497 | .TS 498 | tab(@); 499 | cb cb 500 | c l . 501 | Modifier@Description 502 | \fBmv\fR@ Move file after cloning or after update (then, only if new commits were downloaded). Example: \fBmv "fzf-* -> fzf"\fR. It uses \fB->\fR as separator for old and new file names. Works also with snippets. 503 | \fBcp\fR@ Copy file after cloning or after update (then, only if new commits were downloaded). Example: \fBcp "docker-c* -> dcompose"\fR. Ran after \fBmv\fR. 504 | \fB\fB\fBatclone\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/atload-and-other-at-ices\(ra\fR@ Run command after cloning, within plugin's directory, e.g. \fBzi ice atclone"echo Cloned"\fR. Ran also after downloading snippet. 505 | \fB\fB\fBatpull\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/atload-and-other-at-ices\(ra\fR@ Run command after updating (\fBonly if new commits are waiting for download\fR), within plugin's directory. If starts with "!" then command will be ran before \fBmv\fR & \fBcp\fR ices and before \fBgit pull\fR or \fBsvn update\fR. Otherwise it is ran after them. Can be \fBatpull'%atclone'\fR, to repeat \fBatclone\fR Ice-mod. 506 | \fB\fB\fBatinit\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/atload-and-other-at-ices\(ra\fR@ Run command after directory setup (cloning, checking it, etc.) of plugin/snippet but before loading. 507 | \fB\fB\fBatload\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/atload-and-other-at-ices\(ra\fR@ Run command after loading, within plugin's directory. Can be also used with snippets. Passed code can be preceded with \fB!\fR, it will then be tracked (if using \fBload\fR, not \fBlight\fR). 508 | \fBrun-atpull\fR@ Always run the atpull hook (when updating), not only when there are new commits to be downloaded. 509 | \fBnocd\fR@ Don't switch the current directory into the plugin's directory when evaluating the above ice-mods \fBatinit''\fR,\fBatload''\fR, etc. 510 | \fB\fB\fBmake\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/Installing-with-make\(ra\fR@ Run \fBmake\fR command after cloning/updating and executing \fBmv\fR, \fBcp\fR, \fBatpull\fR, \fBatclone\fR Ice mods. Can obtain argument, e.g. \fBmake"install PREFIX=/opt"\fR. If the value starts with \fB!\fR then \fBmake\fR is ran before \fBatclone\fR/\fBatpull\fR, e.g. \fBmake'!'\fR. 511 | .TE 512 | .SS "Sticky-Emulation Of Other Shells" 513 | .TS 514 | tab(@); 515 | cb cb 516 | c l . 517 | Modifier@Description 518 | \fBsh\fR, \fB!sh\fR@Source the plugin's (or snippet's) script with \fBsh\fR emulation so that also all functions declared within the file will get a \fIsticky\fR emulation assigned \[en] when invoked they'll execute also with the \fBsh\fR emulation set-up. The \fB!sh\fR version switches additional options that are rather not important from the portability perspective. 519 | \fBbash\fR, \fB!bash\fR@The same as \fBsh\fR, but with the \fBSH_GLOB\fR option disabled, so that Bash regular expressions work. 520 | \fBksh\fR, \fB!ksh\fR@The same as \fBsh\fR, but emulating \fBksh\fR shell. 521 | \fBcsh\fR, \fB!csh\fR@The same as \fBsh\fR, but emulating \fBcsh\fR shell. 522 | .TE 523 | .SS "Others" 524 | .TS 525 | tab(@); 526 | cb cb 527 | c l . 528 | Modifier@Description 529 | \fBas\fR@ Can be \fBas"program"\fR (also the alias: \fBas"command"\fR), and will cause to add script/program to \fB$PATH\fR instead of sourcing (see \fBpick\fR). Can also be \fBas"completion"\fR \[en] use with plugins or snippets in whose only underscore-starting \fB_*\fR files you are interested in. 530 | \fB\fB\fBid-as\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/id-as/\(ra\fR@ Nickname a plugin or snippet, to e.g. create a short handler for long-url snippet. 531 | \fBcompile\fR@ Pattern (+ possible \fB{...}\fR expansion, like \fB{a/*,b*}\fR) to select additional files to compile, e.g. \fBcompile"(pure\[rs]|async).zsh"\fR for \fBsindresorhus/pure\fR.\[rs] 532 | \fBnocompile\fR@ Don't try to compile \fBpick\fR-pointed files. If passed the exclamation mark (i.e. \fBnocompile'!'\fR), then do compile, but after \fBmake''\fR and \fBatclone''\fR (useful if Makefile installs some scripts, to point \fBpick''\fR at the location of their installation). 533 | \fBservice\fR@ Make following plugin or snippet a \fIservice\fR, which will be ran in background, and only in single Zshell instance. See \fBzservices-organization\fR \fI\(lahttps://github.com/zservices\(ra\fR page. 534 | \fBreset-prompt\fR@ Reset the prompt after loading the plugin/snippet (by issuing \fBzle .reset-prompt\fR). Note: normally it's sufficient to precede the value of \fBwait''\fR ice with \fB!\fR. 535 | \fBbindmap\fR@ To hold \fB;\fR-separated strings like \fBKey(s)A -> Key(s)B\fR, e.g. \fB^R -> ^T; ^A -> ^B\fR. In general, \fBbindmap''\fRchanges bindings (done with the \fBbindkey\fR builtin) the plugin does. The example would cause the plugin to map Ctrl-T instead of Ctrl-R, and Ctrl-B instead of Ctrl-A. \fBDoes not work with snippets.\fR 536 | \fBtrackbinds\fR@ Shadow but only \fBbindkey\fR calls even with \fBzi light ...\fR, i.e. even with tracking disabled (fast loading), to allow \fBbindmap\fR to remap the key-binds. The same effect has \fBzi light -b ...\fR, i.e. additional \fB-b\fR option to the \fBlight\fR-subcommand. \fBDoes not work with snippets.\fR 537 | \fB\fB\fBwrap-track\fB\fR\fR \fI\(lahttp://z-shell.github.io/zi/wiki/wrap-track\(ra\fR@ Takes a \fB;\fR-separated list of function names that are to be tracked (meaning gathering report and unload data) \fBonce\fR during execution. It works by wrapping the functions with a tracking-enabling and disabling snippet of code. In summary, \fBwrap-track\fR allows to extend the tracking beyond the moment of loading of a plugin. Example use is to \fBwrap-track\fR a precmd function of a prompt (like \fB_p9k_precmd()\fR of powerlevel10k) or other plugin that \fIpostpones its initialization till the first prompt\fR (like e.g.: zsh-autosuggestions). \fBDoes not work with snippets.\fR 538 | \fBaliases\fR@Load the plugin with the aliases mechanism enabled. Use with plugins that define \fBand use\fR aliases in their scripts. 539 | .TE 540 | .SS "Order of Execution" 541 | .P 542 | Order of execution of related Ice-mods: \fBatinit\fR -> \fBatpull!\fR -> \fBmake'!!'\fR -> \fBmv\fR -> \fBcp\fR -> \fBmake!\fR -> \fBatclone\fR/\fBatpull\fR -> \fBmake\fR -> \fB(plugin script loading)\fR -> \fBsrc\fR -> \fBmultisrc\fR -> \fBatload\fR. 543 | .SS "ZI Commands" 544 | .P 545 | Following commands are passed to \fBzi ...\fR to obtain described effects. 546 | .SS "Help" 547 | .TS 548 | tab(@); 549 | cb cb 550 | c l . 551 | Command@Description 552 | \fB-h, --help, help\fR@ Usage information. 553 | \fBman\fR@ Manual. 554 | .TE 555 | .SS "Loading and Unloading" 556 | .TS 557 | tab(@); 558 | cb cb 559 | c l . 560 | Command@Description 561 | \fBload {plg-spec}\fR@ Load plugin, can also receive absolute local path. 562 | \fBlight \[lB]-b\[rB] {plg-spec}\fR@ Light plugin load, without reporting/tracking. \fB-b\fR \[en] track \fBbindkey\fR-calls only. 563 | \fBunload \[lB]-q\[rB] {plg-spec}\fR@ Unload plugin loaded with \fBzi load ...\fR. \fB-q\fR \[en] quiet. 564 | \fBsnippet \[lB]-f\[rB] {url}\fR@ Source local or remote file (by direct URL). \fB-f\fR \[en] don't use cache (force redownload). 565 | .TE 566 | .SS "Completions" 567 | .TS 568 | tab(@); 569 | cb cb 570 | c l . 571 | Command@Description 572 | clist \fB\fIcolumns\fR\fR, completions \fB\fIcolumns\fR\fR @ List completions in use, with \fIcolumns\fR completions per line. \fBzi clist 5\fR will for example print 5 completions per line. Default is 3. 573 | \fBcdisable {cname}\fR@ Disable completion \fBcname\fR. 574 | \fBcenable {cname}\fR@ Enable completion \fBcname\fR. 575 | \fBcreinstall \[lB]-q\[rB] {plg-spec}\fR@ Install completions for plugin, can also receive absolute local path. \fB-q\fR \[en] quiet. 576 | \fBcuninstall {plg-spec}\fR@ Uninstall completions for plugin. 577 | \fBcsearch\fR@ Search for available completions from any plugin. 578 | \fBcompinit\fR@ Refresh installed completions. 579 | \fBcclear\fR@ Clear stray and improper completions. 580 | \fBcdlist\fR@ Show compdef replay list. 581 | \fBcdreplay \[lB]-q\[rB]\fR@ Replay compdefs (to be done after compinit). \fB-q\fR \[en] quiet. 582 | \fBcdclear \[lB]-q\[rB]\fR@ Clear compdef replay list. \fB-q\fR \[en] quiet. 583 | .TE 584 | .SS "Tracking of the Active Session" 585 | .TS 586 | tab(@); 587 | cb cb 588 | c l . 589 | Command@Description 590 | \fBdtrace, dstart\fR@ Start tracking what's going on in session. 591 | \fBdstop\fR@ Stop tracking what's going on in session. 592 | \fBdunload\fR@ Revert changes recorded between dstart and dstop. 593 | \fBdreport\fR@ Report what was going on in session. 594 | \fBdclear\fR@ Clear report of what was going on in session. 595 | .TE 596 | .SS "Reports and Statistics" 597 | .TS 598 | tab(@); 599 | cb cb 600 | c l . 601 | Command@Description 602 | \fBtimes \[lB]-s\[rB]\fR@ Statistics on plugin load times, sorted in order of loading. \fB-s\fR \[en] use seconds instead of milliseconds. 603 | \fBzstatus\fR@ Overall ZI status. 604 | \fBreport {plg-spec}\[rs]|--all\fR@ Show plugin report. \fB--all\fR \[en] do it for all plugins. 605 | \fBloaded \[lB]keyword\[rB], list \[lB]keyword\[rB]\fR@ Show what plugins are loaded (filter with 'keyword'). 606 | \fBls\fR@ List snippets in formatted and colorized manner. Requires \fBtree\fR program. 607 | \fBstatus {plg-spec}\[rs]|URL\[rs]|--all\fR@ Git status for plugin or svn status for snippet. \fB--all\fR \[en] do it for all plugins and snippets. 608 | \fBrecently \[lB]time-spec\[rB]\fR@ Show plugins that changed recently, argument is e.g. 1 month 2 days. 609 | \fBbindkeys\fR@ Lists bindkeys set up by each plugin. 610 | .TE 611 | .SS "Compiling" 612 | .TS 613 | tab(@); 614 | cb cb 615 | c l . 616 | Command@Description 617 | \fBcompile {plg-spec}\[rs]|--all\fR@ Compile plugin. \fB--all\fR \[en] compile all plugins. 618 | \fBuncompile {plg-spec}\[rs]|--all\fR@ Remove compiled version of plugin. \fB--all\fR \[en] do it for all plugins. 619 | \fBcompiled\fR@ List plugins that are compiled. 620 | .TE 621 | .SS "Other" 622 | .TS 623 | tab(@); 624 | cb cb 625 | c l . 626 | Command@Description 627 | \fBself-update\fR@ Updates and compiles ZI. 628 | \fBupdate \[lB]-q\[rB] \[lB]-r\[rB] {plg-spec}\[rs]|URL\[rs]|--all\fR@ Git update plugin or snippet. \fB--all\fR \[en] update all plugins and snippets. \fB-q\fR \[en] quiet. \fB-r\fR | \fB--reset\fR \[en] run \fBgit reset --hard\fR / \fBsvn revert\fR before pulling changes. 629 | \fBice \fR@ Add ice to next command, argument is e.g. from"gitlab". 630 | \fBdelete {plg-spec}\[rs]|URL\[rs]|--clean\[rs]|--all\fR@ Remove plugin or snippet from disk (good to forget wrongly passed ice-mods). \fB--all\fR \[en] purge. \fB--clean\fR \[en] delete plugins and snippets that are not loaded. 631 | \fBcd {plg-spec}\fR@ Cd into plugin's directory. Also support snippets if fed with URL. 632 | \fBedit {plg-spec}\fR@ Edit plugin's file with $EDITOR. 633 | \fBglance {plg-spec}\fR@ Look at plugin's source (pygmentize, {,source-}highlight). 634 | \fBstress {plg-spec}\fR@ Test plugin for compatibility with set of options. 635 | \fBchanges {plg-spec}\fR@ View plugin's git log. 636 | \fBcreate {plg-spec}\fR@ Create plugin (also together with GitHub repository). 637 | \fBsrv {service-id} \[lB]cmd\[rB]\fR@ Control a service, command can be: stop,start,restart,next,quit; \fBnext\fR moves the service to another Zshell. 638 | \fBrecall {plg-spec}\[rs]|URL\fR@ Fetch saved ice modifiers and construct \fBzi ice ...\fR command. 639 | \fBenv-whitelist \[lB]-v\[rB] \[lB]-h\[rB] {env..}\fR@ Allows to specify names (also patterns) of variables left unchanged during an unload. \fB-v\fR \[en] verbose. 640 | \fBmodule\fR@ Manage binary Zsh module shipped with ZI, see \fBzi module help\fR. 641 | .TE 642 | .SS "Updating ZI and Plugins" 643 | .P 644 | To update ZI issue \fBzi self-update\fR in the command line. 645 | .P 646 | To update all plugins and snippets, issue \fBzi update\fR. If you wish to update only a single plugin/snippet instead issue \fBzi update NAME_OF_PLUGIN\fR. A list of commits will be shown: 647 | .P 648 | Some plugins require performing an action each time they're updated. One way you can do this is by using the \fBatpull\fR ice modifier. For example, writing \fBzi ice atpull'./configure'\fR before loading a plugin will execute \fB./configure\fR after a successful update. Refer to \fBIce Modifiers\fR \fI(Ice Modifiers)\fR for more information. 649 | .P 650 | The ice modifiers for any plugin or snippet are stored in their directory in a \fB._zi\fR subdirectory, hence the plugin doesn't have to be loaded to be correctly updated. There's one other file created there, \fB.zi_lstupd\fR \[en] it holds the log of the new commits pulled-in in the last update. 651 | .SS "Using Oh My Zsh Themes" 652 | .P 653 | To use \fBthemes\fR created for Oh My Zsh you might want to first source the \fBgit\fR library there: 654 | .P 655 | .RS 2 656 | .nf 657 | zi snippet http://github.com/ohmyzsh/ohmyzsh/raw/master/lib/git.zsh 658 | # Or using OMZ:: shorthand: 659 | zi snippet OMZ::lib/git.zsh 660 | .fi 661 | .RE 662 | .P 663 | If the library will not be loaded, then similar to following errors will be appearing: 664 | .P 665 | .RS 2 666 | .nf 667 | ........:1: command not found: git_prompt_status 668 | ........:1: command not found: git_prompt_short_sha 669 | .fi 670 | .RE 671 | .P 672 | Then you can use the themes as snippets (\fBzi snippet {file path or GitHub URL}\fR). Some themes require not only Oh My Zsh's Git \fBlibrary\fR, but also Git \fBplugin\fR (error about \fBcurrent_branch\fR function can be appearing). Load this Git-plugin as single-file snippet directly from OMZ: 673 | .P 674 | .RS 2 675 | .nf 676 | zi snippet OMZ::plugins/git/git.plugin.zsh 677 | .fi 678 | .RE 679 | .P 680 | Such lines should be added to \fB.zshrc\fR. Snippets are cached locally, use \fB-f\fR option to download a fresh version of a snippet, or \fBzi update {URL}\fR. Can also use \fBzi update --all\fR to update all snippets (and plugins). 681 | .P 682 | Most themes require \fBpromptsubst\fR option (\fBsetopt promptsubst\fR in \fBzshrc\fR), if it isn't set, then prompt will appear as something like: \fB... $(build_prompt) ...\fR. 683 | .P 684 | You might want to suppress completions provided by the git plugin by issuing \fBzi cdclear -q\fR (\fB-q\fR is for quiet) \[en] see below \fBIgnoring Compdefs\fR. 685 | .P 686 | To summarize: 687 | .P 688 | .RS 2 689 | .nf 690 | # Load OMZ Git library 691 | zi snippet OMZ::lib/git.zsh 692 | 693 | # Load Git plugin from OMZ 694 | zi snippet OMZ::plugins/git/git.plugin.zsh 695 | zi cdclear -q # <- forget completions provided up to this moment 696 | 697 | setopt promptsubst 698 | 699 | # Load theme from OMZ 700 | zi snippet OMZ::themes/dstufft.zsh-theme 701 | 702 | # Load normal GitHub plugin with theme depending on OMZ Git library 703 | zi light NicoSantangelo/Alpharized 704 | .fi 705 | .RE 706 | .P 707 | See also the Wiki page: \fBExample Oh My Zsh Setup\fR \fI\(lahttp://z-shell.github.io/zi/wiki/Example-Oh-My-Zsh-setup/\(ra\fR. 708 | .SH "COMPLETIONS" 709 | .SS "Calling \fBcompinit\fR Without Turbo Mode" 710 | .P 711 | With no Turbo mode in use, compinit can be called normally, i.e.: as \fBautoload compinit; 712 | compinit\fR. This should be done after loading of all plugins and before possibly calling \fBzi cdreplay\fR. Also, plugins aren't allowed to simply run \fBcompdefs\fR. You can decide whether to run \fBcompdefs\fR by issuing \fBzi cdreplay\fR (reads: \fBcompdef\fR-replay). To summarize: 713 | .P 714 | .RS 2 715 | .nf 716 | source ~/.zi/bin/zi.zsh 717 | 718 | zi load "some/plugin" 719 | ... 720 | compdef _gnu_generic fd # this will be intercepted by ZI, because as the compinit 721 | # isn't yet loaded, thus there's no such function `compdef'; yet 722 | # ZI provides its own `compdef' function which saves the 723 | # completion-definition for later possible re-run with `zi 724 | # cdreplay` or `zpcdreplay` (the second one can be used in hooks 725 | # like atload'', atinit'', etc.) 726 | ... 727 | zi load "other/plugin" 728 | 729 | autoload -Uz compinit 730 | compinit 731 | 732 | zi cdreplay -q # -q is for quiet; actually run all the `compdef's saved before 733 | #`compinit` call (`compinit' declares the `compdef' function, so 734 | # it cannot be used until `compinit` is ran; ZI solves this 735 | # via intercepting the `compdef'-calls and storing them for later 736 | # use with `zi cdreplay') 737 | .fi 738 | .RE 739 | .P 740 | This allows to call compinit once. Performance gains are huge, example shell startup time with double \fBcompinit\fR: \fB0.980\fR sec, with \fBcdreplay\fR and single \fBcompinit\fR: \fB0.156\fR sec. 741 | .SS "Calling \fBcompinit\fR With Turbo Mode" 742 | .P 743 | If you load completions using \fBwait''\fR Turbo mode then you can add \fBatinit'zpcompinit'\fR to syntax-highlighting plugin (which should be the last one loaded, as their (2 projects, \fBz-sy-h\fR \fI\(lahttps://github.com/zsh-users/zsh-syntax-highlighting\(ra\fR & \fBf-sy-h\fR \fI\(lahttps://github.com/z-shell/fast-syntax-highlighting\(ra\fR) documentation state), or \fBatload'zpcompinit'\fR to last completion-related plugin. \fBzpcompinit\fR is a function that just runs \fBautoload 744 | compinit; compinit\fR, created for convenience. There's also \fBzpcdreplay\fR which will replay any caught compdefs so you can also do: \fBatinit'zpcompinit; 745 | zpcdreplay'\fR, etc. Basically, the whole topic is the same as normal \fBcompinit\fR call, but it is done in \fBatinit\fR or \fBatload\fR hook of the last related plugin with use of the helper functions (\fBzpcompinit\fR,\fBzpcdreplay\fR & \fBzpcdclear\fR \[en] see below for explanation of the last one). 746 | .SS "Ignoring Compdefs" 747 | .P 748 | If you want to ignore compdefs provided by some plugins or snippets, place their load commands before commands loading other plugins or snippets, and issue \fBzi cdclear\fR (or \fBzpcdclear\fR, designed to be used in hooks like \fBatload''\fR): 749 | .P 750 | .RS 2 751 | .nf 752 | source ~/.zi/bin/zi.zsh 753 | zi snippet OMZ::plugins/git/git.plugin.zsh 754 | zi cdclear -q # <- forget completions provided by Git plugin 755 | 756 | zi load "some/plugin" 757 | ... 758 | zi load "other/plugin" 759 | 760 | autoload -Uz compinit 761 | compinit 762 | zi cdreplay -q # <- execute compdefs provided by rest of plugins 763 | zi cdlist # look at gathered compdefs 764 | .fi 765 | .RE 766 | .SS "Disabling System-Wide \fBcompinit\fR Call (Ubuntu)" 767 | .P 768 | On Ubuntu users might get surprised that e.g. their completions work while they didn't call \fBcompinit\fR in their \fB.zshrc\fR. That's because the function is being called in \fB/etc/zshrc\fR. To disable this call \[en] what is needed to avoid the slowdown and if user loads any completion-equipped plugins, i.e. almost on 100% \[en] add the following lines to \fB~/.zshenv\fR: 769 | .P 770 | .RS 2 771 | .nf 772 | # Skip the not really helping Ubuntu global compinit 773 | skip_global_compinit=1 774 | .fi 775 | .RE 776 | .SH "ZI MODULE" 777 | .SS "Motivation" 778 | .P 779 | The module is a binary Zsh module (think about \fBzmodload\fR Zsh command, it's that topic) which transparently and automatically \fBcompiles sourced scripts\fR. Many plugin managers do not offer compilation of plugins, the module is a solution to this. Even if a plugin manager does compile plugin's main script (like ZI does), the script can source smaller helper scripts or dependency libraries (for example, the prompt \fBgeometry-zsh/geometry\fR does that) and there are very few solutions to that, which are demanding (e.g. specifying all helper files in plugin load command and tracking updates to the plugin \[en] in ZI case: by using \fBcompile\fR ice-mod). 780 | .P 781 | \fBimage\fR \fI\(lahttps://raw.githubusercontent.com/z-shell/zi/images/mod-auto-compile.png\(ra\fR 782 | .SS "Installation" 783 | .SS "Without ZI" 784 | .P 785 | To install just the binary ZI module \fBstandalone\fR (ZI is not needed, the module can be used with any other plugin manager), execute: 786 | .P 787 | .RS 2 788 | .nf 789 | sh -c "$(curl -fsSL https://raw.githubusercontent.com/z-shell/zi/main/lib/mod-install.sh)" 790 | .fi 791 | .RE 792 | .P 793 | This script will display what to add to \fB~/.zshrc\fR (2 lines) and show usage instructions. 794 | .SS "With ZI" 795 | .P 796 | ZI users can build the module by issuing following command instead of running above \fBmod-install.sh\fR script (the script is for e.g. \fBzgen\fR users or users of any other plugin manager): 797 | .P 798 | .RS 2 799 | .nf 800 | zi module build 801 | .fi 802 | .RE 803 | .P 804 | This command will compile the module and display instructions on what to add to \fB~/.zshrc\fR. 805 | .SS "Measuring Time of \fBsource\fRs" 806 | .P 807 | Besides the compilation-feature, the module also measures \fBduration\fR of each script sourcing. Issue \fBzpmod 808 | source-study\fR after loading the module at top of \fB~/.zshrc\fR to see a list of all sourced files with the time the sourcing took in milliseconds on the left. This feature allows to profile the shell startup. Also, no script can pass-through that check and you will obtain a complete list of all loaded scripts, like if Zshell itself was tracking this. The list can be surprising. 809 | .SS "Debugging" 810 | .P 811 | To enable debug messages from the module set: 812 | .P 813 | .RS 2 814 | .nf 815 | typeset -g ZPLG_MOD_DEBUG=1 816 | .fi 817 | .RE 818 | .SH "HINTS AND TIPS" 819 | .SS "Customizing Paths" 820 | .P 821 | Following variables can be set to custom values, before sourcing ZI. The previous global variables like \fB$ZPLG_HOME\fR have been removed to not pollute the namespace \[en] there's single \fB$ZPLGM\fR ("\fIZI MAP\fR") hash instead of \fB8\fR string variables. Please update your dotfiles. 822 | .P 823 | .RS 2 824 | .nf 825 | declare -A ZPLGM # initial ZI's hash definition, if configuring before loading ZI, and then: 826 | .fi 827 | .RE 828 | .TS 829 | tab(@); 830 | cb cb 831 | l l . 832 | Hash Field@Description 833 | ZPLGM\fBBIN_DIR\fR@ Where ZI code resides, e.g.: "~/.zi/bin" 834 | ZPLGM\fBHOME_DIR\fR@ Where ZI should create all working directories, e.g.: "~/.zi" 835 | ZPLGM\fBPLUGINS_DIR\fR@Override single working directory \[en] for plugins, e.g. "/opt/zsh/zi/plugins" 836 | ZPLGM\fBCOMPLETIONS_DIR\fR@As above, but for completion files, e.g. "/opt/zsh/zi/root_completions" 837 | ZPLGM\fBSNIPPETS_DIR\fR@ As above, but for snippets 838 | ZPLGM\fBZCOMPDUMP_PATH\fR@Path to \fB.zcompdump\fR file, with the file included (i.e. its name can be different) 839 | ZPLGM\fBCOMPINIT_OPTS\fR@Options for \fBcompinit\fR call (i.e. done by \fBzpcompinit\fR), use to pass -C to speed up loading 840 | ZPLGM\fBMUTE_WARNINGS\fR@If set to \fB1\fR, then mutes some of the ZI warnings, specifically the \fBplugin already registered\fR warning 841 | .TE 842 | .P 843 | There is also \fB$ZPFX\fR, set by default to \fB~/.zi/polaris\fR \[en] a directory where software with \fBMakefile\fR, etc. can be pointed to, by e.g. \fBatclone'./configure --prefix=$ZPFX'\fR. 844 | .SS "Non-GitHub (Local) Plugins" 845 | .P 846 | Use \fBcreate\fR subcommand with user name \fB_local\fR (the default) to create plugin's skeleton in \fB$ZPLGM\[lB]PLUGINS_DIR\[rB]\fR. It will be not connected with GitHub repository (because of user name being \fB_local\fR). To enter the plugin's directory use \fBcd\fR command with just plugin's name (without \fB_local\fR, it's optional). 847 | .P 848 | If user name will not be \fB_local\fR, then ZI will create repository also on GitHub and setup correct repository origin. 849 | .SS "Extending Git" 850 | .P 851 | There are several projects that provide git extensions. Installing them with ZI has many benefits: 852 | .RS 0 853 | .IP \(bu 4 854 | all files are under \fB$HOME\fR \[en] no administrator rights needed, 855 | .IP \(bu 4 856 | declarative setup (like Chef or Puppet) \[en] copying \fB.zshrc\fR to different account brings also git-related setup, 857 | .IP \(bu 4 858 | easy update by e.g. \fBzi update --all\fR. 859 | .RE 0 860 | 861 | .P 862 | Below is a configuration that adds multiple git extensions, loaded in Turbo mode, two seconds after prompt: 863 | .P 864 | .RS 2 865 | .nf 866 | zi ice wait"2" lucid as"program" pick"bin/git-dsf" 867 | zi light z-shell/zsh-diff-so-fancy 868 | 869 | zi ice wait"2" lucid as"program" pick"$ZPFX/bin/git-now" make"prefix=$ZPFX install" 870 | zi light iwata/git-now 871 | 872 | zi ice wait"2" lucid as"program" pick"$ZPFX/bin/git-alias" make"PREFIX=$ZPFX" nocompile 873 | zi light tj/git-extras 874 | 875 | zi ice wait"2" lucid as"program" atclone'perl Makefile.PL PREFIX=$ZPFX' atpull'%atclone' \[rs] 876 | make'install' pick"$ZPFX/bin/git-cal" 877 | zi light k4rthik/git-cal 878 | .fi 879 | .RE 880 | .P 881 | Target directory for installed files is \fB$ZPFX\fR (\fB~/.zi/polaris\fR by default). 882 | .SS "Preinstalling Plugins" 883 | .P 884 | If you create a Docker image that uses ZI, or want to install Turbo-loaded plugins before the shell starts interactively, you can invoke the zi-scheduler function in such a way, that it: 885 | .RS 0 886 | .IP \(bu 4 887 | installs plugins without waiting for the prompt (i.e. it's script friendly), 888 | .IP \(bu 4 889 | installs \fBall\fR plugins instantly, without respecting the \fBwait''\fR argument. 890 | .RE 0 891 | 892 | .P 893 | To accomplish this, use \fBburst\fR argument and call \fB-zi-scheduler\fR function. Example \fBDockerfile\fR entry: 894 | .P 895 | .RS 2 896 | .nf 897 | RUN zsh -i -c -- '-zi-scheduler burst || true' 898 | .fi 899 | .RE 900 | .P 901 | An example \fBDockerfile\fR can be found \fB\fBhere\fR\fR \fI\(lahttps://github.com/robobenklein/configs/blob/master/Dockerfile\(ra\fR. 902 | .SH "GETTING HELP AND COMMUNITY" 903 | .P 904 | Whant to learn more? 905 | .RS 0 906 | .IP \(bu 4 907 | See Z-Shell News Blog: \fBhttps://z-shell.github.io\fR 908 | .RE 0 909 | 910 | .P 911 | -------------------------------------------------------------------------------- /lib/_zi: -------------------------------------------------------------------------------- 1 | #compdef zi 2 | 3 | setopt local_options warn_create_global type_set_silent 4 | 5 | local curcontext="$curcontext" state state_descr line ret=1 6 | local -a expl 7 | 8 | typeset -a commands 9 | commands=( 10 | analytics:"Statistics, benchmarks and information" 11 | subcmds:"Shows subcommands registered by annex" 12 | icemods:"Shows ice-modifiers registered by annex" 13 | zstatus:"Check and provide status information" 14 | times:"Statistics on plugin loading times" 15 | self-update:"Updates and compiles ❮ Zi ❯" 16 | help:"Usage information" 17 | man:"Manpage" 18 | load:"Load plugin" 19 | light:"Light load plugin" 20 | delete:"Delete plugin" 21 | unload:"Unload plugin" 22 | snippet:"Source (or add to PATH with --command) local or remote file (-f: force - do not use cache)" 23 | update:"Git update plugin (or all plugins and snippets if --all passed)" 24 | status:"Git status for plugin (or all plugins if --all passed)" 25 | report:"Show plugins report (or all plugins if --all passed)" 26 | loaded:"Show loaded plugins" 27 | list:"List loaded plugins" 28 | ls:"List snippets in formatted and colorized manner" 29 | cd:"Go into plugin directory" 30 | create:"Create plugin (also together with Github repository)" 31 | edit:"Edit plugin's file with \$EDITOR" 32 | glance:"View the plugin source" 33 | stress:"Test the plugin for compatibility with set of options" 34 | changes:"View the plugin git log" 35 | recently:"Show plugins that changed recently, argument is e.g. 1 month 2 days" 36 | clist:"List completions in use" 37 | cclear:"Clear stray and improper completions" 38 | completions:"List completions in use" 39 | cdisable:"Disable completion" 40 | cenable:"Enable completion" 41 | creinstall:"Install completions for plugin" 42 | cuninstall:"Uninstall completions for plugin" 43 | csearch:"Search for available completions from any plugin" 44 | compinit:"Refresh installed completions" 45 | dtrace:"Start tracking what's going on in session" 46 | dstart:"Start tracking what's going on in session" 47 | dstop:"Stop tracking what's going on in session" 48 | dunload:"Revert changes recorded between dstart and dstop" 49 | dreport:"Report what was going on in session" 50 | dclear:"Clear report of what was going on in session" 51 | compile:"Compile plugin (or all plugins if --all passed)" 52 | uncompile:"Remove compiled version of plugin (or of all plugins if --all passed)" 53 | compiled:"Show which plugins are compiled" 54 | cdlist:"Show compdef replay list" 55 | cdreplay:"Replay compdefs (to be done after compinit)" 56 | cdclear:"Clear compdef replay list" 57 | srv:"Control a service, command can be: stop,start,restart,next,quit; next'' moves the service to another Zshell" 58 | recall:"Fetch saved ice modifiers and construct 'zi ice ...' command" 59 | bindkeys:"Lists bindkeys set up by each plugin" 60 | module:"Manage binary Zsh module, see 'zi module help' for more info" 61 | run:"Execute code inside plugin's folder" 62 | env-whitelist:"Allows to specify names (also patterns) of variables left unchanged during an unload. -v - verbose" 63 | add-fpath:"Add plugin folder to \$fpath" 64 | ) 65 | 66 | _arguments -C \ 67 | '1: :->command'\ 68 | '*: :->argument' \ 69 | && ret=0 70 | 71 | case $state in 72 | command) 73 | _describe -t commands "Zi command" commands && ret=0 74 | ;; 75 | argument) 76 | case $words[2] in 77 | help) 78 | _message "Hit enter to get usage information" && ret=0 79 | ;; 80 | subcmds) 81 | _message "Hit enter to get subcommands list" && ret=0 82 | ;; 83 | icemods) 84 | _message "Hit enter to get ice-modifiers list" && ret=0 85 | ;; 86 | analytics) 87 | _message "Hit enter to show commands for stats" && ret=0 88 | ;; 89 | man) 90 | _message "Hit enter to view manual" && ret=0 91 | ;; 92 | zstatus) 93 | _message "Hit enter to get overall status information" && ret=0 94 | ;; 95 | times) 96 | _message "Hit enter to get plugin load time statistics" && ret=0 97 | ;; 98 | load|light) 99 | typeset -a plugins 100 | plugins=( "${ZI[PLUGINS_DIR]}"/*(N:t) ) 101 | plugins=( "${plugins[@]//---//}" ) 102 | plugins=( "${plugins[@]:#_local/zi}" ) 103 | plugins=( "${plugins[@]:#custom}" ) 104 | 105 | _alternative \ 106 | 'plugins:-- Plugin --:compadd -a - plugins' \ 107 | 'directories:-- Directory --:_directories' \ 108 | && ret=0 109 | ;; 110 | run|fpath|add-fpath) 111 | typeset -a plugins 112 | plugins=( "${ZI[PLUGINS_DIR]}"/*(N:t) ) 113 | plugins=( "${plugins[@]//---//}" ) 114 | plugins=( "${plugins[@]:#_local/zi}" ) 115 | plugins=( "${plugins[@]:#custom}" ) 116 | 117 | local -a opts 118 | if [[ $words[2] = run ]]; then 119 | opts=( -l ) 120 | else 121 | opts=( -f --front ) 122 | fi 123 | _alternative \ 124 | 'plugins:-- Plugin --:compadd -a - plugins' \ 125 | 'directories:-- Directory --:_directories' \ 126 | 'opts:-- Option --:compadd -a - opts' \ 127 | && ret=0 128 | ;; 129 | compile|stress|edit|glance|recall|update|status|cd|changes|delete) 130 | typeset -a plugins 131 | plugins=( "${ZI[PLUGINS_DIR]}"/*(N:t) ) 132 | plugins=( "${plugins[@]//---//}" ) 133 | plugins=( "${plugins[@]:#_local/zi}" ) 134 | plugins=( "${plugins[@]:#custom}" ) 135 | 136 | # snippets 137 | local -a snippets snippets_alreadyld 138 | local sni 139 | 140 | snippets=( "${ZI[SNIPPETS_DIR]}"/**/._zi(D/:h) ) 141 | snippets=( ${snippets[@]#${ZI[SNIPPETS_DIR]}/} ) 142 | snippets=( ${snippets[@]/(#b)(http|https|ftp|ftps|scp)--/${match[1]}://} ) 143 | snippets=( ${snippets[@]/--//} ) 144 | 145 | for sni ( ${snippets[@]} ) { 146 | if [[ -n ${ZI_SNIPPETS[$sni]} ]]; then 147 | snippets_alreadyld+=( $sni ) 148 | snippets=( ${snippets[@]:#$sni} ) 149 | fi 150 | } 151 | 152 | _alternative \ 153 | 'dsnippets:-- Downloaded Snippet --:compadd -a - snippets' \ 154 | 'lsnippets:-- Already Loaded Snippet --:compadd -a - snippets_alreadyld' \ 155 | 'plugins:-- Plugin --:compadd -a - plugins' \ 156 | && ret=0 157 | ;; 158 | unload|report) 159 | typeset -a plugins absolute normal 160 | plugins=( "${ZI_REGISTERED_PLUGINS[@]:#_local/zi}" ) 161 | normal=( "${plugins[@]:#%*}" ) 162 | absolute=( "${(M)plugins[@]:#%*}" ) 163 | absolute=( "${absolute[@]/\%\/\//%/}" ) 164 | local hm="${HOME%/}" 165 | absolute=( "${absolute[@]/$hm/HOME}" ) 166 | plugins=( $normal $absolute ) 167 | 168 | _wanted plugins expl "-- Plugin --" \ 169 | compadd "$@" -a - plugins \ 170 | && ret=0 171 | ;; 172 | all-reports) 173 | _message "Hit enter to get all reports (for all loaded plugins)" && ret=0 174 | ;; 175 | loaded|list) 176 | _message "Hit enter or give part of plugin name" && ret=0 177 | ;; 178 | clist|completions) 179 | _message "Hit enter to get list of completions" && ret=0 180 | ;; 181 | cclear) 182 | _message "Hit enter to clear stray and improper completions" && ret=0 183 | ;; 184 | cdisable) # Find enabled completions 185 | typeset -a completions 186 | completions=( "${ZI[COMPLETIONS_DIR]}"/_*(N:t) ) 187 | completions=( "${completions[@]#_}" ) 188 | _wanted plugins expl "-- Completion --" \ 189 | compadd "$@" -a - completions \ 190 | && ret=0 191 | ;; 192 | cenable) # find disabled completions 193 | typeset -a completions 194 | completions=( "${ZI[COMPLETIONS_DIR]}"/[^_]*(N:t) ) 195 | _wanted plugins expl "-- Completion --" \ 196 | compadd "$@" -a - completions \ 197 | && ret=0 198 | ;; 199 | creinstall) 200 | # complete only plugins that have any completions 201 | # iterate each plugin to check for completions that can be installed 202 | typeset -a plugins completions 203 | local p c user plugin 204 | for p in "${ZI[PLUGINS_DIR]}"/*; do 205 | completions=( "$p"/**/_[^_.]*~*(*.zwc|*.html|*.txt|*.png|*.jpg|*.jpeg|*.js|*.md|_zsh_highlight*|/zsdoc/*)(DN) ) 206 | for c in "${completions[@]}"; do 207 | p="${p:t}" 208 | user="${p%%---*}" 209 | plugin="${p#*---}" 210 | [[ "$user" = "$plugin" && "${user}---${plugin}" != "$p" ]] && user="" 211 | plugins+=( "${user:+$user/}$plugin" ) 212 | break 213 | done 214 | done 215 | _wanted plugins expl "-- Plugin --" \ 216 | compadd "$@" -a - plugins \ 217 | && ret=0 218 | ;; 219 | cuninstall) 220 | # iterate each plugin and check if it has completions that are installed 221 | typeset -a plugins completions 222 | local p c user plugin cfile bkpfile 223 | for p in "${ZI[PLUGINS_DIR]}"/*; do 224 | completions=( "$p"/**/_[^_.][^.]#(N) ) 225 | for c in "${completions[@]}"; do 226 | cfile="${c:t}" 227 | bkpfile="${cfile#_}" 228 | # completion installed, either enabled or disabled? 229 | if [[ -e "${ZI[COMPLETIONS_DIR]}"/"$cfile" || -e "${ZI[COMPLETIONS_DIR]}"/"$bkpfile" ]]; then 230 | p="${p:t}" 231 | user="${p%%---*}" 232 | plugin="${p#*---}" 233 | [[ "$user" = "$plugin" && "${user}---${plugin}" != "$p" ]] && user="" 234 | plugins+=( "${user:+$user/}$plugin" ) 235 | break 236 | fi 237 | done 238 | done 239 | _wanted plugins expl "-- Plugin --" \ 240 | compadd "$@" -a - plugins \ 241 | && ret=0 242 | ;; 243 | compinit) 244 | _message "Hit enter to refresh completion system" && ret=0 245 | ;; 246 | snippet) 247 | local -a snippets snippets_alreadyld 248 | local sni 249 | 250 | snippets=( "${ZI[SNIPPETS_DIR]}"/**/._zi(D/:h) ) 251 | snippets=( ${snippets[@]#${ZI[SNIPPETS_DIR]}/} ) 252 | snippets=( ${snippets[@]/(#b)(http|https|ftp|ftps|scp)--/${match[1]}://} ) 253 | snippets=( ${snippets[@]/--//} ) 254 | 255 | for sni ( ${snippets[@]} ) { 256 | if [[ -n ${ZI_SNIPPETS[$sni]} ]]; then 257 | snippets_alreadyld+=( $sni ) 258 | snippets=( ${snippets[@]:#$sni} ) 259 | fi 260 | } 261 | 262 | _alternative \ 263 | 'dsnippets:-- Downloaded Snippet --:compadd -a - snippets' \ 264 | 'lsnippets:-- Already Loaded Snippet --:compadd -a - snippets_alreadyld' \ 265 | 'files:-- File --:_files' \ 266 | && ret=0 267 | ;; 268 | dstart|dtrace) 269 | _message "Hit enter to start tracking this session" && ret=0 270 | ;; 271 | dstop) 272 | _message "Hit enter to stop tracking this session" && ret=0 273 | ;; 274 | dunload) 275 | _message "Hit enter to revert changes recorded between dstart and dstop" && ret=0 276 | ;; 277 | dreport) 278 | _message "Hit enter to show report of what was going on in session" && ret=0 279 | ;; 280 | dclear) 281 | _message "Hit enter to clear report of what was going on in session" && ret=0 282 | ;; 283 | compile-all) 284 | _message 'Hit enter to compile all downloaded plugins' && ret=0 285 | ;; 286 | uncompile) 287 | typeset -a plugins 288 | plugins=( "${ZI[PLUGINS_DIR]}"/*(N) ) 289 | 290 | typeset -a show_plugins p matches 291 | for p in "${plugins[@]}"; do 292 | matches=( $p/*.zwc(N) ) 293 | if [ "$#matches" -ne "0" ]; then 294 | p="${p:t}" 295 | [ "$p" = "_local---zi" ] && continue 296 | [ "$p" = "custom" ] && continue 297 | p="${p//---//}" 298 | show_plugins+=( "$p" ) 299 | fi 300 | done 301 | 302 | _wanted show_plugins expl "-- Plugin --" \ 303 | compadd "$@" -a - show_plugins \ 304 | && ret=0 305 | ;; 306 | uncompile-all) 307 | _message 'Hit enter remove compiled versions of all downloaded plugins' && ret=0 308 | ;; 309 | compiled) 310 | _message 'Hit enter to get list of compiled plugins' && ret=0 311 | ;; 312 | cdlist) 313 | _message 'Hit enter to show compdef replay list' && ret=0 314 | ;; 315 | cdreplay) 316 | _message 'Hit enter to replay recorded compdefs' && ret=0 317 | ;; 318 | cdclear) 319 | _message 'Hit enter to clear compdef replay list' && ret=0 320 | ;; 321 | recently) 322 | typeset -a timespecs 323 | timespecs=( 324 | "1 month":"code modified during last month" 325 | "1 week":"code modified during last 7 days (default)" 326 | "3 days":"code modified during last 3 days" 327 | ) 328 | _describe -t timespecs "Time spec" timespecs && ret=0 329 | ;; 330 | create) 331 | _message 'Plugin spec or just enter, to create new plugin' && ret=0 332 | ;; 333 | env-whitelist) 334 | _wanted plugins expl "-- Parameter To White List During Any Plugin Unload --" _parameters \ 335 | && ret=0 336 | ;; 337 | *) 338 | ret=1 339 | ;; 340 | esac 341 | esac 342 | 343 | return $ret 344 | -------------------------------------------------------------------------------- /lib/templates/example-script: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env zsh 2 | # -*- mode: sh; sh-indentation: 2; indent-tabs-mode: nil; sh-basic-offset: 2; -*- 3 | # 4 | # Copyright (c) YEAR USER_NAME 5 | # 6 | # An example of type-agnostic script/function, i.e.: the file can be run as a +x 7 | # script or as an autoload function. Set the base and typically useful options 8 | builtin emulate -L zsh ${=${options[xtrace]:#off}:+-o xtrace} 9 | builtin setopt extended_glob warn_create_global typeset_silent no_short_loops rc_quotes no_auto_pushd 10 | 11 | if [[ $0 != example-script || -n $ZSH_SCRIPT ]]; then 12 | # #̶ =̶=̶=̶ =̶=̶=̶ =̶=̶=̶ #̶ 13 | # 𝟘 - https://wiki.zshell.dev/community/zsh_plugin_standard 14 | # Standardized $0 Handling - [ zero-handling ] 15 | 0="${ZERO:-${${0:#$ZSH_ARGZERO}:-${(%):-%N}}}" 16 | 0="${${(M)0:#/*}:-$PWD/$0}" 17 | # #̶ =̶=̶=̶ =̶=̶=̶ =̶=̶=̶ #̶ 18 | # 𝟙 - # https://wiki.zshell.dev/community/zsh_plugin_standard#funtions-directory 19 | # The below snippet added to the plugin.zsh file will add the directory 20 | # to the $fpath with the compatibility with any new plugin managers preserved. 21 | if [[ $PMSPEC != *f* ]] { 22 | fpath+=( "${0:h}/functions" ) 23 | } 24 | # #̶ =̶=̶=̶ =̶=̶=̶ =̶=̶=̶ #̶ 25 | # 𝟚 - # https://wiki.zshell.dev/community/zsh_plugin_standard#unload-function 26 | # If a plugin is named kalc* and is available via any-user/kalc_plugin_ID, 27 | # then it can provide a function, kalc_plugin_unload, that can be called by a 28 | # plugin manager to undo the effects of loading that plugin. 29 | # #̶ =̶=̶=̶ =̶=̶=̶ =̶=̶=̶ #̶ 30 | # 𝟛 - https://wiki.zshell.dev/community/zsh_plugin_standard#run-on-unload-call 31 | # RUN ON UNLOAD CALL 32 | # #̶ =̶=̶=̶ =̶=̶=̶ =̶=̶=̶ #̶ 33 | # 𝟜 - https://wiki.zshell.dev/community/zsh_plugin_standard#run-on-update-call 34 | # RUN ON UPDATE CALL 35 | # #̶ =̶=̶=̶ =̶=̶=̶ =̶=̶=̶ #̶ 36 | # 𝟝 - https://wiki.zshell.dev/community/zsh_plugin_standard#activity-indicator 37 | # Zi will set the $zsh_loaded_plugins array to contain all previously loaded plugins 38 | # and the plugin currently being loaded, as the last element. 39 | if [[ ${zsh_loaded_plugins[-1]} != */kalc && -z ${fpath[(r)${0:h}]} ]] { 40 | fpath+=( "${0:h}" ) 41 | } 42 | # #̶ =̶=̶=̶ =̶=̶=̶ =̶=̶=̶ #̶ 43 | # 𝟞 - https://wiki.zshell.dev/community/zsh_plugin_standard#global-parameter-with-prefix 44 | # Global Parameter With PREFIX For Make, Configure, Etc 45 | # #̶ =̶=̶=̶ =̶=̶=̶ =̶=̶=̶ #̶ 46 | # 𝟟 - https://wiki.zshell.dev/community/zsh_plugin_standard#global-parameter-with-capabilities 47 | # PMSPEC 48 | # #̶ =̶=̶=̶ =̶=̶=̶ =̶=̶=̶ #̶ 49 | # 𝟠 - https://wiki.zshell.dev/community/zsh_plugin_standard#zsh-plugin-programming-best-practices 50 | # Zsh Plugin-Programming Best practices 51 | # #̶ =̶=̶=̶ =̶=̶=̶ =̶=̶=̶ #̶ 52 | # Such global variable is expected to be typeset'd -g in the plugin.zsh 53 | # file. Here it's restored in case of the function being run as a script. 54 | typeset -gA Plugins 55 | Plugins[MY_PLUGIN_DIR]=${0:h} 56 | # In case of the script using other scripts from the plugin, either set up 57 | # $fpath and autoload, or add the directory to $PATH. 58 | fpath+=( $Plugins[MY_PLUGIN_DIR] ) 59 | autoload … 60 | # OR 61 | path+=( $Plugins[MY_PLUGIN_DIR] ) 62 | fi 63 | # The script/function contents possibly using $Plugins[MY_PLUGIN_DIR] … 64 | # … 65 | # Use alternate marks [[[ and ]]] as the original ones can confuse nested 66 | # substitutions, e.g.: ${${${VAR}}} 67 | # 68 | # Made with love by Z-Shell Community 69 | # 70 | # vim:ft=zsh:tw=120:sw=2:sts=2:et:foldmarker=[[[,]]] 71 | -------------------------------------------------------------------------------- /lib/templates/zsh.gitignore: -------------------------------------------------------------------------------- 1 | # Zsh compiled script + zrecompile backup 2 | *.zwc 3 | *.zwc.old 4 | 5 | # Zsh completion-optimization dumpfile 6 | *zcompdump* 7 | 8 | # Zsh zcalc history 9 | .zcalc_history 10 | 11 | # A popular plugin manager's files 12 | ._zi 13 | ._zinit 14 | .zi_lastupd 15 | .zinit_lastupd 16 | 17 | # A popular older versions plugin manager's files 18 | ._zplugin 19 | .zplugin_lstupd 20 | 21 | # z-shell/zshelldoc tool's files 22 | zsdoc/data 23 | docs/zsdoc/data 24 | 25 | # ohmyzsh/ohmyzsh/plugins/per-directory-history plugin's files 26 | # (when set-up to store the history in the local directory) 27 | .directory_history 28 | 29 | # MichaelAquilina/zsh-autoswitch-virtualenv plugin's files 30 | # (for Zsh plugins using Python) 31 | .venv 32 | 33 | # Zunit tests' output 34 | /tests/_output/* 35 | !/tests/_output/.gitkeep 36 | 37 | ### C 38 | # Prerequisites 39 | *.d 40 | 41 | # Object files 42 | *.o 43 | *.ko 44 | *.obj 45 | *.elf 46 | 47 | # Linker output 48 | *.ilk 49 | *.map 50 | *.exp 51 | 52 | # Precompiled Headers 53 | *.gch 54 | *.pch 55 | 56 | # Libraries 57 | *.lib 58 | *.a 59 | *.la 60 | *.lo 61 | 62 | # Shared objects (inc. Windows DLLs) 63 | *.dll 64 | *.so 65 | *.so.* 66 | *.dylib 67 | 68 | # Executables 69 | *.exe 70 | *.out 71 | *.app 72 | *.i*86 73 | *.x86_64 74 | *.hex 75 | 76 | # Debug files 77 | *.dSYM/ 78 | *.su 79 | *.idb 80 | *.pdb 81 | 82 | # Kernel Module Compile Results 83 | *.mod* 84 | *.cmd 85 | .tmp_versions/ 86 | modules.order 87 | Module.symvers 88 | Mkfile.old 89 | dkms.conf 90 | -------------------------------------------------------------------------------- /lib/zcompile: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env zsh 2 | zcompile "$@" 3 | -------------------------------------------------------------------------------- /lib/zsh/additional.zsh: -------------------------------------------------------------------------------- 1 | # -*- mode: zsh; sh-indentation: 2; indent-tabs-mode: nil; sh-basic-offset: 2; -*- 2 | # vim: ft=zsh sw=2 ts=2 et 3 | # 4 | # Copyright (c) 2016-2020 Sebastian Gniazdowski and contributors. 5 | # Copyright (c) 2021 Salvydas Lukosius and Z-Shell Community. 6 | 7 | # FUNCTION: :zi-tmp-subst-source [[[ 8 | :zi-tmp-subst-source() { 9 | local -a ___substs ___ab 10 | ___substs=( "${(@s.;.)ICE[subst]}" ) 11 | if [[ -n ${(M)___substs:#*\\(#e)} ]] { 12 | local ___prev 13 | ___substs=( ${___substs[@]//(#b)((*)\\(#e)|(*))/${match[3]:+${___prev:+$___prev\;}}${match[3]}${${___prev::=${match[2]:+${___prev:+$___prev\;}}${match[2]}}:+}} ) 14 | } 15 | 16 | # Load the plugin 17 | if [[ ! -r $1 ]] { 18 | +zi-message "{error}source: Couldn't read the script {obj}${1}{error}" \ 19 | ", cannot substitute {data}${ICE[subst]}{error}.{rst}" 20 | } 21 | 22 | local ___data="$(<$1)" 23 | 24 | () { 25 | builtin emulate -LR zsh -o extendedglob -o interactivecomments ${=${options[xtrace]:#off}:+-o xtrace} 26 | local ___subst ___tabspc=$'\t' 27 | for ___subst ( "${___substs[@]}" ) { 28 | ___ab=( "${(@)${(@)${(@s:->:)___subst}##[[:space:]]##}%%[[:space:]]##}" ) 29 | ___ab[2]=${___ab[2]//(#b)\\([[:digit:]])/\${match[${match[1]}]}} 30 | builtin eval "___data=\"\${___data//(#b)\${~___ab[1]}/${___ab[2]}}\"" 31 | } 32 | ___data="() { ${(F)${(@)${(f)___data[@]}:#[$___tabspc]#\#*}} ; } \"\${@[2,-1]}\"" 33 | } 34 | 35 | builtin eval "$___data" 36 | } 37 | # ]]] 38 | # FUNCTION: .zi-service [[[ 39 | # Handles given service, i.e. obtains lock, runs it, or waits if no lock 40 | # 41 | # $1 - type "p" or "s" (plugin or snippet) 42 | # $2 - mode - for plugin (light or load) 43 | # $3 - id - URL or plugin ID or alias name (from id-as'') 44 | .zi-service() { 45 | builtin emulate -LR zsh ${=${options[xtrace]:#off}:+-o xtrace} 46 | builtin setopt extendedglob warncreateglobal typesetsilent noshortloops 47 | local ___tpe="$1" ___mode="$2" ___id="$3" ___fle="${ZI[SERVICES_DIR]}/${ICE[service]}.lock" ___fd ___cmd ___tmp ___lckd ___strd=0 48 | { builtin print -n >! "$___fle"; } 2>/dev/null 1>&2 49 | [[ ! -e ${___fle:r}.fifo ]] && command mkfifo "${___fle:r}.fifo" 2>/dev/null 1>&2 50 | [[ ! -e ${___fle:r}.fifo2 ]] && command mkfifo "${___fle:r}.fifo2" 2>/dev/null 1>&2 51 | typeset -g ZSRV_WORK_DIR="${ZI[SERVICES_DIR]}" ZSRV_ID="${ICE[service]}" # should be also set by other p-m 52 | while (( 1 )); do 53 | ( 54 | while (( 1 )); do 55 | [[ ! -f ${___fle:r}.stop ]] && if (( ___lckd )) || zsystem 2>/dev/null 1>&2 flock -t 1 -f ___fd -e $___fle; then 56 | ___lckd=1 57 | if (( ! ___strd )) || [[ $___cmd = RESTART ]]; then 58 | [[ $___tpe = p ]] && { ___strd=1; .zi-load "$___id" "" "$___mode"; } 59 | [[ $___tpe = s ]] && { ___strd=1; .zi-load-snippet "$___id" ""; } 60 | fi 61 | ___cmd= 62 | while (( 1 )); do builtin read -t 32767 ___cmd <>"${___fle:r}.fifo" && break; done 63 | else 64 | return 0 65 | fi 66 | [[ $___cmd = (#i)NEXT ]] && { kill -TERM "$ZSRV_PID"; builtin read -t 2 ___tmp <>"${___fle:r}.fifo2"; kill -HUP "$ZSRV_PID"; exec {___fd}>&-; ___lckd=0; ___strd=0; builtin read -t 10 ___tmp <>"${___fle:r}.fifo2"; } 67 | [[ $___cmd = (#i)STOP ]] && { kill -TERM "$ZSRV_PID"; builtin read -t 2 ___tmp <>"${___fle:r}.fifo2"; kill -HUP "$ZSRV_PID"; ___strd=0; builtin print >! "${___fle:r}.stop"; } 68 | [[ $___cmd = (#i)QUIT ]] && { kill -HUP ${sysparams[pid]}; return 1; } 69 | [[ $___cmd != (#i)RESTART ]] && { ___cmd=; builtin read -t 1 ___tmp <>"${___fle:r}.fifo2"; } 70 | done 71 | ) || break 72 | builtin read -t 1 ___tmp <>"${___fle:r}.fifo2" 73 | done >>! "$ZSRV_WORK_DIR/$ZSRV_ID".log 2>&1 74 | } # ]]] 75 | # FUNCTION: .zi-wrap-functions [[[ 76 | # Handles the wrap'…' ice-modifier which allows to extend the tracking (e.g: gathering of report and unload data) of a plugin 77 | # beyond the moment of sourcing it's main file(s). It works by wrapping the given functions with a tracking-enabling 78 | # and disabling snippet of code.This is useful especially with prompts, as they very often do their 79 | # initialization in the first call to their precmd hook function. 80 | .zi-wrap-functions() { 81 | local user="$1" plugin="$2" id_as="$3" f 82 | local -a wt 83 | wt=( ${(@s.;.)ICE[wrap]} ) 84 | for f in ${wt[@]}; do 85 | functions[${f}-zi-bkp]="${functions[$f]}" 86 | eval " 87 | function $f { 88 | ZI[CUR_USR]=\"$user\" ZI[CUR_PLUGIN]=\"$plugin\" ZI[CUR_USPL2]=\"$id_as\" 89 | .zi-add-report \"\${ZI[CUR_USPL2]}\" \"Note: === Starting to track function: $f ===\" 90 | .zi-diff \"\${ZI[CUR_USPL2]}\" begin 91 | .zi-tmp-subst-on load 92 | functions[${f}]=\${functions[${f}-zi-bkp]} 93 | ${f} \"\$@\" 94 | .zi-tmp-subst-off load 95 | .zi-diff \"\${ZI[CUR_USPL2]}\" end 96 | .zi-add-report \"\${ZI[CUR_USPL2]}\" \"Note: === Ended tracking function: $f ===\" 97 | ZI[CUR_USR]= ZI[CUR_PLUGIN]= ZI[CUR_USPL2]= 98 | }" 99 | done 100 | } # ]]] 101 | 102 | # 103 | # Dtrace 104 | # 105 | 106 | # FUNCTION: .zi-debug-start [[[ 107 | # Starts Dtrace, i.e. session tracking for changes in Zsh state. 108 | .zi-debug-start() { 109 | if [[ ${ZI[DTRACE]} = 1 ]]; then 110 | +zi-message "{error}Dtrace is already active, stop it first with \`dstop'{rst}" 111 | return 1 112 | fi 113 | 114 | ZI[DTRACE]=1 115 | 116 | .zi-diff _dtrace/_dtrace begin 117 | 118 | # Full shadeing on 119 | .zi-tmp-subst-on dtrace 120 | } # ]]] 121 | # FUNCTION: .zi-debug-stop [[[ 122 | # Stops Dtrace, i.e. session tracking for changes in Zsh state. 123 | .zi-debug-stop() { 124 | ZI[DTRACE]=0 125 | # Shadowing fully off 126 | .zi-tmp-subst-off dtrace 127 | # Gather end data now, for diffing later 128 | .zi-diff _dtrace/_dtrace end 129 | } # ]]] 130 | # FUNCTION: .zi-clear-debug-report [[[ 131 | # Forgets dtrace repport gathered up to this moment. 132 | .zi-clear-debug-report() { 133 | .zi-clear-report-for _dtrace/_dtrace 134 | } # ]]] 135 | # FUNCTION: .zi-debug-unload [[[ 136 | # Reverts changes detected by dtrace run. 137 | .zi-debug-unload() { 138 | (( ${+functions[.zi-unload]} )) || builtin source "${ZI[BIN_DIR]}/lib/zsh/autoload.zsh" || return 1 139 | if [[ ${ZI[DTRACE]} = 1 ]]; then 140 | +zi-message "{error}Dtrace is still active, stop it first with \`dstop'{rst}" 141 | else 142 | .zi-unload _dtrace _dtrace 143 | fi 144 | } # ]]] 145 | -------------------------------------------------------------------------------- /lib/zsh/git-process-output.zsh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env zsh 2 | 3 | builtin emulate -LR zsh 4 | builtin setopt extended_glob warn_create_global typeset_silent 5 | 6 | { typeset -g COLS="$(tput cols)" } 2>/dev/null 7 | if (( COLS < 10 )) { 8 | COLS=40 9 | } 10 | # Credit to molovo/revolver for the ideas 11 | typeset -ga progress_frames 12 | progress_frames=( 13 | '0.1 ⠋ ⠙ ⠹ ⠸ ⠼ ⠴ ⠦ ⠧ ⠇ ⠏' 14 | '0.1 ⣾ ⣽ ⣻ ⢿ ⡿ ⣟ ⣯ ⣷' 15 | '0.1 ⢹ ⢺ ⢼ ⣸ ⣇ ⡧ ⡗ ⡏' 16 | ) 17 | 18 | integer -g progress_style=$(( RANDOM % 2 + 1 )) cur_frame=1 19 | typeset -F SECONDS=0 last_time=0 20 | 21 | # Alpine Linux doesn't have tput; FreeBSD and Dragonfly BSD have termcap 22 | if whence tput &> /dev/null; then 23 | if [[ $OSTYPE == freebsd* ]] || [[ $OSTYPE == dragonfly* ]]; then 24 | # termcap commands 25 | ZI_CNORM='tput ve' 26 | ZI_CIVIS='tput vi' 27 | else 28 | # terminfo is more common 29 | ZI_CNORM='tput cnorm' 30 | ZI_CIVIS='tput civis' 31 | fi 32 | fi 33 | 34 | if (( $+ZI_CNORM )); then 35 | trap $ZI_CNORM EXIT INT TERM 36 | fi 37 | 38 | local first=1 39 | 40 | # Code by leoj3n 41 | timeline() { 42 | local sp='▚▞'; sp="${sp:$2%2:1}" 43 | # Maximal width is 24 characters 44 | local bar="$(builtin print -f "%.$2s█%0$(($3-$2-1))s" "░▒▓█████████████████████" "")" 45 | local -a frames_splitted 46 | frames_splitted=( ${(@zQ)progress_frames[progress_style]} ) 47 | if (( SECONDS - last_time >= frames_splitted[1] )) { 48 | (( cur_frame = (cur_frame+1) % (${#frames_splitted}+1-1) )) 49 | (( cur_frame = cur_frame ? cur_frame : 1 )) 50 | last_time=$SECONDS 51 | } 52 | builtin print -nr -- ${frames_splitted[cur_frame+1]}" " 53 | builtin print -nPr "%F{201}" 54 | builtin print -f "%s %s" "${bar// /░}" "" 55 | builtin print -nPr "%f" 56 | } 57 | 58 | # $1 - n of objects 59 | # $2 - packed objects 60 | # $3 - total objects 61 | # $4 - receiving percentage 62 | # $5 - resolving percentage 63 | print_my_line() { 64 | local col="%F{201}" col3="%F{201}" col4="%F{201}" col5="%F{046}" 65 | [[ -n "${4#...}" && -z "${5#...}" ]] && local col="%F{226}" col3="%F{226}" col4="%F{226}" 66 | [[ -n "${5#...}" ]] && local col="%F{201}" col3="%F{046}" col4="%F{046}" 67 | if (( COLS >= 70 )) { 68 | builtin print -Pnr -- "${col}OBJ%f: $1, ${col}PACK%f: $2/$3${${4:#...}:+, ${col3}REC%f: $4%}${${5:#...}:+, ${col4}RES%f: $5%} " 69 | } elif (( COLS >= 60 )) { 70 | builtin print -Pnr -- "${col}OBJ%f: $1, ${${4:#...}:+, ${col3}REC%f: $4%}${${5:#...}:+, ${col4}RES%f: $5%} " 71 | } else { 72 | builtin print -Pnr -- "${${4:#...}:+, ${col3}REC%f: $4%}${${5:#...}:+, ${col4}RES%f: $5%} " 73 | } 74 | builtin print -n $'\015' 75 | } 76 | 77 | print_my_line_compress() { 78 | local col="%F{201}" col3="%F{201}" col4="%F{201}" col5="%F{046}" 79 | [[ -n "${4#...}" && -z "${5#...}" && -z "${6#...}" ]] && local col="%F{226}" col3="%F{226}" col4="%F{226}" col5="%F{226}" 80 | [[ -n "${5#...}" && -z "${6#...}" ]] && local col="%F{201}" col3="%F{226}" col4="%F{226}" col5="%F{226}" 81 | [[ -n "${6#...}" ]] && local col3="%F{201}" col4="%F{046}" col5="%F{046}" 82 | if (( COLS >= 80 )) { 83 | builtin print -Pnr -- "${col}OBJ%f: $1, ${col}PACK%f: $2/$3, ${col3}COMPR%f: $4%%${${5:#...}:+, ${col4}REC%f: $5%%}${${6:#...}:+, ${col5}RES%f: $6%%} " 84 | } elif (( COLS >= 65 )) { 85 | builtin print -Pnr -- "${col}OBJ%f: $1, ${col3}COMPR%f: $4%%${${5:#...}:+, ${col4}REC%f: $5%%}${${6:#...}:+, ${col5}RES%f: $6%%} " 86 | } else { 87 | builtin print -Pnr -- "${col}OBJ%f: $1, ${${5:#...}:+, ${col4}REC%f: $5%%}${${6:#...}:+, ${col5}RES%f: $6%%} " 88 | } 89 | builtin print -n $'\015' 90 | } 91 | 92 | integer have_1_counting=0 have_2_total=0 have_3_receiving=0 have_4_deltas=0 have_5_compress=0 93 | integer counting_1=0 total_2=0 total_packed_2=0 receiving_3=0 deltas_4=0 compress_5=0 94 | integer loop_count=0 95 | 96 | IFS='' 97 | 98 | [[ $+ZI_CIVIS == 1 && -n $TERM ]] && eval $ZI_CIVIS 99 | 100 | if [[ -n $TERM ]] { 101 | { command perl -pe 'BEGIN { $|++; $/ = \1 }; tr/\r/\n/' || \ 102 | gstdbuf -o0 gtr '\r' '\n' || \ 103 | cat } |& \ 104 | while read -r line; do 105 | (( ++ loop_count )) 106 | if [[ "$line" = "Cloning into"* ]]; then 107 | builtin print $line 108 | continue 109 | elif [[ "$line" = (#i)*user*name* || "$line" = (#i)*password* ]]; then 110 | builtin print $line 111 | continue 112 | elif [[ "$line" = remote:*~*(Counting|Total|Compressing|Enumerating)* || "$line" = fatal:* ]]; then 113 | builtin print $line 114 | continue 115 | fi 116 | if [[ "$line" = (#b)"remote: Counting objects:"[\ ]#([0-9]##)(*) ]]; then 117 | have_1_counting=1 118 | counting_1="${match[1]}" 119 | fi 120 | if [[ "$line" = (#b)"remote: Enumerating objects:"[\ ]#([0-9]##)(*) ]]; then 121 | have_1_counting=1 122 | counting_1="${match[1]}" 123 | fi 124 | if [[ "$line" = (#b)*"remote: Total"[\ ]#([0-9]##)*"pack-reused"[\ ]#([0-9]##)* ]]; then 125 | have_2_total=1 126 | total_2="${match[1]}" total_packed_2="${match[2]}" 127 | fi 128 | if [[ "$line" = (#b)"Receiving objects:"[\ ]#([0-9]##)%([[:blank:]]#\(([0-9]##)/([0-9]##)\)|)* ]]; then 129 | have_3_receiving=1 130 | receiving_3="${match[1]}" 131 | [[ -n "${match[2]}" ]] && { 132 | have_2_total=1 133 | total_packed_2="${match[3]}" total_2="${match[4]}" 134 | } 135 | fi 136 | if [[ "$line" = (#b)"Resolving deltas:"[\ ]#([0-9]##)%* ]]; then 137 | have_4_deltas=1 138 | deltas_4="${match[1]}" 139 | fi 140 | if [[ "$line" = (#b)"remote: Compressing objects:"[\ ]#([0-9]##)"%"(*) ]]; then 141 | have_5_compress=1 142 | compress_5="${match[1]}" 143 | fi 144 | if (( loop_count >= 2 )); then 145 | integer pr 146 | (( pr = have_4_deltas ? deltas_4 / 10 : ( 147 | have_3_receiving ? receiving_3 / 10 : ( 148 | have_5_compress ? compress_5 / 10 : ( ( ( loop_count - 1 ) / 14 ) % 10 ) + 1 ) ) )) 149 | timeline "" $pr 11 150 | if (( have_5_compress )); then 151 | print_my_line_compress "${${${(M)have_1_counting:#1}:+$counting_1}:-...}" \ 152 | "${${${(M)have_2_total:#1}:+$total_packed_2}:-0}" \ 153 | "${${${(M)have_2_total:#1}:+$total_2}:-0}" \ 154 | "${${${(M)have_5_compress:#1}:+$compress_5}:-...}" \ 155 | "${${${(M)have_3_receiving:#1}:+$receiving_3}:-...}" \ 156 | "${${${(M)have_4_deltas:#1}:+$deltas_4}:-...}" 157 | else 158 | print_my_line "${${${(M)have_1_counting:#1}:+$counting_1}:-...}" \ 159 | "${${${(M)have_2_total:#1}:+$total_packed_2}:-0}" \ 160 | "${${${(M)have_2_total:#1}:+$total_2}:-0}" \ 161 | "${${${(M)have_3_receiving:#1}:+$receiving_3}:-...}" \ 162 | "${${${(M)have_4_deltas:#1}:+$deltas_4}:-...}" 163 | fi 164 | fi 165 | done 166 | 167 | } else { 168 | grep fatal: 169 | } 170 | 171 | builtin print 172 | 173 | [[ $+ZI_CNORM == 1 && -n $TERM ]] && eval $ZI_CNORM 174 | 175 | unset ZI_CNORM ZI_CIVIS 176 | -------------------------------------------------------------------------------- /lib/zsh/rpm2cpio.zsh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env zsh 2 | 3 | builtin emulate -R zsh ${=${options[xtrace]:#off}:+-o xtrace} 4 | builtin setopt extended_glob 5 | 6 | local pkg=$1 7 | if [[ -z $pkg || ! -e $pkg ]] { 8 | print -u2 -Pr "%F{160}rpm2cpio.sh%f: no package supplied" 9 | exit 1 10 | } 11 | 12 | local leadsize=96 13 | local o=$(( $leadsize + 8 )) 14 | set -- ${(s: :)$(od -j $o -N 8 -t u1 $pkg)} 15 | local i=$(( 256 * ( 256 * ( 256 * $2 + $3 ) + $4 ) + $5 )) 16 | local d=$(( 256 * ( 256 * ( 256 * $6 + $7 ) + $8 ) + $9 )) 17 | 18 | sigsize=$(( 8 + 16 * $i + $d )) 19 | o=$(( $o + $sigsize + ( 8 - ( $sigsize % 8 ) ) % 8 + 8 )) 20 | set -- ${(s: :)$(od -j $o -N 8 -t u1 $pkg)} 21 | i=$(( 256 * ( 256 * ( 256 * $2 + $3 ) + $4 ) + $5 )) 22 | d=$(( 256 * ( 256 * ( 256 * $6 + $7 ) + $8 ) + $9 )) 23 | 24 | local hdrsize=$(( 8 + 16 * $i + $d )) 25 | o=$(( $o + $hdrsize )) 26 | local -a UNPACKCMD 27 | UNPACKCMD=( dd if=$pkg ibs=$o skip=1 ) 28 | 29 | local COMPRESSION="$($=UNPACKCMD | file -)" 30 | local -a DECOMPRESSCMD 31 | 32 | if [[ $COMPRESSION == (#i)*gzip* ]] { 33 | DECOMPRESSCMD=( gunzip ) 34 | } elif [[ $COMPRESSION == (#i)*bzip2* ]] { 35 | DECOMPRESSCMD=( bunzip2 ) 36 | } elif [[ $COMPRESSION == (#i)*xz* ]] { 37 | DECOMPRESSCMD=( unxz ) 38 | } elif [[ $COMPRESSION == (#i)*cpio* ]] { 39 | DECOMPRESSCMD=( cat ) 40 | } else { 41 | DECOMPRESSCMD=( $(which unlzma 2>/dev/null) ) 42 | if [[ $DECOMPRESSCMD != /* ]] { 43 | DECOMPRESSCMD=( $(which lzmash 2>/dev/null) ) 44 | if [[ $DECOMPRESSCMD == /* ]] { 45 | DECOMPRESSCMD=( lzmash -d -c ) 46 | } else { 47 | DECOMPRESSCMD=( cat ) 48 | } 49 | } 50 | } 51 | 52 | command "$UNPACKCMD[@]" 2>/dev/null | command "$DECOMPRESSCMD[@]" 53 | -------------------------------------------------------------------------------- /lib/zsh/side.zsh: -------------------------------------------------------------------------------- 1 | # -*- mode: zsh; sh-indentation: 2; indent-tabs-mode: nil; sh-basic-offset: 2; -*- 2 | # vim: ft=zsh sw=2 ts=2 et 3 | # 4 | # Copyright (c) 2016-2020 Sebastian Gniazdowski and contributors. 5 | # Copyright (c) 2021 Salvydas Lukosius and Z-Shell Community. 6 | 7 | # FUNCTION: .zi-exists-physically [[[ 8 | # Checks if directory of given plugin exists in PLUGIN_DIR. 9 | # 10 | # Testable. 11 | # 12 | # $1 - plugin spec (4 formats: user---plugin, user/plugin, user, plugin) 13 | # $2 - plugin (only when $1 - i.e. user - given) 14 | .zi-exists-physically() { 15 | .zi-any-to-user-plugin "$1" "$2" 16 | if [[ ${reply[-2]} = % ]]; then 17 | [[ -d ${reply[-1]} ]] && return 0 || return 1 18 | else 19 | [[ -d ${ZI[PLUGINS_DIR]}/${reply[-2]:+${reply[-2]}---}${reply[-1]//\//---} ]] && return 0 || return 1 20 | fi 21 | } # ]]] 22 | # FUNCTION: .zi-exists-physically-message [[[ 23 | # Checks if directory of given plugin exists in PLUGIN_DIR, and outputs error message if it doesn't. 24 | # 25 | # Testable. 26 | # 27 | # $1 - plugin spec (4 formats: user---plugin, user/plugin, user, plugin) 28 | # $2 - plugin (only when $1 - i.e. user - given) 29 | .zi-exists-physically-message() { 30 | builtin emulate -LR zsh ${=${options[xtrace]:#off}:+-o xtrace} 31 | builtin setopt extendedglob warncreateglobal typesetsilent noshortloops rcquotes 32 | if ! .zi-exists-physically "$1" "$2"; then 33 | .zi-any-to-user-plugin "$1" "$2" 34 | if [[ $reply[1] = % ]] { 35 | .zi-any-to-pid "$1" "$2" 36 | local spec1=$REPLY 37 | if [[ $1 = %* ]] { 38 | local spec2=%${1#%}${${1#%}:+${2:+/}}$2 39 | } elif [[ -z $1 || -z $2 ]] { 40 | local spec3=%${1#%}${2#%} 41 | } 42 | } else { 43 | integer nospec=1 44 | } 45 | .zi-any-colorify-as-uspl2 "$1" "$2" 46 | 47 | +zi-message "{error}No such (plugin or snippet){rst}: $REPLY." 48 | [[ $nospec -eq 0 && $spec1 != $spec2 ]] && +zi-message "(expands to: {file}${spec2#%}{rst})." 49 | return 1 50 | fi 51 | return 0 52 | } # ]]] 53 | # FUNCTION: .zi-first [[[ 54 | # Finds the main file of plugin. There are multiple file name formats, they are ordered in order starting from more correct 55 | # ones, and matched. .zi-load-plugin() has similar code parts and doesn't call .zi-first() – for performance. Obscure matching 56 | # is done in .zi-find-other-matches, here and in .zi-load(). Obscure = non-standard main-file naming convention. 57 | # 58 | # $1 - plugin spec (4 formats: user---plugin, user/plugin, user, plugin) 59 | # $2 - plugin (only when $1 - i.e. user - given) 60 | .zi-first() { 61 | .zi-any-to-user-plugin "$1" "$2" 62 | local user="${reply[-2]}" plugin="${reply[-1]}" 63 | 64 | .zi-any-to-pid "$1" "$2" 65 | .zi-get-object-path plugin "$REPLY" 66 | integer ret=$? 67 | local dname="$REPLY" 68 | (( ret )) && { reply=( "$dname" "" ); return 1; } 69 | # Look for file to compile. First look for the most common one 70 | # (optimization) then for other possibilities 71 | if [[ -e "$dname/$plugin.plugin.zsh" ]]; then 72 | reply=( "$dname/$plugin.plugin.zsh" ) 73 | else 74 | .zi-find-other-matches "$dname" "$plugin" 75 | fi 76 | if [[ "${#reply}" -eq "0" ]]; then 77 | reply=( "$dname" "" ) 78 | return 1 79 | fi 80 | # Take first entry (ksharrays resilience) 81 | reply=( "$dname" "${reply[-${#reply}]}" ) 82 | return 0 83 | } # ]]] 84 | # FUNCTION: .zi-any-colorify-as-uspl2 [[[ 85 | # Returns ANSI-colorified "user/plugin" string, from any supported plugin spec (user---plugin, user/plugin, user plugin, plugin). 86 | # 87 | # $1 - plugin spec (4 formats: user---plugin, user/plugin, user, plugin) 88 | # $2 - plugin (only when $1 - i.e. user - given) 89 | # $REPLY = ANSI-colorified "user/plugin" string 90 | .zi-any-colorify-as-uspl2() { 91 | .zi-any-to-user-plugin "$1" "$2" 92 | local user="${reply[-2]}" plugin="${reply[-1]}" 93 | if [[ "$user" = "%" ]] { 94 | .zi-any-to-pid "" $plugin 95 | REPLY="${REPLY/https--github.com--(robbyrussell--oh-my-zsh|ohmyzsh--ohmyzsh)--trunk--plugins--/OMZP::}" 96 | REPLY="${REPLY/https--github.com--(robbyrussell--oh-my-zsh|ohmyzsh--ohmyzsh)--trunk--plugins/OMZP}" 97 | REPLY="${REPLY/https--github.com--(robbyrussell--oh-my-zsh|ohmyzsh--ohmyzsh)--trunk--lib--/OMZL::}" 98 | REPLY="${REPLY/https--github.com--(robbyrussell--oh-my-zsh|ohmyzsh--ohmyzsh)--trunk--lib/OMZL}" 99 | REPLY="${REPLY/https--github.com--(robbyrussell--oh-my-zsh|ohmyzsh--ohmyzsh)--trunk--themes--/OMZT::}" 100 | REPLY="${REPLY/https--github.com--(robbyrussell--oh-my-zsh|ohmyzsh--ohmyzsh)--trunk--themes/OMZT}" 101 | REPLY="${REPLY/https--github.com--(robbyrussell--oh-my-zsh|ohmyzsh--ohmyzsh)--trunk--/OMZ::}" 102 | REPLY="${REPLY/https--github.com--(robbyrussell--oh-my-zsh|ohmyzsh--ohmyzsh)--trunk/OMZ}" 103 | REPLY="${REPLY/https--github.com--sorin-ionescu--prezto--trunk--modules--/PZTM::}" 104 | REPLY="${REPLY/https--github.com--sorin-ionescu--prezto--trunk--modules/PZTM}" 105 | REPLY="${REPLY/https--github.com--sorin-ionescu--prezto--trunk--/PZT::}" 106 | REPLY="${REPLY/https--github.com--sorin-ionescu--prezto--trunk/PZT}" 107 | REPLY="${REPLY/(#b)%([A-Z]##)(#c0,1)(*)/%$ZI[col-uname]$match[1]$ZI[col-pname]$match[2]$ZI[col-rst]}" 108 | } elif [[ $user == http(|s): ]] { 109 | REPLY="${ZI[col-ice]}${user}/${plugin}${ZI[col-rst]}" 110 | } else { 111 | REPLY="${user:+${ZI[col-uname]}${user}${ZI[col-rst]}/}${ZI[col-pname]}${plugin}${ZI[col-rst]}" 112 | } 113 | } # ]]] 114 | # FUNCTION: .zi-two-paths [[[ 115 | # Obtains a snippet URL without specification if it is an SVN URL (points to directory) or regular URL (points to file), 116 | # returns 2 possible paths for further examination 117 | .zi-two-paths() { 118 | builtin emulate -LR zsh ${=${options[xtrace]:#off}:+-o xtrace} 119 | builtin setopt extendedglob typesetsilent warncreateglobal noshortloops 120 | 121 | local url=$1 url1 url2 local_dirA dirnameA svn_dirA local_dirB dirnameB 122 | local -a fileB_there 123 | # Remove leading whitespace and trailing / 124 | url="${${url#"${url%%[! $'\t']*}"}%/}" 125 | url1=$url url2=$url 126 | 127 | .zi-get-object-path snippet "$url1" 128 | local_dirA=$reply[-3] dirnameA=$reply[-2] 129 | [[ -d "$local_dirA/$dirnameA/.svn" ]] && { 130 | svn_dirA=".svn" 131 | if { .zi-first % "$local_dirA/$dirnameA"; } { 132 | fileB_there=( ${reply[-1]} ) 133 | } 134 | } 135 | 136 | .zi-get-object-path snippet "$url2" 137 | local_dirB=$reply[-3] dirnameB=$reply[-2] 138 | [[ -z $svn_dirA ]] && \ 139 | fileB_there=( "$local_dirB/$dirnameB"/*~*.(zwc|md|js|html)(.-DOnN[1]) ) 140 | reply=( "$local_dirA/$dirnameA" "$svn_dirA" "$local_dirB/$dirnameB" "${fileB_there[1]##$local_dirB/$dirnameB/#}" ) 141 | } # ]]] 142 | # FUNCTION: .zi-compute-ice [[[ 143 | # Computes ICE array (default, it can be specified via $3) from a) input ICE, b) static ice, c) saved ice, 144 | # taking priorities into account. Also returns path to snippet directory and optional name of snippet file 145 | # (only valid if ICE[svn] is not set). 146 | # 147 | # Can also pack resulting ices into ZI_SICE (see $2). 148 | # 149 | # $1 - URL (also plugin-spec) 150 | # $2 - "pack" or "nopack" or "pack-nf" - packing means ICE 151 | # wins with static ice; "pack-nf" means that disk-ices will 152 | # be ignored (no-file?) 153 | # $3 - name of output associative array, "ICE" is the default 154 | # $4 - name of output string parameter, to hold path to directory ("local_dir") 155 | # $5 - name of output string parameter, to hold filename ("filename") 156 | # $6 - name of output string parameter, to hold is-snippet 0/1-bool ("is_snippet") 157 | .zi-compute-ice() { 158 | builtin emulate -LR zsh ${=${options[xtrace]:#off}:+-o xtrace} 159 | builtin setopt extendedglob typesetsilent warncreateglobal noshortloops 160 | 161 | local ___URL="${1%/}" ___pack="$2" ___is_snippet=0 162 | local ___var_name1="${3:-ZI_ICE}" ___var_name2="${4:-local_dir}" ___var_name3="${5:-filename}" ___var_name4="${6:-is_snippet}" 163 | # Copy from .zi-recall 164 | local -a ice_order nval_ices 165 | ice_order=( 166 | ${(As:|:)ZI[ice-list]} 167 | # Include all additional ices – after stripping them from the possible: '' 168 | ${(@)${(@Akons:|:u)${ZI_EXTS[ice-mods]//\'\'/}}/(#s)<->-/} 169 | ) 170 | nval_ices=( 171 | ${(As:|:)ZI[nval-ice-list]} 172 | # Include only those additional ices, don't have the '' in their name, i.e aren't designed to hold value 173 | ${(@)${(@)${(@Akons:|:u)${ZI_EXTS[ice-mods]//\'\'/}}/(#s)<->-/}} 174 | # Must be last 175 | svn 176 | ) 177 | # Remove whitespace from beginning of URL 178 | ___URL="${${___URL#"${___URL%%[! $'\t']*}"}%/}" 179 | # Snippet? 180 | .zi-two-paths "$___URL" 181 | local ___s_path="${reply[-4]}" ___s_svn="${reply[-3]}" ___path="${reply[-2]}" ___filename="${reply[-1]}" ___local_dir 182 | if [[ -d "$___s_path" || -d "$___path" ]]; then 183 | ___is_snippet=1 184 | else 185 | # Plugin 186 | .zi-any-to-user-plugin "$___URL" "" 187 | local ___user="${reply[-2]}" ___plugin="${reply[-1]}" 188 | ___s_path="" ___filename="" 189 | [[ "$___user" = "%" ]] && ___path="$___plugin" || ___path="${ZI[PLUGINS_DIR]}/${___user:+${___user}---}${___plugin//\//---}" 190 | .zi-exists-physically-message "$___user" "$___plugin" || return 1 191 | fi 192 | [[ $___pack = pack* ]] && (( ${#ICE} > 0 )) && .zi-pack-ice "${___user-$___URL}" "$___plugin" 193 | local -A ___sice 194 | local -a ___tmp 195 | ___tmp=( "${(z@)ZI_SICE[${___user-$___URL}${${___user:#(%|/)*}:+/}$___plugin]}" ) 196 | (( ${#___tmp[@]} > 1 && ${#___tmp[@]} % 2 == 0 )) && ___sice=( "${(Q)___tmp[@]}" ) 197 | 198 | if [[ "${+___sice[svn]}" = "1" || -n "$___s_svn" ]]; then 199 | if (( !___is_snippet && ${+___sice[svn]} == 1 )); then 200 | builtin print -r -- "The \`svn' ice is given, but the argument ($___URL) is a plugin" 201 | builtin print -r -- "(\`svn' can be used only with snippets)" 202 | return 1 203 | elif (( !___is_snippet )); then 204 | builtin print -r -- "Undefined behavior #1 occurred, please report at https://github.com/z-shell/zi/issues" 205 | return 1 206 | fi 207 | if [[ -e "$___s_path" && -n "$___s_svn" ]]; then 208 | ___sice[svn]="" 209 | ___local_dir="$___s_path" 210 | else 211 | [[ ! -e "$___path" ]] && { builtin print -r -- "No such snippet, looked at paths (1): $___s_path, and: $___path"; return 1; } 212 | unset '___sice[svn]' 213 | ___local_dir="$___path" 214 | fi 215 | else 216 | if [[ -e "$___path" ]]; then 217 | unset '___sice[svn]' 218 | ___local_dir="$___path" 219 | else 220 | builtin print -r -- "No such snippet, looked at paths (2): $___s_path, and: $___path" 221 | return 1 222 | fi 223 | fi 224 | 225 | local ___zi_path="$___local_dir/._zi" 226 | 227 | # Rename Zplugin > ZI 228 | if [[ ! -d $___zi_path && -d $___local_dir/._zplugin ]]; then 229 | ( 230 | builtin print -Pr -- "${ZI[col-pre]}UPGRADING THE DIRECTORY STRUCTURE" "FOR THE ZPLUGIN -> ZI RENAME…%f" 231 | builtin cd -q ${ZI[PLUGINS_DIR]} || return 1 232 | autoload -Uz zmv 233 | ( zmv -W '**/._zplugin' '**/._zi' ) &>/dev/null 234 | builtin cd -q ${ZI[SNIPPETS_DIR]} || return 1 235 | ( zmv -W '**/._zplugin' '**/._zi' ) &>/dev/null 236 | builtin print -Pr -- "${ZI[col-obj]}THE UPGRADE SUCCEDED!%f" 237 | ) || builtin print -Pr -- "${ZI[col-error]}THE UPGRADE FAILED!%f" 238 | fi 239 | 240 | # Rename Zinit > ZI 241 | if [[ ! -d $___zi_path && -d $___local_dir/._zinit ]]; then 242 | ( 243 | builtin print -Pr -- "${ZI[col-pre]}UPGRADING THE DIRECTORY STRUCTURE" "FOR THE ZINIT -> ZI RENAME…%f" 244 | builtin cd -q ${ZI[PLUGINS_DIR]} || return 1 245 | autoload -Uz zmv 246 | ( zmv -W '**/.zinit' '**/._zi' ) &>/dev/null 247 | builtin cd -q ${ZI[SNIPPETS_DIR]} || return 1 248 | ( zmv -W '**/._zinit' '**/._zi' ) &>/dev/null 249 | builtin print -Pr -- "${ZI[col-obj]}THE UPGRADE SUCCEDED!%f" 250 | ) || builtin print -Pr -- "${ZI[col-error]}THE UPGRADE FAILED!%f" 251 | fi 252 | 253 | # Read disk-Ice 254 | local -A ___mdata 255 | local ___key 256 | { for ___key in mode url is_release is_release{2..5} ${ice_order[@]}; do 257 | [[ -f "$___zi_path/$___key" ]] && ___mdata[$___key]="$(<$___zi_path/$___key)" 258 | done 259 | [[ "${___mdata[mode]}" = "1" ]] && ___mdata[svn]="" 260 | } 2>/dev/null 261 | # Handle flag-Ices; svn must be last 262 | for ___key in ${ice_order[@]}; do 263 | [[ $___key == (no|)compile ]] && continue 264 | (( 0 == ${+ICE[no$___key]} && 0 == ${+___sice[no$___key]} )) && continue 265 | # "If there is such ice currently, and there's no no* ice given, and there's the no* ice in the static ice" – skip, don't unset. 266 | # With conjunction with the previous line this has the proper meaning: uset if at least in one – current or static – ice 267 | # there's the no* ice, but not if it's only in the static ice (unless there's on such ice "anyway"). 268 | (( 1 == ${+ICE[$___key]} && 0 == ${+ICE[no$___key]} && 1 == ${+___sice[no$___key]} )) && continue 269 | if [[ "$___key" = "svn" ]]; then 270 | command builtin print -r -- "0" >! "$___zi_path/mode" 271 | ___mdata[mode]=0 272 | else 273 | command rm -f -- "$___zi_path/$___key" 274 | fi 275 | unset "___mdata[$___key]" "___sice[$___key]" "ICE[$___key]" 276 | done 277 | 278 | # Final decision, static ice vs. saved ice 279 | local -A ___MY_ICE 280 | for ___key in mode url is_release is_release{2..5} ${ice_order[@]}; do 281 | # The second sum is: if the pack is *not* pack-nf, then depending on the disk availability, otherwise: no disk ice 282 | (( ${+___sice[$___key]} + ${${${___pack:#pack-nf*}:+${+___mdata[$___key]}}:-0} )) && ___MY_ICE[$___key]="${___sice[$___key]-${___mdata[$___key]}}" 283 | done 284 | # One more round for the special case – update, which ALWAYS needs the teleid from the disk or static ice 285 | ___key=teleid; [[ "$___pack" = pack-nftid ]] && { 286 | (( ${+___sice[$___key]} + ${+___mdata[$___key]} )) && ___MY_ICE[$___key]="${___sice[$___key]-${___mdata[$___key]}}" 287 | } 288 | 289 | : ${(PA)___var_name1::="${(kv)___MY_ICE[@]}"} 290 | : ${(P)___var_name2::=$___local_dir} 291 | : ${(P)___var_name3::=$___filename} 292 | : ${(P)___var_name4::=$___is_snippet} 293 | 294 | return 0 295 | } # ]]] 296 | # FUNCTION: .zi-store-ices [[[ 297 | # Saves ice mods in given hash onto disk. 298 | # 299 | # $1 - directory where to create / delete files 300 | # $2 - name of hash that holds values 301 | # $3 - additional keys of hash to store, space separated 302 | # $4 - additional keys of hash to store, empty-meaningful ices, space separated 303 | # $5 - the URL, if applicable 304 | # $6 - the mode (1 - svn, 0 - single file), if applicable 305 | .zi-store-ices() { 306 | local ___pfx="$1" ___ice_var="$2" ___add_ices="$3" ___add_ices2="$4" url="$5" mode="$6" 307 | # Copy from .zi-recall 308 | local -a ice_order nval_ices 309 | ice_order=( 310 | ${(As:|:)ZI[ice-list]} 311 | # Include all additional ices – after stripping them from the possible: '' 312 | ${(@)${(@Akons:|:u)${ZI_EXTS[ice-mods]//\'\'/}}/(#s)<->-/} 313 | ) 314 | nval_ices=( 315 | ${(As:|:)ZI[nval-ice-list]} 316 | # Include only those additional ices, don't have the '' in their name, i.e. aren't designed to hold value 317 | ${(@)${(@)${(@Akons:|:u)${ZI_EXTS[ice-mods]//\'\'/}}/(#s)<->-/}} 318 | # Must be last 319 | svn 320 | ) 321 | command mkdir -p "$___pfx" 322 | local ___key ___var_name 323 | # No nval_ices here 324 | for ___key in ${ice_order[@]:#(${(~j:|:)nval_ices[@]})} ${(s: :)___add_ices[@]}; do 325 | ___var_name="${___ice_var}[$___key]" 326 | (( ${(P)+___var_name} )) && builtin print -r -- "${(P)___var_name}" >! "$___pfx"/"$___key" 327 | done 328 | # Ices that even empty mean something 329 | for ___key in ${nval_ices[@]} ${(s: :)___add_ices2[@]}; do 330 | ___var_name="${___ice_var}[$___key]" 331 | if (( ${(P)+___var_name} )) { 332 | builtin print -r -- "${(P)___var_name}" >! "$___pfx"/"$___key" 333 | } else { 334 | command rm -f "$___pfx"/"$___key" 335 | } 336 | done 337 | # url and mode are declared at the beginning of the body 338 | for ___key in url mode; do 339 | [[ -n "${(P)___key}" ]] && builtin print -r -- "${(P)___key}" >! "$___pfx"/"$___key" 340 | done 341 | } # ]]] 342 | # FUNCTION: .zi-countdown [[[ 343 | # Displays a countdown 5...4... etc. and returns 0 if it 344 | # sucessfully reaches 0, or 1 if Ctrl-C will be pressed. 345 | .zi-countdown() { 346 | (( !${+ICE[countdown]} )) && return 0 347 | builtin emulate -L zsh -o extendedglob ${=${options[xtrace]:#off}:+-o xtrace} 348 | trap "+zi-message \"{ehi}ABORTING, the ice {ice}$ice{ehi} not ran{rst}\"; return 1" INT 349 | local count=5 tpe="$1" ice 350 | ice="${ICE[$tpe]}" 351 | [[ $tpe = "atpull" && $ice = "%atclone" ]] && ice="${ICE[atclone]}" 352 | ice="{b}{ice}$tpe{ehi}:{rst}${ice//(#b)(\{[a-z0-9…–_-]##\})/\\$match[1]}" 353 | +zi-message -n "{hi}Running $ice{rst}{hi} ice in...{rst} " 354 | while (( -- count + 1 )) { 355 | +zi-message -n -- "{b}{error}"$(( count + 1 ))"{rst}{…}" 356 | sleep 1 357 | } 358 | +zi-message -r -- "{b}{error}0 {rst}{…}" 359 | return 0 360 | } # ]]] 361 | # FUNCTION: .zi-check-module. [[[ 362 | # Check module. Don't trust access times and verify hard stored values. 363 | .zi-check-module() { 364 | [[ -e ${ZI[ZMODULES_DIR]}/zpmod/COMPILED_AT ]] && \ 365 | local compiled_at_ts="$(<${ZI[ZMODULES_DIR]}/zpmod/COMPILED_AT)" 366 | [[ -e ${ZI[ZMODULES_DIR]}/zpmod/RECOMPILE_REQUEST ]] && \ 367 | local recompile_request_ts="$(<${ZI[ZMODULES_DIR]}/zpmod/RECOMPILE_REQUEST)" 368 | if [[ ${recompile_request_ts:-1} -gt ${compiled_at_ts:-0} ]]; then 369 | +zi-message "{u-warn}WARNING{b-warn}:{rst}{msg} A {lhi}recompilation{rst}" \ 370 | "of the zpmod module has been requested… {hi}Building{rst}…" 371 | (( ${+functions[.zi-confirm]} )) || builtin source "${ZI[BIN_DIR]}/lib/zsh/autoload.zsh" || return 1 372 | command make -C "${ZI[ZMODULES_DIR]}/zpmod" distclean &>/dev/null 373 | .zi-module build &>/dev/null 374 | if command make -C "${ZI[ZMODULES_DIR]}/zpmod" &>/dev/null; then 375 | +zi-message "{ok}Build successful!{rst}" 376 | return 0 377 | else 378 | builtin print -r -- "${ZI[col-error]}Compilation failed.${ZI[col-rst]}" \ 379 | "${ZI[col-pre]}You can enter the following command:${ZI[col-rst]}" \ 380 | 'make -C ${ZI[ZMODULES_DIR]}/zpmod' "${ZI[col-pre]}to see the error messages and e.g.: report an issue" \ 381 | "at GitHub${ZI[col-rst]}" 382 | return 1 383 | fi 384 | fi 385 | } # ]]] 386 | -------------------------------------------------------------------------------- /lib/zsh/single-line.zsh: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env zsh 2 | 3 | builtin emulate -R zsh ${=${options[xtrace]:#off}:+-o xtrace} 4 | builtin setopt extended_glob warn_create_global typeset_silent no_short_loops rc_quotes 5 | 6 | local zero=$'\0' r=$'\r' n=$'\n' IFS= 7 | { command perl -pe 'BEGIN { $|++; $/ = \1 }; tr/\r\n/\n\0/' || gstdbuf -o0 gtr '\r\n' '\n\0' || \ 8 | stdbuf -o0 tr '\r\n' '\n\0'; print } 2>/dev/null | while read -r line; do 9 | if [[ $line == *$zero* ]]; then 10 | # Unused by cURL (there's no newline after the previous progress bar) print -nr -- $r${(l:COLUMNS:: :):-}$r${line##*$zero} 11 | print -nr -- $r${(l:COLUMNS:: :):-}$r${line%$zero} 12 | else 13 | print -nr -- $r${(l:COLUMNS:: :):-}$r${${line//[$r$n]/}%\%*}${${(M)line%\%}:+%} 14 | fi 15 | done 16 | print 17 | --------------------------------------------------------------------------------